Commit 512adc21 authored by Patricio Cano's avatar Patricio Cano

Add setting that allows admins to choose which Git access protocols are enabled

parent 1141eaf5
...@@ -176,6 +176,7 @@ v 8.9.0 ...@@ -176,6 +176,7 @@ v 8.9.0
- Fix horizontal scrollbar for long commit message. - Fix horizontal scrollbar for long commit message.
- GitLab Performance Monitoring now tracks the total method execution time and call count per method - GitLab Performance Monitoring now tracks the total method execution time and call count per method
- Add Environments and Deployments - Add Environments and Deployments
- Add "Enabled Git access protocols" to Application Settings
- Redesign account and email confirmation emails - Redesign account and email confirmation emails
- Don't fail builds for projects that are deleted - Don't fail builds for projects that are deleted
- Support Docker Registry manifest v1 - Support Docker Registry manifest v1
......
...@@ -281,3 +281,10 @@ ...@@ -281,3 +281,10 @@
color: $gl-icon-color; color: $gl-icon-color;
} }
} }
.clone-dropdown-btn a {
color: #555;
&:hover {
text-decoration: none;
}
}
...@@ -110,6 +110,7 @@ class Admin::ApplicationSettingsController < Admin::ApplicationController ...@@ -110,6 +110,7 @@ class Admin::ApplicationSettingsController < Admin::ApplicationController
:send_user_confirmation_email, :send_user_confirmation_email,
:container_registry_token_expire_delay, :container_registry_token_expire_delay,
:repository_storage, :repository_storage,
:enabled_git_access_protocols,
restricted_visibility_levels: [], restricted_visibility_levels: [],
import_sources: [], import_sources: [],
disabled_oauth_sign_in_sources: [] disabled_oauth_sign_in_sources: []
......
...@@ -31,6 +31,28 @@ module ApplicationSettingsHelper ...@@ -31,6 +31,28 @@ module ApplicationSettingsHelper
current_application_settings.akismet_enabled? current_application_settings.akismet_enabled?
end end
def allowed_protocols_present?
current_application_settings.enabled_git_access_protocols.present?
end
def enabled_protocol
case current_application_settings.enabled_git_access_protocols
when 'http'
gitlab_config.protocol
when 'ssh'
'ssh'
end
end
def enabled_project_tooltip(project, protocol)
case protocol
when 'ssh'
sanitize(ssh_clone_button(project), tags: %w(a), attributes: %w(id class title data-html data-container data-placement data-title data-original-title aria-describedby))
else
sanitize(http_clone_button(project), tags: %w(a), attributes: %w(id class title data-html data-container data-placement data-title data-original-title aria-describedby))
end
end
# Return a group of checkboxes that use Bootstrap's button plugin for a # Return a group of checkboxes that use Bootstrap's button plugin for a
# toggle button effect. # toggle button effect.
def restricted_level_checkboxes(help_block_id) def restricted_level_checkboxes(help_block_id)
......
...@@ -206,10 +206,14 @@ module ProjectsHelper ...@@ -206,10 +206,14 @@ module ProjectsHelper
end end
def default_clone_protocol def default_clone_protocol
if !current_user || current_user.require_ssh_key? if allowed_protocols_present?
gitlab_config.protocol enabled_protocol
else else
"ssh" if !current_user || current_user.require_ssh_key?
gitlab_config.protocol
else
'ssh'
end
end end
end end
......
...@@ -59,6 +59,8 @@ class ApplicationSetting < ActiveRecord::Base ...@@ -59,6 +59,8 @@ class ApplicationSetting < ActiveRecord::Base
presence: true, presence: true,
inclusion: { in: ->(_object) { Gitlab.config.repositories.storages.keys } } inclusion: { in: ->(_object) { Gitlab.config.repositories.storages.keys } }
validates_inclusion_of :enabled_git_access_protocols, in: %w(ssh http), allow_blank: true, allow_nil: true
validates_each :restricted_visibility_levels do |record, attr, value| validates_each :restricted_visibility_levels do |record, attr, value|
unless value.nil? unless value.nil?
value.each do |level| value.each do |level|
......
...@@ -43,6 +43,12 @@ ...@@ -43,6 +43,12 @@
= link_to "(?)", help_page_path("integration", "bitbucket") = link_to "(?)", help_page_path("integration", "bitbucket")
and GitLab.com and GitLab.com
= link_to "(?)", help_page_path("integration", "gitlab") = link_to "(?)", help_page_path("integration", "gitlab")
.form-group
%label.control-label.col-sm-2 Enabled Git access protocols
.col-sm-10
= select(:application_setting, :enabled_git_access_protocols, [['Both SSH and HTTP', nil], ['Only SSH', 'ssh'], ['Only HTTP(S)', 'http']], {}, class: 'form-control')
%span.help-block#clone-protocol-help
Allow only the selected protocols to be used for Git access.
.form-group .form-group
.col-sm-offset-2.col-sm-10 .col-sm-offset-2.col-sm-10
.checkbox .checkbox
......
...@@ -2,15 +2,20 @@ ...@@ -2,15 +2,20 @@
.git-clone-holder.input-group .git-clone-holder.input-group
.input-group-btn .input-group-btn
%a#clone-dropdown.clone-dropdown-btn.btn{href: '#', 'data-toggle' => 'dropdown'} -if allowed_protocols_present?
%span .clone-dropdown-btn.btn
= default_clone_protocol.upcase %span
= icon('caret-down') = enabled_project_tooltip(project, enabled_protocol)
%ul.dropdown-menu.dropdown-menu-right.clone-options-dropdown - else
%li %a#clone-dropdown.clone-dropdown-btn.btn{href: '#', data: { toggle: 'dropdown' }}
= ssh_clone_button(project) %span
%li = default_clone_protocol.upcase
= http_clone_button(project) = icon('caret-down')
%ul.dropdown-menu.dropdown-menu-right.clone-options-dropdown
%li
= ssh_clone_button(project)
%li
= http_clone_button(project)
= text_field_tag :project_clone, default_url_to_repo(project), class: "js-select-on-focus form-control", readonly: true = text_field_tag :project_clone, default_url_to_repo(project), class: "js-select-on-focus form-control", readonly: true
.input-group-btn .input-group-btn
......
# See http://doc.gitlab.com/ce/development/migration_style_guide.html
# for more information on how to write migrations for GitLab.
# rubocop:disable all
class AddEnabledGitAccessProtocolsToApplicationSettings < ActiveRecord::Migration
include Gitlab::Database::MigrationHelpers
def change
add_column :application_settings, :enabled_git_access_protocols, :string
end
end
...@@ -86,6 +86,7 @@ ActiveRecord::Schema.define(version: 20160705163108) do ...@@ -86,6 +86,7 @@ ActiveRecord::Schema.define(version: 20160705163108) do
t.integer "container_registry_token_expire_delay", default: 5 t.integer "container_registry_token_expire_delay", default: 5
t.text "after_sign_up_text" t.text "after_sign_up_text"
t.string "repository_storage", default: "default" t.string "repository_storage", default: "default"
t.string "enabled_git_access_protocols"
end end
create_table "audit_events", force: :cascade do |t| create_table "audit_events", force: :cascade do |t|
......
...@@ -68,6 +68,7 @@ PUT /application/settings ...@@ -68,6 +68,7 @@ PUT /application/settings
| `after_sign_out_path` | string | no | Where to redirect users after logout | | `after_sign_out_path` | string | no | Where to redirect users after logout |
| `container_registry_token_expire_delay` | integer | no | Container Registry token duration in minutes | | `container_registry_token_expire_delay` | integer | no | Container Registry token duration in minutes |
| `repository_storage` | string | no | Storage path for new projects. The value should be the name of one of the repository storage paths defined in your gitlab.yml | | `repository_storage` | string | no | Storage path for new projects. The value should be the name of one of the repository storage paths defined in your gitlab.yml |
| `enabled_git_access_protocols` | string | no | Enabled protocols for Git access. Allowed values are: `ssh`, `http`, and `nil` to allow both protocols.
```bash ```bash
curl -X PUT -H "PRIVATE-TOKEN: 9koXpg98eAheJpvBs5tK" https://gitlab.example.com/api/v3/application/settings?signup_enabled=false&default_project_visibility=1 curl -X PUT -H "PRIVATE-TOKEN: 9koXpg98eAheJpvBs5tK" https://gitlab.example.com/api/v3/application/settings?signup_enabled=false&default_project_visibility=1
......
require 'rails_helper'
feature 'Admin disables Git access protocol', feature: true do
let(:project) { create(:empty_project, :empty_repo) }
let(:admin) { create(:admin) }
background do
login_as(admin)
end
context 'with HTTP disabled' do
background do
disable_http_protocol
end
scenario 'shows only SSH url' do
visit_project
expect(page).to have_content("git clone #{project.ssh_url_to_repo}")
expect(page).not_to have_selector('#clone-dropdown')
end
end
context 'with SSH disabled' do
background do
disable_ssh_protocol
end
scenario 'shows only HTTP url' do
visit_project
expect(page).to have_content("git clone #{project.http_url_to_repo}")
expect(page).not_to have_selector('#clone-dropdown')
end
end
context 'with nothing disabled' do
background do
create(:personal_key, user: admin)
end
scenario 'shows default SSH url and protocol selection dropdown' do
visit_project
expect(page).to have_content("git clone #{project.ssh_url_to_repo}")
expect(page).to have_selector('#clone-dropdown')
end
end
def visit_project
visit namespace_project_path(project.namespace, project)
end
def disable_http_protocol
visit admin_application_settings_path
find('#application_setting_enabled_git_access_protocols').find(:xpath, 'option[2]').select_option
click_on 'Save'
end
def disable_ssh_protocol
visit admin_application_settings_path
find('#application_setting_enabled_git_access_protocols').find(:xpath, 'option[3]').select_option
click_on 'Save'
end
end
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment