diff options
author | Stan Hu <stanhu@gmail.com> | 2019-05-25 22:42:42 -0700 |
---|---|---|
committer | Stan Hu <stanhu@gmail.com> | 2019-06-05 16:43:31 -0700 |
commit | f8d93b24822937d803da4c9fcc89d50c85de89c7 (patch) | |
tree | 4e26c50a4887dbe46ad0bf7df46c3bc09d48d001 | |
parent | e6a88b024fa7f8e1ec5b712744d0e0d118b026e6 (diff) | |
download | gitlab-ce-f8d93b24822937d803da4c9fcc89d50c85de89c7.tar.gz |
Set project default visibility to max allowed
If the default, instance-wide visibility were set to internal but a
group were private, the radio button would be set on internal even
though that setting were not allowed. We now consider the allowed
visibility setting for the group in determining what the default should
be.
Closes https://gitlab.com/gitlab-org/gitlab-ce/issues/62298
-rw-r--r-- | app/helpers/visibility_level_helper.rb | 38 | ||||
-rw-r--r-- | app/views/projects/_new_project_fields.html.haml | 2 | ||||
-rw-r--r-- | changelogs/unreleased/sh-default-visibility-fix.yml | 5 | ||||
-rw-r--r-- | spec/features/projects/new_project_spec.rb | 30 | ||||
-rw-r--r-- | spec/helpers/visibility_level_helper_spec.rb | 45 |
5 files changed, 119 insertions, 1 deletions
diff --git a/app/helpers/visibility_level_helper.rb b/app/helpers/visibility_level_helper.rb index 9deb783d289..70e60bfba8d 100644 --- a/app/helpers/visibility_level_helper.rb +++ b/app/helpers/visibility_level_helper.rb @@ -165,8 +165,46 @@ module VisibilityLevelHelper !form_model.visibility_level_allowed?(level) end + # Visibility level can be restricted in two ways: + # + # 1. The group permissions (e.g. a subgroup is private, which requires + # all projects to be private) + # 2. The global allowed visibility settinngs, set by the admin + def selected_visibility_level(form_model, requested_level) + requested_level = + if requested_level.present? + requested_level.to_i + else + default_project_visibility + end + + [requested_level, max_allowed_visibility_level(form_model)].min + end + private + def max_allowed_visibility_level(form_model) + # First obtain the maximum visibility for the project or group + current_level = max_allowed_visibility_level_by_model(form_model) + + # Now limit this by the global setting + Gitlab::VisibilityLevel.closest_allowed_level(current_level) + end + + def max_allowed_visibility_level_by_model(form_model) + current_level = Gitlab::VisibilityLevel::PRIVATE + + Gitlab::VisibilityLevel.values.sort.each do |value| + if disallowed_visibility_level?(form_model, value) + break + else + current_level = value + end + end + + current_level + end + def visibility_level_errors_for_group(group, level_name) group_name = link_to group.name, group_path(group) change_visiblity = link_to 'change the visibility', edit_group_path(group) diff --git a/app/views/projects/_new_project_fields.html.haml b/app/views/projects/_new_project_fields.html.haml index 9ae84a909a5..e423631ec99 100644 --- a/app/views/projects/_new_project_fields.html.haml +++ b/app/views/projects/_new_project_fields.html.haml @@ -1,4 +1,4 @@ -- visibility_level = params.dig(:project, :visibility_level) || default_project_visibility +- visibility_level = selected_visibility_level(@project, params.dig(:project, :visibility_level)) - ci_cd_only = local_assigns.fetch(:ci_cd_only, false) - hide_init_with_readme = local_assigns.fetch(:hide_init_with_readme, false) - track_label = local_assigns.fetch(:track_label, 'blank_project') diff --git a/changelogs/unreleased/sh-default-visibility-fix.yml b/changelogs/unreleased/sh-default-visibility-fix.yml new file mode 100644 index 00000000000..8308f310150 --- /dev/null +++ b/changelogs/unreleased/sh-default-visibility-fix.yml @@ -0,0 +1,5 @@ +--- +title: Set project default visibility to max allowed +merge_request: 28754 +author: +type: fixed diff --git a/spec/features/projects/new_project_spec.rb b/spec/features/projects/new_project_spec.rb index b54ea929978..033e1afe866 100644 --- a/spec/features/projects/new_project_spec.rb +++ b/spec/features/projects/new_project_spec.rb @@ -63,6 +63,36 @@ describe 'New project' do end end end + + context 'when group visibility is private but default is internal' do + before do + stub_application_setting(default_project_visibility: Gitlab::VisibilityLevel::INTERNAL) + end + + it 'has private selected' do + group = create(:group, visibility_level: Gitlab::VisibilityLevel::PRIVATE) + visit new_project_path(namespace_id: group.id) + + page.within('#blank-project-pane') do + expect(find_field("project_visibility_level_#{Gitlab::VisibilityLevel::PRIVATE}")).to be_checked + end + end + end + + context 'when group visibility is public but user requests private' do + before do + stub_application_setting(default_project_visibility: Gitlab::VisibilityLevel::INTERNAL) + end + + it 'has private selected' do + group = create(:group, visibility_level: Gitlab::VisibilityLevel::PUBLIC) + visit new_project_path(namespace_id: group.id, project: { visibility_level: Gitlab::VisibilityLevel::PRIVATE }) + + page.within('#blank-project-pane') do + expect(find_field("project_visibility_level_#{Gitlab::VisibilityLevel::PRIVATE}")).to be_checked + end + end + end end context 'Readme selector' do diff --git a/spec/helpers/visibility_level_helper_spec.rb b/spec/helpers/visibility_level_helper_spec.rb index e565ac8c530..25a2fcf5a81 100644 --- a/spec/helpers/visibility_level_helper_spec.rb +++ b/spec/helpers/visibility_level_helper_spec.rb @@ -162,4 +162,49 @@ describe VisibilityLevelHelper do end end end + + describe "selected_visibility_level" do + let(:group) { create(:group, :public) } + let!(:project) { create(:project, :internal, group: group) } + let!(:forked_project) { fork_project(project) } + + using RSpec::Parameterized::TableSyntax + + PUBLIC = Gitlab::VisibilityLevel::PUBLIC + INTERNAL = Gitlab::VisibilityLevel::INTERNAL + PRIVATE = Gitlab::VisibilityLevel::PRIVATE + + # This is a subset of all the permutations + where(:requested_level, :max_allowed, :global_default_level, :restricted_levels, :expected) do + PUBLIC | PUBLIC | PUBLIC | [] | PUBLIC + PUBLIC | PUBLIC | PUBLIC | [PUBLIC] | INTERNAL + INTERNAL | PUBLIC | PUBLIC | [] | INTERNAL + INTERNAL | PRIVATE | PRIVATE | [] | PRIVATE + PRIVATE | PUBLIC | PUBLIC | [] | PRIVATE + PUBLIC | PRIVATE | INTERNAL | [] | PRIVATE + PUBLIC | INTERNAL | PUBLIC | [] | INTERNAL + PUBLIC | PRIVATE | PUBLIC | [] | PRIVATE + PUBLIC | INTERNAL | INTERNAL | [] | INTERNAL + PUBLIC | PUBLIC | INTERNAL | [] | PUBLIC + end + + before do + stub_application_setting(restricted_visibility_levels: restricted_levels, + default_project_visibility: global_default_level) + end + + with_them do + it "provides correct visibility level for forked project" do + project.update(visibility_level: max_allowed) + + expect(selected_visibility_level(forked_project, requested_level)).to eq(expected) + end + + it "provides correct visibiility level for project in group" do + project.group.update(visibility_level: max_allowed) + + expect(selected_visibility_level(project, requested_level)).to eq(expected) + end + end + end end |