diff --git a/app/assets/javascripts/pages/groups/edit/index.js b/app/assets/javascripts/pages/groups/edit/index.js index bb91ac84ffb..8737f537296 100644 --- a/app/assets/javascripts/pages/groups/edit/index.js +++ b/app/assets/javascripts/pages/groups/edit/index.js @@ -1,9 +1,15 @@ import groupAvatar from '~/group_avatar'; import TransferDropdown from '~/groups/transfer_dropdown'; import initConfirmDangerModal from '~/confirm_danger_modal'; +import initSettingsPanels from '~/settings_panels'; document.addEventListener('DOMContentLoaded', () => { groupAvatar(); new TransferDropdown(); // eslint-disable-line no-new initConfirmDangerModal(); }); + +document.addEventListener('DOMContentLoaded', () => { + // Initialize expandable settings panels + initSettingsPanels(); +}); diff --git a/app/views/groups/edit.html.haml b/app/views/groups/edit.html.haml index 96ed63937fa..390ef3f62c7 100644 --- a/app/views/groups/edit.html.haml +++ b/app/views/groups/edit.html.haml @@ -1,78 +1,39 @@ - breadcrumb_title "General Settings" - @content_class = "limit-container-width" unless fluid_layout +- expanded = Rails.env.test? -.card.prepend-top-default - .card-header - Group settings - .card-body - = form_for @group, html: { multipart: true, class: "gl-show-field-errors" }, authenticity_token: true do |f| - = form_errors(@group) - = render 'shared/group_form', f: f - .form-group.row - .offset-sm-2.col-sm-10 - .avatar-container.s160 - = group_icon(@group, alt: '', class: 'avatar group-avatar s160') - %p.light - - if @group.avatar? - You can change the group avatar here - - else - You can upload a group avatar here - = render 'shared/choose_group_avatar_button', f: f - - if @group.avatar? - %hr - = link_to _('Remove avatar'), group_avatar_path(@group.to_param), data: { confirm: _("Avatar will be removed. Are you sure?")}, method: :delete, class: "btn btn-danger btn-inverted" +%section.settings.as-general.no-animate#js-general-settings{ class: ('expanded' if expanded) } + .settings-header + %h4 + = _('General group settings') + %button.btn.js-settings-toggle{ type: 'button' } + = expanded ? _('Collapse') : _('Expand') + %p + = _('Update your group name, description, avatar, and other general settings.') + .settings-content + = render 'groups/settings/general' - = render 'shared/visibility_level', f: f, visibility_level: @group.visibility_level, can_change_visibility_level: can_change_group_visibility_level?(@group), form_model: @group +%section.settings.as-permissions.no-animate#js-permissions-settings{ class: ('expanded' if expanded) } + .settings-header + %h4 + = _('Permissions') + %button.btn.js-settings-toggle{ type: 'button' } + = expanded ? _('Collapse') : _('Expand') + %p + = _('Enable or disable certain group features and choose access levels.') + .settings-content + = render 'groups/settings/permissions' - .form-group.row - .offset-sm-2.col-sm-10 - = render 'shared/allow_request_access', form: f - - .form-group.row - %label.col-form-label.col-sm-2 - = s_("GroupSettings|Share with group lock") - .col-sm-10 - .form-check - = f.label :share_with_group_lock do - = f.check_box :share_with_group_lock, disabled: !can_change_share_with_group_lock?(@group) - %strong - - group_link = link_to @group.name, group_path(@group) - = s_("GroupSettings|Prevent sharing a project within %{group} with other groups").html_safe % { group: group_link } - %br - %span.descr= share_with_group_lock_help_text(@group) - - = render 'group_admin_settings', f: f - - .form-actions - = f.submit 'Save group', class: "btn btn-save" - -.card.bg-danger - .card-header Remove group - .card-body - = form_tag(@group, method: :delete) do - %p - Removing group will cause all child projects and resources to be removed. - %br - %strong Removed group can not be restored! - - .form-actions - = button_to 'Remove group', '#', class: "btn btn-remove js-confirm-danger", data: { "confirm-danger-message" => remove_group_message(@group) } - -- if supports_nested_groups? - .card.bg-warning - .card-header Transfer group - .card-body - = form_for @group, url: transfer_group_path(@group), method: :put do |f| - .form-group - = dropdown_tag('Select parent group', options: { toggle_class: 'js-groups-dropdown', title: 'Parent Group', filter: true, dropdown_class: 'dropdown-open-top dropdown-group-transfer', placeholder: "Search groups", data: { data: parent_group_options(@group) } }) - = hidden_field_tag 'new_parent_group_id' - - %ul - %li Be careful. Changing a group's parent can have unintended #{link_to 'side effects', 'https://docs.gitlab.com/ce/user/project/index.html#redirects-when-changing-repository-paths', target: 'blank'}. - %li You can only transfer the group to a group you manage. - %li You will need to update your local repositories to point to the new location. - %li If the parent group's visibility is lower than the group current visibility, visibility levels for subgroups and projects will be changed to match the new parent group's visibility. - = f.submit 'Transfer group', class: "btn btn-warning" +%section.settings.as-advanced-settings.no-animate#js-advanced-settings{ class: ('expanded' if expanded) } + .settings-header + %h4 + = _('Advanced settings') + %button.btn.js-settings-toggle{ type: 'button' } + = expanded ? _('Collapse') : _('Expand') + %p + = _('Perform advanced options such as changing path, transferring, or removing the group.') + .settings-content + = render 'groups/settings/advanced' = render 'shared/confirm_modal', phrase: @group.path diff --git a/app/views/groups/settings/_advanced.html.haml b/app/views/groups/settings/_advanced.html.haml new file mode 100644 index 00000000000..ddefb98e671 --- /dev/null +++ b/app/views/groups/settings/_advanced.html.haml @@ -0,0 +1,49 @@ +.sub-section + %h4.warning-title Change group path + = form_for @group, html: { multipart: true, class: 'gl-show-field-errors' }, authenticity_token: true do |f| + = form_errors(@group) + .form-group + %p + Changing group path can have unintended side effects. + = succeed '.' do + = link_to 'Learn more', help_page_path('user/group/index', anchor: 'changing-a-groups-path'), target: '_blank' + + .input-group.gl-field-error-anchor + .group-root-path.input-group-prepend.has-tooltip{ title: group_path, :'data-placement' => 'bottom' } + .input-group-text + %span>= root_url + - if parent + %strong= parent.full_path + '/' + = f.hidden_field :parent_id + = f.text_field :path, placeholder: 'open-source', class: 'form-control', + autofocus: local_assigns[:autofocus] || false, required: true, + pattern: Gitlab::PathRegex::NAMESPACE_FORMAT_REGEX_JS, + title: 'Please choose a group path with no special characters.', + "data-bind-in" => "#{'create_chat_team' if Gitlab.config.mattermost.enabled}" + + = f.submit 'Change group path', class: 'btn btn-warning' + +.sub-section + %h4.danger-title Remove group + = form_tag(@group, method: :delete) do + %p + Removing group will cause all child projects and resources to be removed. + %br + %strong Removed group can not be restored! + + = button_to 'Remove group', '#', class: 'btn btn-remove js-confirm-danger', data: { 'confirm-danger-message' => remove_group_message(@group) } + +- if supports_nested_groups? + .sub-section + %h4.warning-title Transfer group + = form_for @group, url: transfer_group_path(@group), method: :put do |f| + .form-group + = dropdown_tag('Select parent group', options: { toggle_class: 'js-groups-dropdown', title: 'Parent Group', filter: true, dropdown_class: 'dropdown-open-top dropdown-group-transfer', placeholder: 'Search groups', data: { data: parent_group_options(@group) } }) + = hidden_field_tag 'new_parent_group_id' + + %ul + %li Be careful. Changing a group's parent can have unintended #{link_to 'side effects', 'https://docs.gitlab.com/ce/user/project/index.html#redirects-when-changing-repository-paths', target: 'blank'}. + %li You can only transfer the group to a group you manage. + %li You will need to update your local repositories to point to the new location. + %li If the parent group's visibility is lower than the group current visibility, visibility levels for subgroups and projects will be changed to match the new parent group's visibility. + = f.submit 'Transfer group', class: 'btn btn-warning' diff --git a/app/views/groups/settings/_general.html.haml b/app/views/groups/settings/_general.html.haml new file mode 100644 index 00000000000..6f0e1b8c337 --- /dev/null +++ b/app/views/groups/settings/_general.html.haml @@ -0,0 +1,36 @@ += form_for @group, html: { multipart: true, class: 'gl-show-field-errors' }, authenticity_token: true do |f| + = form_errors(@group) + + %fieldset + .row + .form-group.col-md-9 + = f.label :name, class: 'label-light' do + Group name + = f.text_field :name, class: 'form-control' + + .form-group.col-md-3 + = f.label :id, class: 'label-light' do + Group ID + = f.text_field :id, class: 'form-control', readonly: true + + .form-group + = f.label :description, class: 'label-light' do + Group description + %span.light (optional) + = f.text_area :description, class: 'form-control', rows: 3, maxlength: 250 + + .form-group.row + .col-sm-12 + .avatar-container.s160 + = group_icon(@group, alt: '', class: 'avatar group-avatar s160') + %p.light + - if @group.avatar? + You can change the group avatar here + - else + You can upload a group avatar here + = render 'shared/choose_group_avatar_button', f: f + - if @group.avatar? + %hr + = link_to _('Remove avatar'), group_avatar_path(@group.to_param), data: { confirm: _('Avatar will be removed. Are you sure?')}, method: :delete, class: 'btn btn-danger btn-inverted' + + = f.submit 'Save group', class: 'btn btn-success' diff --git a/app/views/groups/settings/_permissions.html.haml b/app/views/groups/settings/_permissions.html.haml new file mode 100644 index 00000000000..3e6979a778b --- /dev/null +++ b/app/views/groups/settings/_permissions.html.haml @@ -0,0 +1,26 @@ += form_for @group, html: { multipart: true, class: 'gl-show-field-errors' }, authenticity_token: true do |f| + = form_errors(@group) + + %fieldset + = render 'shared/visibility_level', f: f, visibility_level: @group.visibility_level, can_change_visibility_level: can_change_group_visibility_level?(@group), form_model: @group + + .form-group.row + .offset-sm-2.col-sm-10 + = render 'shared/allow_request_access', form: f + + .form-group.row + %label.col-form-label.col-sm-2 + = s_('GroupSettings|Share with group lock') + .col-sm-10 + .form-check + = f.label :share_with_group_lock do + = f.check_box :share_with_group_lock, disabled: !can_change_share_with_group_lock?(@group) + %strong + - group_link = link_to @group.name, group_path(@group) + = s_('GroupSettings|Prevent sharing a project within %{group} with other groups').html_safe % { group: group_link } + %br + %span.descr= share_with_group_lock_help_text(@group) + + = render 'group_admin_settings', f: f + + = f.submit 'Save group', class: 'btn btn-success' diff --git a/changelogs/unreleased/dz-redesign-group-settings-page.yml b/changelogs/unreleased/dz-redesign-group-settings-page.yml new file mode 100644 index 00000000000..4a8dfbb61dc --- /dev/null +++ b/changelogs/unreleased/dz-redesign-group-settings-page.yml @@ -0,0 +1,5 @@ +--- +title: Redesign group settings page into expandable sections +merge_request: 19184 +author: +type: changed diff --git a/spec/features/groups_spec.rb b/spec/features/groups_spec.rb index c1f3d94bc20..185770c312f 100644 --- a/spec/features/groups_spec.rb +++ b/spec/features/groups_spec.rb @@ -141,8 +141,10 @@ feature 'Group' do end it 'saves new settings' do - fill_in 'group_name', with: new_name - click_button 'Save group' + page.within('.as-general') do + fill_in 'group_name', with: new_name + click_button 'Save group' + end expect(page).to have_content 'successfully updated' expect(find('#group_name').value).to eq(new_name)