1
1
mirror of https://github.com/go-gitea/gitea synced 2025-08-04 08:38:37 +00:00

Rework delete org and rename org UI (#34762)

# What's the problem of the original implementation

Renaming organization will mix with organization's information change
make the operation difficult to keep consistent.

This PR created a danger zone like what's repository setting. It also
moved organization's `rename` and `delete` operations to this zone. The
original updating repository will not change the name any more.

This is also a step to extract the `updaterepository` function
completely.

Before:


![image](https://github.com/user-attachments/assets/d097dfdf-07be-4d79-8fcf-e78822515575)

![image](https://github.com/user-attachments/assets/42ee832c-cb44-41ec-9fe3-92a1c94747d2)

After:


![image](https://github.com/user-attachments/assets/f7700ed7-f104-4302-a924-09e118f24be3)

![image](https://github.com/user-attachments/assets/4c49952a-578e-4d14-bd01-4a68c9e02412)

![image](https://github.com/user-attachments/assets/814829d3-00fe-4e87-ae05-625c129170d2)

![image](https://github.com/user-attachments/assets/b067b263-c909-4b48-b23c-73481c32d350)

---------

Co-authored-by: wxiaoguang <wxiaoguang@gmail.com>
This commit is contained in:
Lunny Xiao
2025-06-22 02:21:48 +08:00
committed by GitHub
parent 4fc626daa1
commit 7de114a332
17 changed files with 314 additions and 211 deletions

View File

@@ -1,35 +0,0 @@
{{template "org/settings/layout_head" (dict "ctxData" . "pageClass" "organization settings delete")}}
<div class="org-setting-content">
<h4 class="ui top attached error header">
{{ctx.Locale.Tr "org.settings.delete_account"}}
</h4>
<div class="ui attached error segment">
<div class="ui red message">
<p class="text left">{{svg "octicon-alert"}} {{ctx.Locale.Tr "org.settings.delete_prompt"}}</p>
</div>
<form class="ui form ignore-dirty" id="delete-form" action="{{.Link}}" method="post">
{{.CsrfTokenHtml}}
<div class="inline required field {{if .Err_OrgName}}error{{end}}">
<label for="org_name">{{ctx.Locale.Tr "org.org_name_holder"}}</label>
<input id="org_name" name="org_name" value="" autocomplete="off" autofocus required>
</div>
<button class="ui red button delete-button" data-type="form" data-form="#delete-form">
{{ctx.Locale.Tr "org.settings.confirm_delete_account"}}
</button>
</form>
</div>
</div>
<div class="ui g-modal-confirm delete modal">
<div class="header">
{{svg "octicon-trash"}}
{{ctx.Locale.Tr "org.settings.delete_org_title"}}
</div>
<div class="content">
<p>{{ctx.Locale.Tr "org.settings.delete_org_desc"}}</p>
</div>
{{template "base/modal_actions_confirm" .}}
</div>
{{template "org/settings/layout_footer" .}}

View File

@@ -41,8 +41,5 @@
</div>
</details>
{{end}}
<a class="{{if .PageIsSettingsDelete}}active {{end}}item" href="{{.OrgLink}}/settings/delete">
{{ctx.Locale.Tr "org.settings.delete"}}
</a>
</div>
</div>

View File

@@ -1,101 +1,97 @@
{{template "org/settings/layout_head" (dict "ctxData" . "pageClass" "organization settings options")}}
<div class="org-setting-content">
<h4 class="ui top attached header">
{{ctx.Locale.Tr "org.settings.options"}}
</h4>
<div class="ui attached segment">
<form class="ui form" action="{{.Link}}" method="post">
{{.CsrfTokenHtml}}
<div class="required field {{if .Err_Name}}error{{end}}">
<label for="org_name">{{ctx.Locale.Tr "org.org_name_holder"}}
<span class="text red tw-hidden" id="org-name-change-prompt">
<br>{{ctx.Locale.Tr "org.settings.change_orgname_prompt"}}<br>{{ctx.Locale.Tr "org.settings.change_orgname_redirect_prompt"}}
</span>
</label>
<input id="org_name" name="name" value="{{.Org.Name}}" data-org-name="{{.Org.Name}}" required maxlength="40">
</div>
<div class="field {{if .Err_FullName}}error{{end}}">
<label for="full_name">{{ctx.Locale.Tr "org.org_full_name_holder"}}</label>
<input id="full_name" name="full_name" value="{{.Org.FullName}}" maxlength="100">
</div>
<div class="field {{if .Err_Email}}error{{end}}">
<label for="email">{{ctx.Locale.Tr "org.settings.email"}}</label>
<input id="email" name="email" type="email" value="{{.Org.Email}}" maxlength="255">
</div>
<div class="field {{if .Err_Description}}error{{end}}">
{{/* it is rendered as markdown, but the length is limited, so at the moment we do not use the markdown editor here */}}
<label for="description">{{ctx.Locale.Tr "org.org_desc"}}</label>
<textarea id="description" name="description" rows="2" maxlength="255">{{.Org.Description}}</textarea>
</div>
<div class="field {{if .Err_Website}}error{{end}}">
<label for="website">{{ctx.Locale.Tr "org.settings.website"}}</label>
<input id="website" name="website" type="url" value="{{.Org.Website}}" maxlength="255">
</div>
<div class="field">
<label for="location">{{ctx.Locale.Tr "org.settings.location"}}</label>
<input id="location" name="location" value="{{.Org.Location}}" maxlength="50">
</div>
<div class="divider"></div>
<div class="field" id="visibility_box">
<label for="visibility">{{ctx.Locale.Tr "org.settings.visibility"}}</label>
<div class="field">
<div class="ui radio checkbox">
<input class="enable-system-radio" name="visibility" type="radio" value="0" {{if eq .CurrentVisibility 0}}checked{{end}}>
<label>{{ctx.Locale.Tr "org.settings.visibility.public"}}</label>
</div>
</div>
<div class="field">
<div class="ui radio checkbox">
<input class="enable-system-radio" name="visibility" type="radio" value="1" {{if eq .CurrentVisibility 1}}checked{{end}}>
<label>{{ctx.Locale.Tr "org.settings.visibility.limited"}}</label>
</div>
</div>
<div class="field">
<div class="ui radio checkbox">
<input class="enable-system-radio" name="visibility" type="radio" value="2" {{if eq .CurrentVisibility 2}}checked{{end}}>
<label>{{ctx.Locale.Tr "org.settings.visibility.private"}}</label>
</div>
</div>
</div>
<div class="ui segments org-setting-content">
<h4 class="ui top attached header">
{{ctx.Locale.Tr "org.settings.options"}}
</h4>
<div class="ui attached segment">
<form class="ui form" action="{{.Link}}" method="post">
{{.CsrfTokenHtml}}
<div class="field {{if .Err_FullName}}error{{end}}">
<label for="full_name">{{ctx.Locale.Tr "org.org_full_name_holder"}}</label>
<input id="full_name" name="full_name" value="{{.Org.FullName}}" maxlength="100">
</div>
<div class="field {{if .Err_Email}}error{{end}}">
<label for="email">{{ctx.Locale.Tr "org.settings.email"}}</label>
<input id="email" name="email" type="email" value="{{.Org.Email}}" maxlength="255">
</div>
<div class="field {{if .Err_Description}}error{{end}}">
{{/* it is rendered as markdown, but the length is limited, so at the moment we do not use the markdown editor here */}}
<label for="description">{{ctx.Locale.Tr "org.org_desc"}}</label>
<textarea id="description" name="description" rows="2" maxlength="255">{{.Org.Description}}</textarea>
</div>
<div class="field {{if .Err_Website}}error{{end}}">
<label for="website">{{ctx.Locale.Tr "org.settings.website"}}</label>
<input id="website" name="website" type="url" value="{{.Org.Website}}" maxlength="255">
</div>
<div class="field">
<label for="location">{{ctx.Locale.Tr "org.settings.location"}}</label>
<input id="location" name="location" value="{{.Org.Location}}" maxlength="50">
</div>
<div class="field" id="permission_box">
<label>{{ctx.Locale.Tr "org.settings.permission"}}</label>
<div class="field">
<div class="ui checkbox">
<input type="checkbox" name="repo_admin_change_team_access" {{if .RepoAdminChangeTeamAccess}}checked{{end}}>
<label>{{ctx.Locale.Tr "org.settings.repoadminchangeteam"}}</label>
</div>
</div>
</div>
{{if .SignedUser.IsAdmin}}
<div class="divider"></div>
<div class="inline field {{if .Err_MaxRepoCreation}}error{{end}}">
<label for="max_repo_creation">{{ctx.Locale.Tr "admin.users.max_repo_creation"}}</label>
<input id="max_repo_creation" name="max_repo_creation" type="number" min="-1" value="{{.Org.MaxRepoCreation}}">
<p class="help">{{ctx.Locale.Tr "admin.users.max_repo_creation_desc"}}</p>
</div>
{{end}}
<div class="field">
<button class="ui primary button">{{ctx.Locale.Tr "org.settings.update_settings"}}</button>
</div>
</form>
<div class="divider"></div>
<form class="ui form" action="{{.Link}}/avatar" method="post" enctype="multipart/form-data">
{{.CsrfTokenHtml}}
<div class="inline field">
{{template "shared/avatar_upload_crop" dict "LabelText" (ctx.Locale.Tr "settings.choose_new_avatar")}}
</div>
<div class="field">
<button class="ui primary button">{{ctx.Locale.Tr "settings.update_avatar"}}</button>
<button class="ui red button link-action" data-url="{{.Link}}/avatar/delete">{{ctx.Locale.Tr "settings.delete_current_avatar"}}</button>
</div>
</form>
<div class="divider"></div>
<div class="field" id="visibility_box">
<label for="visibility">{{ctx.Locale.Tr "org.settings.visibility"}}</label>
<div class="field">
<div class="ui radio checkbox">
<input class="enable-system-radio" name="visibility" type="radio" value="0" {{if eq .CurrentVisibility 0}}checked{{end}}>
<label>{{ctx.Locale.Tr "org.settings.visibility.public"}}</label>
</div>
</div>
<div class="field">
<div class="ui radio checkbox">
<input class="enable-system-radio" name="visibility" type="radio" value="1" {{if eq .CurrentVisibility 1}}checked{{end}}>
<label>{{ctx.Locale.Tr "org.settings.visibility.limited"}}</label>
</div>
</div>
<div class="field">
<div class="ui radio checkbox">
<input class="enable-system-radio" name="visibility" type="radio" value="2" {{if eq .CurrentVisibility 2}}checked{{end}}>
<label>{{ctx.Locale.Tr "org.settings.visibility.private"}}</label>
</div>
</div>
</div>
<div class="field" id="permission_box">
<label>{{ctx.Locale.Tr "org.settings.permission"}}</label>
<div class="field">
<div class="ui checkbox">
<input type="checkbox" name="repo_admin_change_team_access" {{if .RepoAdminChangeTeamAccess}}checked{{end}}>
<label>{{ctx.Locale.Tr "org.settings.repoadminchangeteam"}}</label>
</div>
</div>
</div>
{{if .SignedUser.IsAdmin}}
<div class="divider"></div>
<div class="inline field {{if .Err_MaxRepoCreation}}error{{end}}">
<label for="max_repo_creation">{{ctx.Locale.Tr "admin.users.max_repo_creation"}}</label>
<input id="max_repo_creation" name="max_repo_creation" type="number" min="-1" value="{{.Org.MaxRepoCreation}}">
<p class="help">{{ctx.Locale.Tr "admin.users.max_repo_creation_desc"}}</p>
</div>
{{end}}
<div class="field">
<button class="ui primary button">{{ctx.Locale.Tr "org.settings.update_settings"}}</button>
</div>
</form>
<div class="divider"></div>
<form class="ui form" action="{{.Link}}/avatar" method="post" enctype="multipart/form-data">
{{.CsrfTokenHtml}}
<div class="inline field">
{{template "shared/avatar_upload_crop" dict "LabelText" (ctx.Locale.Tr "settings.choose_new_avatar")}}
</div>
<div class="field">
<button class="ui primary button">{{ctx.Locale.Tr "settings.update_avatar"}}</button>
<button class="ui red button link-action" data-url="{{.Link}}/avatar/delete">{{ctx.Locale.Tr "settings.delete_current_avatar"}}</button>
</div>
</form>
</div>
</div>
{{template "org/settings/options_dangerzone" .}}
{{template "org/settings/layout_footer" .}}

View File

@@ -0,0 +1,93 @@
<h4 class="ui top attached error header">
{{ctx.Locale.Tr "repo.settings.danger_zone"}}
</h4>
<div class="ui attached error danger segment">
<div class="flex-list">
<div class="flex-item tw-items-center">
<div class="flex-item-main">
<div class="flex-item-title">{{ctx.Locale.Tr "org.settings.rename"}}</div>
<div class="flex-item-body">{{ctx.Locale.Tr "org.settings.rename_desc"}}</div>
</div>
<div class="flex-item-trailing">
<button class="ui basic red show-modal button" data-modal="#rename-org-modal">{{ctx.Locale.Tr "org.settings.rename"}}</button>
</div>
</div>
<div class="flex-item">
<div class="flex-item-main">
<div class="flex-item-title">{{ctx.Locale.Tr "org.settings.delete_account"}}</div>
<div class="flex-item-body">{{ctx.Locale.Tr "org.settings.delete_prompt"}}</div>
</div>
<div class="flex-item-trailing">
<button class="ui basic red show-modal button" data-modal="#delete-org-modal">{{ctx.Locale.Tr "org.settings.delete_account"}}</button>
</div>
</div>
</div>
</div>
<div class="ui small modal" id="rename-org-modal">
<div class="header">
{{ctx.Locale.Tr "org.settings.rename"}}
</div>
<div class="content">
<ul class="ui warning message">
<li>{{ctx.Locale.Tr "org.settings.rename_notices_1"}}</li>
<li>{{ctx.Locale.Tr "org.settings.rename_notices_2"}}</li>
</ul>
<form class="ui form form-fetch-action" action="{{.Link}}/rename" method="post">
{{.CsrfTokenHtml}}
<div class="field">
<label>
{{ctx.Locale.Tr "org.settings.name_confirm"}}
<span class="text red">{{.Org.Name}}</span>
</label>
</div>
<div class="required field">
<label for="org_name_to_rename">{{ctx.Locale.Tr "org.org_name_holder"}}</label>
<input id="org_name_to_rename" name="org_name" required>
</div>
<div class="required field">
<label>{{ctx.Locale.Tr "org.settings.rename_new_org_name"}}</label>
<input name="new_org_name" required>
</div>
<div class="actions">
<button class="ui cancel button">{{ctx.Locale.Tr "settings.cancel"}}</button>
<button class="ui red button">{{ctx.Locale.Tr "org.settings.rename"}}</button>
</div>
</form>
</div>
</div>
<div class="ui small modal" id="delete-org-modal">
<div class="header">
{{ctx.Locale.Tr "org.settings.delete_account"}}
</div>
<div class="content">
<ul class="ui warning message">
<li>{{ctx.Locale.Tr "org.settings.delete_notices_1"}}</li>
<li>{{ctx.Locale.Tr "org.settings.delete_notices_2" .Org.Name}}</li>
<li>{{ctx.Locale.Tr "org.settings.delete_notices_3" .Org.Name}}</li>
<li>{{ctx.Locale.Tr "org.settings.delete_notices_4" .Org.Name}}</li>
</ul>
<form class="ui form form-fetch-action" action="{{.Link}}/delete" method="post">
{{.CsrfTokenHtml}}
<div class="field">
<label>
{{ctx.Locale.Tr "org.settings.name_confirm"}}
<span class="text red">{{.Org.Name}}</span>
</label>
</div>
<div class="required field">
<label>{{ctx.Locale.Tr "org.org_name_holder"}}</label>
<input name="org_name" required>
</div>
<div class="actions">
<button class="ui cancel button">{{ctx.Locale.Tr "settings.cancel"}}</button>
<button class="ui red button">{{ctx.Locale.Tr "org.settings.delete_account"}}</button>
</div>
</form>
</div>
</div>