Feature: Deploy keys between projects
This commit is contained in:
parent
8e4625af61
commit
1882baa1aa
13 changed files with 86 additions and 105 deletions
|
@ -5,7 +5,8 @@ class DeployKeysController < ProjectResourceController
|
|||
before_filter :authorize_admin_project!
|
||||
|
||||
def index
|
||||
@keys = @project.deploy_keys.all
|
||||
@enabled_keys = @project.deploy_keys.all
|
||||
@available_keys = available_keys - @enabled_keys
|
||||
end
|
||||
|
||||
def show
|
||||
|
@ -19,8 +20,9 @@ class DeployKeysController < ProjectResourceController
|
|||
end
|
||||
|
||||
def create
|
||||
@key = @project.deploy_keys.new(params[:key])
|
||||
if @key.save
|
||||
@key = DeployKey.new(params[:deploy_key])
|
||||
|
||||
if @key.valid? && @project.deploy_keys << @key
|
||||
redirect_to project_deploy_keys_path(@project)
|
||||
else
|
||||
render "new"
|
||||
|
@ -36,4 +38,22 @@ class DeployKeysController < ProjectResourceController
|
|||
format.js { render nothing: true }
|
||||
end
|
||||
end
|
||||
|
||||
def enable
|
||||
project.deploy_keys << available_keys.find(params[:id])
|
||||
|
||||
redirect_to project_deploy_keys_path(@project)
|
||||
end
|
||||
|
||||
def disable
|
||||
@project.deploy_keys_projects.where(deploy_key_id: params[:id]).last.destroy
|
||||
|
||||
redirect_to project_deploy_keys_path(@project)
|
||||
end
|
||||
|
||||
protected
|
||||
|
||||
def available_keys
|
||||
@available_keys ||= DeployKey.in_projects(current_user.owned_projects)
|
||||
end
|
||||
end
|
||||
|
|
|
@ -1,4 +1,6 @@
|
|||
class DeployKey < Key
|
||||
has_many :deploy_keys_projects, dependent: :destroy
|
||||
has_many :projects, through: :deploy_keys_projects
|
||||
|
||||
scope :in_projects, ->(projects) { joins(:deploy_keys_projects).where('deploy_keys_projects.project_id in (?)', projects) }
|
||||
end
|
||||
|
|
|
@ -46,10 +46,6 @@ class Key < ActiveRecord::Base
|
|||
errors.add(:key, "can't be fingerprinted") if $?.exitstatus != 0
|
||||
end
|
||||
|
||||
def is_deploy_key
|
||||
project.present?
|
||||
end
|
||||
|
||||
# projects that has this key
|
||||
def projects
|
||||
user.authorized_projects
|
||||
|
|
|
@ -55,7 +55,6 @@ class Project < ActiveRecord::Base
|
|||
has_many :users_projects, dependent: :destroy
|
||||
has_many :notes, dependent: :destroy
|
||||
has_many :snippets, dependent: :destroy
|
||||
has_many :deploy_keys, dependent: :destroy, class_name: "Key", foreign_key: "project_id"
|
||||
has_many :hooks, dependent: :destroy, class_name: "ProjectHook"
|
||||
has_many :protected_branches, dependent: :destroy
|
||||
has_many :user_team_project_relationships, dependent: :destroy
|
||||
|
@ -65,6 +64,9 @@ class Project < ActiveRecord::Base
|
|||
has_many :user_team_user_relationships, through: :user_teams
|
||||
has_many :user_teams_members, through: :user_team_user_relationships
|
||||
|
||||
has_many :deploy_keys_projects, dependent: :destroy
|
||||
has_many :deploy_keys, through: :deploy_keys_projects
|
||||
|
||||
delegate :name, to: :owner, allow_nil: true, prefix: true
|
||||
|
||||
# Validations
|
||||
|
|
|
@ -89,7 +89,7 @@ class User < ActiveRecord::Base
|
|||
|
||||
has_many :personal_projects, through: :namespace, source: :projects
|
||||
has_many :projects, through: :users_projects
|
||||
has_many :own_projects, foreign_key: :creator_id
|
||||
has_many :own_projects, foreign_key: :creator_id, class_name: 'Project'
|
||||
has_many :owned_projects, through: :namespaces, source: :projects
|
||||
|
||||
#
|
||||
|
|
25
app/views/deploy_keys/_deploy_key.html.haml
Normal file
25
app/views/deploy_keys/_deploy_key.html.haml
Normal file
|
@ -0,0 +1,25 @@
|
|||
%li
|
||||
.pull-right
|
||||
- if @available_keys.include?(deploy_key)
|
||||
= link_to enable_project_deploy_key_path(@project, deploy_key), class: 'btn btn-small', method: :put do
|
||||
%i.icon-plus
|
||||
Enable
|
||||
- else
|
||||
- if deploy_key.projects.count > 1
|
||||
= link_to disable_project_deploy_key_path(@project, deploy_key), class: 'btn btn-small', method: :put do
|
||||
%i.icon-off
|
||||
Disable
|
||||
- else
|
||||
= link_to 'Remove', project_deploy_key_path(@project, deploy_key), confirm: 'Are you sure?', method: :delete, class: "btn btn-remove delete-key btn-small pull-right"
|
||||
|
||||
|
||||
= link_to project_deploy_key_path(@project, deploy_key) do
|
||||
%i.icon-key
|
||||
%strong= deploy_key.title
|
||||
|
||||
%p.light.prepend-top-10
|
||||
- deploy_key.projects.map(&:name_with_namespace).each do |project_name|
|
||||
%span.label= project_name
|
||||
%small.pull-right
|
||||
Created #{time_ago_in_words(deploy_key.created_at)} ago
|
||||
|
|
@ -18,6 +18,6 @@
|
|||
= link_to "here", help_ssh_path
|
||||
|
||||
.actions
|
||||
= f.submit 'Save', class: "btn-save btn"
|
||||
= f.submit 'Create', class: "btn-create btn"
|
||||
= link_to "Cancel", project_deploy_keys_path(@project), class: "btn btn-cancel"
|
||||
|
||||
|
|
|
@ -1,12 +0,0 @@
|
|||
%tr
|
||||
%td
|
||||
%a{href: project_deploy_key_path(key.project, key)}
|
||||
%strong= key.title
|
||||
%td
|
||||
%span.update-author
|
||||
Added
|
||||
= time_ago_in_words(key.created_at)
|
||||
ago
|
||||
%td
|
||||
= link_to 'Remove', project_deploy_key_path(key.project, key), confirm: 'Are you sure?', method: :delete, class: "btn btn-remove delete-key btn-small pull-right"
|
||||
|
|
@ -1,17 +1,26 @@
|
|||
= render "projects/settings_nav"
|
||||
|
||||
%p.slead
|
||||
Deploy keys allow read-only access to repository. They can be used for CI, staging or production servers. A deploy key can be added to only one project. If you need to add the same key to multiple projects you can create a deploy user and add that user to multiple projects.
|
||||
Deploy keys allow read-only access to repository. They can be used for CI, staging or production servers
|
||||
|
||||
- if can? current_user, :admin_project, @project
|
||||
= link_to new_project_deploy_key_path(@project), class: "btn btn-small", title: "New Deploy Key" do
|
||||
Add Deploy Key
|
||||
- if @keys.any?
|
||||
%table
|
||||
%thead
|
||||
%tr
|
||||
%th Keys
|
||||
%th
|
||||
%th
|
||||
- @keys.each do |key|
|
||||
= render(partial: 'show', locals: {key: key})
|
||||
%p
|
||||
You can create a deploy key or add existing one
|
||||
= link_to new_project_deploy_key_path(@project), class: "btn btn-primary pull-right", title: "New Deploy Key" do
|
||||
%i.icon-plus
|
||||
New Deploy Key
|
||||
|
||||
%hr.clearfix
|
||||
|
||||
.row
|
||||
.span6.enabled-keys
|
||||
%h5.cgreen
|
||||
Enabled deploy keys
|
||||
%small for this project
|
||||
%ul.bordered-list
|
||||
= render @enabled_keys
|
||||
.span6.available-keys
|
||||
%h5
|
||||
Available deploy keys
|
||||
%small from projects you are able to manage
|
||||
%ul.bordered-list
|
||||
= render @available_keys
|
||||
|
|
|
@ -12,4 +12,4 @@
|
|||
%hr
|
||||
%pre= @key.key
|
||||
.pull-right
|
||||
= link_to 'Remove', project_deploy_key_path(@key.project, @key), confirm: 'Are you sure?', method: :delete, class: "btn-remove btn delete-key"
|
||||
= link_to 'Remove', project_deploy_key_path(@project, @key), confirm: 'Are you sure?', method: :delete, class: "btn-remove btn delete-key"
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
- @logs.each do |content_data|
|
||||
- @logs.each do |content_data|
|
||||
- file_name = content_data[:file_name]
|
||||
- commit = content_data[:commit]
|
||||
|
||||
|
|
|
@ -215,7 +215,13 @@ Gitlab::Application.routes.draw do
|
|||
end
|
||||
end
|
||||
|
||||
resources :deploy_keys
|
||||
resources :deploy_keys do
|
||||
member do
|
||||
put :enable
|
||||
put :disable
|
||||
end
|
||||
end
|
||||
|
||||
resources :protected_branches, only: [:index, :create, :destroy]
|
||||
|
||||
resources :refs, only: [] do
|
||||
|
|
|
@ -1,67 +0,0 @@
|
|||
require 'spec_helper'
|
||||
|
||||
describe "Projects", "DeployKeys" do
|
||||
let(:project) { create(:project) }
|
||||
|
||||
before do
|
||||
login_as :user
|
||||
project.team << [@user, :master]
|
||||
end
|
||||
|
||||
describe "GET /keys" do
|
||||
before do
|
||||
@key = create(:key, project: project)
|
||||
visit project_deploy_keys_path(project)
|
||||
end
|
||||
|
||||
subject { page }
|
||||
|
||||
it { should have_content(@key.title) }
|
||||
|
||||
describe "Destroy" do
|
||||
before { visit project_deploy_key_path(project, @key) }
|
||||
|
||||
it "should remove entry" do
|
||||
expect {
|
||||
click_link "Remove"
|
||||
}.to change { project.deploy_keys.count }.by(-1)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
describe "New key" do
|
||||
before do
|
||||
visit project_deploy_keys_path(project)
|
||||
click_link "New Deploy Key"
|
||||
end
|
||||
|
||||
it "should open new key popup" do
|
||||
page.should have_content("New Deploy key")
|
||||
end
|
||||
|
||||
describe "fill in" do
|
||||
before do
|
||||
fill_in "key_title", with: "laptop"
|
||||
fill_in "key_key", with: "ssh-rsa AAAAB3NzaC1yc2EAAAABIwAAAQEAzrEJUIR6Y03TCE9rIJ+GqTBvgb8t1jI9h5UBzCLuK4VawOmkLornPqLDrGbm6tcwM/wBrrLvVOqi2HwmkKEIecVO0a64A4rIYScVsXIniHRS6w5twyn1MD3sIbN+socBDcaldECQa2u1dI3tnNVcs8wi77fiRe7RSxePsJceGoheRQgC8AZ510UdIlO+9rjIHUdVN7LLyz512auAfYsgx1OfablkQ/XJcdEwDNgi9imI6nAXhmoKUm1IPLT2yKajTIC64AjLOnE0YyCh6+7RFMpiMyu1qiOCpdjYwTgBRiciNRZCH8xIedyCoAmiUgkUT40XYHwLuwiPJICpkAzp7Q== user@laptop"
|
||||
end
|
||||
|
||||
it { expect { click_button "Save" }.to change {Key.count}.by(1) }
|
||||
|
||||
it "should add new key to table" do
|
||||
click_button "Save"
|
||||
|
||||
page.should have_content "laptop"
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
describe "Show page" do
|
||||
before do
|
||||
@key = create(:key, project: project)
|
||||
visit project_deploy_key_path(project, @key)
|
||||
end
|
||||
|
||||
it { page.should have_content @key.title }
|
||||
it { page.should have_content @key.key[0..10] }
|
||||
end
|
||||
end
|
Loading…
Reference in a new issue