Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
李少辉-开发者
gitlab-foss
提交
c982edfa
G
gitlab-foss
项目概览
李少辉-开发者
/
gitlab-foss
通知
15
Star
0
Fork
0
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
0
列表
看板
标记
里程碑
合并请求
0
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
G
gitlab-foss
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
0
Issue
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
Pages
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
提交
Issue看板
前往新版Gitcode,体验更适合开发者的 AI 搜索 >>
提交
c982edfa
编写于
2月 05, 2019
作者:
B
Bob Van Landuyt
浏览文件
操作
浏览文件
下载
电子邮件补丁
差异文件
Avoid race conditions when creating GpgSignature
This avoids race conditions when creating GpgSignature.
上级
02cc32c6
变更
6
隐藏空白更改
内联
并排
Showing
6 changed file
with
70 addition
and
5 deletion
+70
-5
app/models/application_record.rb
app/models/application_record.rb
+6
-0
app/models/gpg_signature.rb
app/models/gpg_signature.rb
+6
-1
changelogs/unreleased/bvl-fix-race-condition-creating-signature.yml
.../unreleased/bvl-fix-race-condition-creating-signature.yml
+5
-0
lib/gitlab/gpg/commit.rb
lib/gitlab/gpg/commit.rb
+4
-3
spec/models/application_record_spec.rb
spec/models/application_record_spec.rb
+14
-1
spec/models/gpg_signature_spec.rb
spec/models/gpg_signature_spec.rb
+35
-0
未找到文件。
app/models/application_record.rb
浏览文件 @
c982edfa
...
@@ -7,6 +7,12 @@ class ApplicationRecord < ActiveRecord::Base
...
@@ -7,6 +7,12 @@ class ApplicationRecord < ActiveRecord::Base
where
(
id:
ids
)
where
(
id:
ids
)
end
end
def
self
.
safe_find_or_create_by!
(
*
args
)
safe_find_or_create_by
(
*
args
).
tap
do
|
record
|
record
.
validate!
unless
record
.
persisted?
end
end
def
self
.
safe_find_or_create_by
(
*
args
)
def
self
.
safe_find_or_create_by
(
*
args
)
transaction
(
requires_new:
true
)
do
transaction
(
requires_new:
true
)
do
find_or_create_by
(
*
args
)
find_or_create_by
(
*
args
)
...
...
app/models/gpg_signature.rb
浏览文件 @
c982edfa
# frozen_string_literal: true
# frozen_string_literal: true
class
GpgSignature
<
A
ctiveRecord
::
Base
class
GpgSignature
<
A
pplicationRecord
include
ShaAttribute
include
ShaAttribute
sha_attribute
:commit_sha
sha_attribute
:commit_sha
...
@@ -33,6 +33,11 @@ class GpgSignature < ActiveRecord::Base
...
@@ -33,6 +33,11 @@ class GpgSignature < ActiveRecord::Base
)
)
end
end
def
self
.
safe_create!
(
attributes
)
create_with
(
attributes
)
.
safe_find_or_create_by!
(
commit_sha:
attributes
[
:commit_sha
])
end
def
gpg_key
=
(
model
)
def
gpg_key
=
(
model
)
case
model
case
model
when
GpgKey
when
GpgKey
...
...
changelogs/unreleased/bvl-fix-race-condition-creating-signature.yml
0 → 100644
浏览文件 @
c982edfa
---
title
:
Avoid race conditions when creating GpgSignature
merge_request
:
24939
author
:
type
:
fixed
lib/gitlab/gpg/commit.rb
浏览文件 @
c982edfa
...
@@ -88,9 +88,10 @@ module Gitlab
...
@@ -88,9 +88,10 @@ module Gitlab
def
create_cached_signature!
def
create_cached_signature!
using_keychain
do
|
gpg_key
|
using_keychain
do
|
gpg_key
|
signature
=
GpgSignature
.
new
(
attributes
(
gpg_key
))
attributes
=
attributes
(
gpg_key
)
signature
.
save!
unless
Gitlab
::
Database
.
read_only?
break
GpgSignature
.
new
(
attributes
)
if
Gitlab
::
Database
.
read_only?
signature
GpgSignature
.
safe_create!
(
attributes
)
end
end
end
end
...
...
spec/models/application_record_spec.rb
浏览文件 @
c982edfa
...
@@ -11,7 +11,7 @@ describe ApplicationRecord do
...
@@ -11,7 +11,7 @@ describe ApplicationRecord do
end
end
end
end
describe
'
#
safe_find_or_create_by'
do
describe
'
.
safe_find_or_create_by'
do
it
'creates the user avoiding race conditions'
do
it
'creates the user avoiding race conditions'
do
expect
(
Suggestion
).
to
receive
(
:find_or_create_by
).
and_raise
(
ActiveRecord
::
RecordNotUnique
)
expect
(
Suggestion
).
to
receive
(
:find_or_create_by
).
and_raise
(
ActiveRecord
::
RecordNotUnique
)
allow
(
Suggestion
).
to
receive
(
:find_or_create_by
).
and_call_original
allow
(
Suggestion
).
to
receive
(
:find_or_create_by
).
and_call_original
...
@@ -20,4 +20,17 @@ describe ApplicationRecord do
...
@@ -20,4 +20,17 @@ describe ApplicationRecord do
.
to
change
{
Suggestion
.
count
}.
by
(
1
)
.
to
change
{
Suggestion
.
count
}.
by
(
1
)
end
end
end
end
describe
'.safe_find_or_create_by!'
do
it
'creates a record using safe_find_or_create_by'
do
expect
(
Suggestion
).
to
receive
(
:find_or_create_by
).
and_call_original
expect
(
Suggestion
.
safe_find_or_create_by!
(
build
(
:suggestion
).
attributes
))
.
to
be_a
(
Suggestion
)
end
it
'raises a validation error if the record was not persisted'
do
expect
{
Suggestion
.
find_or_create_by!
(
note:
nil
)
}.
to
raise_error
(
ActiveRecord
::
RecordInvalid
)
end
end
end
end
spec/models/gpg_signature_spec.rb
浏览文件 @
c982edfa
...
@@ -23,6 +23,41 @@ RSpec.describe GpgSignature do
...
@@ -23,6 +23,41 @@ RSpec.describe GpgSignature do
it
{
is_expected
.
to
validate_presence_of
(
:gpg_key_primary_keyid
)
}
it
{
is_expected
.
to
validate_presence_of
(
:gpg_key_primary_keyid
)
}
end
end
describe
'.safe_create!'
do
let
(
:attributes
)
do
{
commit_sha:
commit_sha
,
project:
project
,
gpg_key_primary_keyid:
gpg_key
.
keyid
}
end
it
'finds a signature by commit sha if it existed'
do
gpg_signature
expect
(
described_class
.
safe_create!
(
commit_sha:
commit_sha
)).
to
eq
(
gpg_signature
)
end
it
'creates a new signature if it was not found'
do
expect
{
described_class
.
safe_create!
(
attributes
)
}.
to
change
{
described_class
.
count
}.
by
(
1
)
end
it
'assigns the correct attributes when creating'
do
signature
=
described_class
.
safe_create!
(
attributes
)
expect
(
signature
.
project
).
to
eq
(
project
)
expect
(
signature
.
commit_sha
).
to
eq
(
commit_sha
)
expect
(
signature
.
gpg_key_primary_keyid
).
to
eq
(
gpg_key
.
keyid
)
end
it
'does not raise an error in case of a race condition'
do
expect
(
described_class
).
to
receive
(
:find_or_create_by
).
and_raise
(
ActiveRecord
::
RecordNotUnique
)
allow
(
described_class
).
to
receive
(
:find_or_create_by
).
and_call_original
described_class
.
safe_create!
(
attributes
)
end
end
describe
'#commit'
do
describe
'#commit'
do
it
'fetches the commit through the project'
do
it
'fetches the commit through the project'
do
expect_any_instance_of
(
Project
).
to
receive
(
:commit
).
with
(
commit_sha
).
and_return
(
commit
)
expect_any_instance_of
(
Project
).
to
receive
(
:commit
).
with
(
commit_sha
).
and_return
(
commit
)
...
...
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录