Merge branch 'git_hook_messages_ce' of dev.gitlab.org:gitlab/gitlabhq
Conflicts: GITLAB_SHELL_VERSION
This commit is contained in:
commit
b70cee9c2f
9 changed files with 76 additions and 48 deletions
|
@ -1 +1 @@
|
||||||
2.3.1
|
2.4.0
|
||||||
|
|
|
@ -43,7 +43,7 @@ module API
|
||||||
|
|
||||||
return false unless actor
|
return false unless actor
|
||||||
|
|
||||||
access.allowed?(
|
access.check(
|
||||||
actor,
|
actor,
|
||||||
params[:action],
|
params[:action],
|
||||||
project,
|
project,
|
||||||
|
|
|
@ -80,7 +80,7 @@ module Grack
|
||||||
case git_cmd
|
case git_cmd
|
||||||
when *Gitlab::GitAccess::DOWNLOAD_COMMANDS
|
when *Gitlab::GitAccess::DOWNLOAD_COMMANDS
|
||||||
if user
|
if user
|
||||||
Gitlab::GitAccess.new.download_allowed?(user, project)
|
Gitlab::GitAccess.new.download_access_check(user, project).allowed?
|
||||||
elsif project.public?
|
elsif project.public?
|
||||||
# Allow clone/fetch for public projects
|
# Allow clone/fetch for public projects
|
||||||
true
|
true
|
||||||
|
|
|
@ -5,61 +5,60 @@ module Gitlab
|
||||||
|
|
||||||
attr_reader :params, :project, :git_cmd, :user
|
attr_reader :params, :project, :git_cmd, :user
|
||||||
|
|
||||||
def allowed?(actor, cmd, project, changes = nil)
|
def check(actor, cmd, project, changes = nil)
|
||||||
case cmd
|
case cmd
|
||||||
when *DOWNLOAD_COMMANDS
|
when *DOWNLOAD_COMMANDS
|
||||||
if actor.is_a? User
|
if actor.is_a? User
|
||||||
download_allowed?(actor, project)
|
download_access_check(actor, project)
|
||||||
elsif actor.is_a? DeployKey
|
elsif actor.is_a? DeployKey
|
||||||
actor.projects.include?(project)
|
actor.projects.include?(project)
|
||||||
elsif actor.is_a? Key
|
elsif actor.is_a? Key
|
||||||
download_allowed?(actor.user, project)
|
download_access_check(actor.user, project)
|
||||||
else
|
else
|
||||||
raise 'Wrong actor'
|
raise 'Wrong actor'
|
||||||
end
|
end
|
||||||
when *PUSH_COMMANDS
|
when *PUSH_COMMANDS
|
||||||
if actor.is_a? User
|
if actor.is_a? User
|
||||||
push_allowed?(actor, project, changes)
|
push_access_check(actor, project, changes)
|
||||||
elsif actor.is_a? DeployKey
|
elsif actor.is_a? DeployKey
|
||||||
# Deploy key not allowed to push
|
return build_status_object(false, "Deploy key not allowed to push")
|
||||||
return false
|
|
||||||
elsif actor.is_a? Key
|
elsif actor.is_a? Key
|
||||||
push_allowed?(actor.user, project, changes)
|
push_access_check(actor.user, project, changes)
|
||||||
else
|
else
|
||||||
raise 'Wrong actor'
|
raise 'Wrong actor'
|
||||||
end
|
end
|
||||||
else
|
else
|
||||||
false
|
return build_status_object(false, "Wrong command")
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def download_allowed?(user, project)
|
def download_access_check(user, project)
|
||||||
if user && user_allowed?(user)
|
if user && user_allowed?(user) && user.can?(:download_code, project)
|
||||||
user.can?(:download_code, project)
|
build_status_object(true)
|
||||||
else
|
else
|
||||||
false
|
build_status_object(false, "You don't have access")
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def push_allowed?(user, project, changes)
|
def push_access_check(user, project, changes)
|
||||||
return false unless user && user_allowed?(user)
|
return build_status_object(false, "You don't have access") unless user && user_allowed?(user)
|
||||||
return true if changes.blank?
|
return build_status_object(true) if changes.blank?
|
||||||
|
|
||||||
changes = changes.lines if changes.kind_of?(String)
|
changes = changes.lines if changes.kind_of?(String)
|
||||||
|
|
||||||
# Iterate over all changes to find if user allowed all of them to be applied
|
# Iterate over all changes to find if user allowed all of them to be applied
|
||||||
changes.each do |change|
|
changes.each do |change|
|
||||||
unless change_allowed?(user, project, change)
|
status = change_access_check(user, project, change)
|
||||||
|
unless status.allowed?
|
||||||
# If user does not have access to make at least one change - cancel all push
|
# If user does not have access to make at least one change - cancel all push
|
||||||
return false
|
return status
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
# If user has access to make all changes
|
return build_status_object(true)
|
||||||
true
|
|
||||||
end
|
end
|
||||||
|
|
||||||
def change_allowed?(user, project, change)
|
def change_access_check(user, project, change)
|
||||||
oldrev, newrev, ref = change.split(' ')
|
oldrev, newrev, ref = change.split(' ')
|
||||||
|
|
||||||
action = if project.protected_branch?(branch_name(ref))
|
action = if project.protected_branch?(branch_name(ref))
|
||||||
|
@ -79,7 +78,11 @@ module Gitlab
|
||||||
:push_code
|
:push_code
|
||||||
end
|
end
|
||||||
|
|
||||||
user.can?(action, project)
|
if user.can?(action, project)
|
||||||
|
build_status_object(true)
|
||||||
|
else
|
||||||
|
build_status_object(false, "You don't have permission")
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def forced_push?(project, oldrev, newrev)
|
def forced_push?(project, oldrev, newrev)
|
||||||
|
@ -116,5 +119,11 @@ module Gitlab
|
||||||
nil
|
nil
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
protected
|
||||||
|
|
||||||
|
def build_status_object(status, message = '')
|
||||||
|
GitAccessStatus.new(status, message)
|
||||||
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
15
lib/gitlab/git_access_status.rb
Normal file
15
lib/gitlab/git_access_status.rb
Normal file
|
@ -0,0 +1,15 @@
|
||||||
|
module Gitlab
|
||||||
|
class GitAccessStatus
|
||||||
|
attr_accessor :status, :message
|
||||||
|
alias_method :allowed?, :status
|
||||||
|
|
||||||
|
def initialize(status, message = '')
|
||||||
|
@status = status
|
||||||
|
@message = message
|
||||||
|
end
|
||||||
|
|
||||||
|
def to_json
|
||||||
|
{status: @status, message: @message}.to_json
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
|
@ -1,7 +1,11 @@
|
||||||
module Gitlab
|
module Gitlab
|
||||||
class GitAccessWiki < GitAccess
|
class GitAccessWiki < GitAccess
|
||||||
def change_allowed?(user, project, change)
|
def change_access_check(user, project, change)
|
||||||
user.can?(:write_wiki, project)
|
if user.can?(:write_wiki, project)
|
||||||
|
build_status_object(true)
|
||||||
|
else
|
||||||
|
build_status_object(false, "You don't have access")
|
||||||
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -5,14 +5,14 @@ describe Gitlab::GitAccess do
|
||||||
let(:project) { create(:project) }
|
let(:project) { create(:project) }
|
||||||
let(:user) { create(:user) }
|
let(:user) { create(:user) }
|
||||||
|
|
||||||
describe 'download_allowed?' do
|
describe 'download_access_check' do
|
||||||
describe 'master permissions' do
|
describe 'master permissions' do
|
||||||
before { project.team << [user, :master] }
|
before { project.team << [user, :master] }
|
||||||
|
|
||||||
context 'pull code' do
|
context 'pull code' do
|
||||||
subject { access.download_allowed?(user, project) }
|
subject { access.download_access_check(user, project) }
|
||||||
|
|
||||||
it { should be_true }
|
it { subject.allowed?.should be_true }
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -20,9 +20,9 @@ describe Gitlab::GitAccess do
|
||||||
before { project.team << [user, :guest] }
|
before { project.team << [user, :guest] }
|
||||||
|
|
||||||
context 'pull code' do
|
context 'pull code' do
|
||||||
subject { access.download_allowed?(user, project) }
|
subject { access.download_access_check(user, project) }
|
||||||
|
|
||||||
it { should be_false }
|
it { subject.allowed?.should be_false }
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -33,22 +33,22 @@ describe Gitlab::GitAccess do
|
||||||
end
|
end
|
||||||
|
|
||||||
context 'pull code' do
|
context 'pull code' do
|
||||||
subject { access.download_allowed?(user, project) }
|
subject { access.download_access_check(user, project) }
|
||||||
|
|
||||||
it { should be_false }
|
it { subject.allowed?.should be_false }
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
describe 'without acccess to project' do
|
describe 'without acccess to project' do
|
||||||
context 'pull code' do
|
context 'pull code' do
|
||||||
subject { access.download_allowed?(user, project) }
|
subject { access.download_access_check(user, project) }
|
||||||
|
|
||||||
it { should be_false }
|
it { subject.allowed?.should be_false }
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
describe 'push_allowed?' do
|
describe 'push_access_check' do
|
||||||
def protect_feature_branch
|
def protect_feature_branch
|
||||||
create(:protected_branch, name: 'feature', project: project)
|
create(:protected_branch, name: 'feature', project: project)
|
||||||
end
|
end
|
||||||
|
@ -117,9 +117,9 @@ describe Gitlab::GitAccess do
|
||||||
|
|
||||||
permissions_matrix[role].each do |action, allowed|
|
permissions_matrix[role].each do |action, allowed|
|
||||||
context action do
|
context action do
|
||||||
subject { access.push_allowed?(user, project, changes[action]) }
|
subject { access.push_access_check(user, project, changes[action]) }
|
||||||
|
|
||||||
it { should allowed ? be_true : be_false }
|
it { subject.allowed?.should allowed ? be_true : be_false }
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -11,9 +11,9 @@ describe Gitlab::GitAccessWiki do
|
||||||
project.team << [user, :developer]
|
project.team << [user, :developer]
|
||||||
end
|
end
|
||||||
|
|
||||||
subject { access.push_allowed?(user, project, changes) }
|
subject { access.push_access_check(user, project, changes) }
|
||||||
|
|
||||||
it { should be_true }
|
it { subject.allowed?.should be_true }
|
||||||
end
|
end
|
||||||
|
|
||||||
def changes
|
def changes
|
||||||
|
|
|
@ -37,7 +37,7 @@ describe API::API, api: true do
|
||||||
pull(key, project)
|
pull(key, project)
|
||||||
|
|
||||||
response.status.should == 200
|
response.status.should == 200
|
||||||
response.body.should == 'true'
|
JSON.parse(response.body)["status"].should be_true
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -46,7 +46,7 @@ describe API::API, api: true do
|
||||||
push(key, project)
|
push(key, project)
|
||||||
|
|
||||||
response.status.should == 200
|
response.status.should == 200
|
||||||
response.body.should == 'true'
|
JSON.parse(response.body)["status"].should be_true
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
@ -61,7 +61,7 @@ describe API::API, api: true do
|
||||||
pull(key, project)
|
pull(key, project)
|
||||||
|
|
||||||
response.status.should == 200
|
response.status.should == 200
|
||||||
response.body.should == 'false'
|
JSON.parse(response.body)["status"].should be_false
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -70,7 +70,7 @@ describe API::API, api: true do
|
||||||
push(key, project)
|
push(key, project)
|
||||||
|
|
||||||
response.status.should == 200
|
response.status.should == 200
|
||||||
response.body.should == 'false'
|
JSON.parse(response.body)["status"].should be_false
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
@ -87,7 +87,7 @@ describe API::API, api: true do
|
||||||
pull(key, personal_project)
|
pull(key, personal_project)
|
||||||
|
|
||||||
response.status.should == 200
|
response.status.should == 200
|
||||||
response.body.should == 'false'
|
JSON.parse(response.body)["status"].should be_false
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -96,7 +96,7 @@ describe API::API, api: true do
|
||||||
push(key, personal_project)
|
push(key, personal_project)
|
||||||
|
|
||||||
response.status.should == 200
|
response.status.should == 200
|
||||||
response.body.should == 'false'
|
JSON.parse(response.body)["status"].should be_false
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
@ -114,7 +114,7 @@ describe API::API, api: true do
|
||||||
pull(key, project)
|
pull(key, project)
|
||||||
|
|
||||||
response.status.should == 200
|
response.status.should == 200
|
||||||
response.body.should == 'true'
|
JSON.parse(response.body)["status"].should be_true
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -123,7 +123,7 @@ describe API::API, api: true do
|
||||||
push(key, project)
|
push(key, project)
|
||||||
|
|
||||||
response.status.should == 200
|
response.status.should == 200
|
||||||
response.body.should == 'false'
|
JSON.parse(response.body)["status"].should be_false
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
Loading…
Reference in a new issue