Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
G
gitlab-ce
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
1
Merge Requests
1
Analytics
Analytics
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Commits
Issue Boards
Open sidebar
nexedi
gitlab-ce
Commits
48f11f06
Commit
48f11f06
authored
Aug 12, 2020
by
Felipe Artur
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Allow to mark a requirement as satisfied
Allow to mark requirement as satisfied with GraphQL
parent
9cc1bd95
Changes
15
Hide whitespace changes
Inline
Side-by-side
Showing
15 changed files
with
203 additions
and
18 deletions
+203
-18
doc/api/graphql/reference/gitlab_schema.graphql
doc/api/graphql/reference/gitlab_schema.graphql
+10
-0
doc/api/graphql/reference/gitlab_schema.json
doc/api/graphql/reference/gitlab_schema.json
+24
-0
doc/api/graphql/reference/index.md
doc/api/graphql/reference/index.md
+1
-0
ee/app/graphql/mutations/requirements_management/update_requirement.rb
...l/mutations/requirements_management/update_requirement.rb
+6
-2
ee/app/graphql/types/requirements_management/requirement_type.rb
...graphql/types/requirements_management/requirement_type.rb
+2
-1
ee/app/models/requirements_management/requirement.rb
ee/app/models/requirements_management/requirement.rb
+8
-0
ee/app/models/requirements_management/test_report.rb
ee/app/models/requirements_management/test_report.rb
+10
-10
ee/app/services/requirements_management/update_requirement_service.rb
...ces/requirements_management/update_requirement_service.rb
+12
-0
ee/changelogs/unreleased/issue_218607_be.yml
ee/changelogs/unreleased/issue_218607_be.yml
+5
-0
ee/spec/graphql/mutations/requirements_management/update_requirement_spec.rb
...ations/requirements_management/update_requirement_spec.rb
+5
-3
ee/spec/graphql/types/requirements_management/requirement_type_spec.rb
...ql/types/requirements_management/requirement_type_spec.rb
+1
-1
ee/spec/models/requirements_management/requirement_spec.rb
ee/spec/models/requirements_management/requirement_spec.rb
+46
-0
ee/spec/models/requirements_management/test_report_spec.rb
ee/spec/models/requirements_management/test_report_spec.rb
+32
-0
ee/spec/requests/api/graphql/mutations/requirements_management/update_requirement_spec.rb
...ations/requirements_management/update_requirement_spec.rb
+1
-1
ee/spec/services/requirements_management/update_requirement_service_spec.rb
...equirements_management/update_requirement_service_spec.rb
+40
-0
No files found.
doc/api/graphql/reference/gitlab_schema.graphql
View file @
48f11f06
...
@@ -14254,6 +14254,11 @@ type Requirement {
...
@@ -14254,6 +14254,11 @@ type Requirement {
"""
"""
iid
:
ID
!
iid
:
ID
!
"""
Latest
requirement
test
report
state
"""
lastTestReportState
:
TestReportState
"""
"""
Project
to
which
the
requirement
belongs
Project
to
which
the
requirement
belongs
"""
"""
...
@@ -17314,6 +17319,11 @@ input UpdateRequirementInput {
...
@@ -17314,6 +17319,11 @@ input UpdateRequirementInput {
"""
"""
iid
:
String
!
iid
:
String
!
"""
Creates
a
test
report
for
the
requirement
with
the
given
state
"""
lastTestReportState
:
TestReportState
"""
"""
The
project
full
path
the
requirement
is
associated
with
The
project
full
path
the
requirement
is
associated
with
"""
"""
...
...
doc/api/graphql/reference/gitlab_schema.json
View file @
48f11f06
...
@@ -41613,6 +41613,20 @@
...
@@ -41613,6 +41613,20 @@
"isDeprecated": false,
"isDeprecated": false,
"deprecationReason": null
"deprecationReason": null
},
},
{
"name": "lastTestReportState",
"description": "Latest requirement test report state",
"args": [
],
"type": {
"kind": "ENUM",
"name": "TestReportState",
"ofType": null
},
"isDeprecated": false,
"deprecationReason": null
},
{
{
"name": "project",
"name": "project",
"description": "Project to which the requirement belongs",
"description": "Project to which the requirement belongs",
...
@@ -50832,6 +50846,16 @@
...
@@ -50832,6 +50846,16 @@
},
},
"defaultValue": null
"defaultValue": null
},
},
{
"name": "lastTestReportState",
"description": "Creates a test report for the requirement with the given state",
"type": {
"kind": "ENUM",
"name": "TestReportState",
"ofType": null
},
"defaultValue": null
},
{
{
"name": "clientMutationId",
"name": "clientMutationId",
"description": "A unique identifier for the client performing the mutation.",
"description": "A unique identifier for the client performing the mutation.",
doc/api/graphql/reference/index.md
View file @
48f11f06
...
@@ -1998,6 +1998,7 @@ Represents a requirement
...
@@ -1998,6 +1998,7 @@ Represents a requirement
|
`createdAt`
| Time! | Timestamp of when the requirement was created |
|
`createdAt`
| Time! | Timestamp of when the requirement was created |
|
`id`
| ID! | ID of the requirement |
|
`id`
| ID! | ID of the requirement |
|
`iid`
| ID! | Internal ID of the requirement |
|
`iid`
| ID! | Internal ID of the requirement |
|
`lastTestReportState`
| TestReportState | Latest requirement test report state |
|
`project`
| Project! | Project to which the requirement belongs |
|
`project`
| Project! | Project to which the requirement belongs |
|
`state`
| RequirementState! | State of the requirement |
|
`state`
| RequirementState! | State of the requirement |
|
`title`
| String | Title of the requirement |
|
`title`
| String | Title of the requirement |
...
...
ee/app/graphql/mutations/requirements_management/update_requirement.rb
View file @
48f11f06
...
@@ -29,10 +29,14 @@ module Mutations
...
@@ -29,10 +29,14 @@ module Mutations
required:
true
,
required:
true
,
description:
'The project full path the requirement is associated with'
description:
'The project full path the requirement is associated with'
argument
:last_test_report_state
,
Types
::
RequirementsManagement
::
TestReportStateEnum
,
required:
false
,
description:
'Creates a test report for the requirement with the given state'
def
ready?
(
**
args
)
def
ready?
(
**
args
)
if
args
.
values_at
(
:title
,
:state
).
compact
.
blank?
if
args
.
values_at
(
:title
,
:state
,
:last_test_report_state
).
compact
.
blank?
raise
Gitlab
::
Graphql
::
Errors
::
ArgumentError
,
raise
Gitlab
::
Graphql
::
Errors
::
ArgumentError
,
'title
or
state argument is required'
'title
, state or last_test_report_
state argument is required'
end
end
super
super
...
...
ee/app/graphql/types/requirements_management/requirement_type.rb
View file @
48f11f06
...
@@ -18,7 +18,8 @@ module Types
...
@@ -18,7 +18,8 @@ module Types
description:
'Title of the requirement'
description:
'Title of the requirement'
field
:state
,
RequirementsManagement
::
RequirementStateEnum
,
null:
false
,
field
:state
,
RequirementsManagement
::
RequirementStateEnum
,
null:
false
,
description:
'State of the requirement'
description:
'State of the requirement'
field
:last_test_report_state
,
RequirementsManagement
::
TestReportStateEnum
,
null:
true
,
complexity:
5
,
description:
'Latest requirement test report state'
field
:project
,
ProjectType
,
null:
false
,
field
:project
,
ProjectType
,
null:
false
,
description:
'Project to which the requirement belongs'
,
description:
'Project to which the requirement belongs'
,
resolve:
->
(
obj
,
_args
,
_ctx
)
{
Gitlab
::
Graphql
::
Loaders
::
BatchModelLoader
.
new
(
Project
,
obj
.
project_id
).
find
}
resolve:
->
(
obj
,
_args
,
_ctx
)
{
Gitlab
::
Graphql
::
Loaders
::
BatchModelLoader
.
new
(
Project
,
obj
.
project_id
).
find
}
...
...
ee/app/models/requirements_management/requirement.rb
View file @
48f11f06
...
@@ -58,5 +58,13 @@ module RequirementsManagement
...
@@ -58,5 +58,13 @@ module RequirementsManagement
def
resource_parent
def
resource_parent
project
project
end
end
def
last_test_report_state
test_reports
.
last
&
.
state
end
def
last_test_report_manually_created?
test_reports
.
last
&
.
build
.
nil?
end
end
end
end
end
ee/app/models/requirements_management/test_report.rb
View file @
48f11f06
...
@@ -31,6 +31,16 @@ module RequirementsManagement
...
@@ -31,6 +31,16 @@ module RequirementsManagement
bulk_insert!
(
reports
)
bulk_insert!
(
reports
)
end
end
def
build_report
(
author:
nil
,
state
:,
requirement
:,
build:
nil
,
timestamp:
Time
.
current
)
new
(
requirement_id:
requirement
.
id
,
build_id:
build
&
.
id
,
author_id:
build
&
.
user_id
||
author
&
.
id
,
created_at:
timestamp
,
state:
state
)
end
private
private
def
passed_reports_for_all_requirements
(
build
,
timestamp
)
def
passed_reports_for_all_requirements
(
build
,
timestamp
)
...
@@ -55,16 +65,6 @@ module RequirementsManagement
...
@@ -55,16 +65,6 @@ module RequirementsManagement
end
end
end
end
end
end
def
build_report
(
state
:,
requirement
:,
build
:,
timestamp
:)
new
(
requirement_id:
requirement
.
id
,
build_id:
build
.
id
,
author_id:
build
.
user_id
,
created_at:
timestamp
,
state:
state
)
end
end
end
end
end
end
end
ee/app/services/requirements_management/update_requirement_service.rb
View file @
48f11f06
...
@@ -8,11 +8,23 @@ module RequirementsManagement
...
@@ -8,11 +8,23 @@ module RequirementsManagement
attrs
=
whitelisted_requirement_params
attrs
=
whitelisted_requirement_params
requirement
.
update
(
attrs
)
requirement
.
update
(
attrs
)
create_test_report_for
(
requirement
)
if
manually_create_test_report?
requirement
requirement
end
end
private
private
def
manually_create_test_report?
params
[
:last_test_report_state
].
present?
end
def
create_test_report_for
(
requirement
)
return
unless
can?
(
current_user
,
:create_requirement_test_report
,
project
)
TestReport
.
build_report
(
requirement:
requirement
,
state:
params
[
:last_test_report_state
],
author:
current_user
).
save!
end
def
whitelisted_requirement_params
def
whitelisted_requirement_params
params
.
slice
(
:title
,
:state
)
params
.
slice
(
:title
,
:state
)
end
end
...
...
ee/changelogs/unreleased/issue_218607_be.yml
0 → 100644
View file @
48f11f06
---
title
:
Allow requirement status to be updated with GraphQL
merge_request
:
39371
author
:
type
:
added
ee/spec/graphql/mutations/requirements_management/update_requirement_spec.rb
View file @
48f11f06
...
@@ -21,13 +21,14 @@ RSpec.describe Mutations::RequirementsManagement::UpdateRequirement do
...
@@ -21,13 +21,14 @@ RSpec.describe Mutations::RequirementsManagement::UpdateRequirement do
project_path:
project
.
full_path
,
project_path:
project
.
full_path
,
iid:
requirement
.
iid
.
to_s
,
iid:
requirement
.
iid
.
to_s
,
title:
'foo'
,
title:
'foo'
,
state:
'archived'
state:
'archived'
,
last_test_report_state:
'passed'
)
)
end
end
it_behaves_like
'requirements not available'
it_behaves_like
'requirements not available'
context
'when the user can update the
epic
'
do
context
'when the user can update the
requirement
'
do
before
do
before
do
project
.
add_developer
(
user
)
project
.
add_developer
(
user
)
end
end
...
@@ -40,7 +41,8 @@ RSpec.describe Mutations::RequirementsManagement::UpdateRequirement do
...
@@ -40,7 +41,8 @@ RSpec.describe Mutations::RequirementsManagement::UpdateRequirement do
it
'updates new requirement'
,
:aggregate_failures
do
it
'updates new requirement'
,
:aggregate_failures
do
expect
(
subject
[
:requirement
]).
to
have_attributes
(
expect
(
subject
[
:requirement
]).
to
have_attributes
(
title:
'foo'
,
title:
'foo'
,
state:
'archived'
state:
'archived'
,
last_test_report_state:
'passed'
)
)
expect
(
subject
[
:errors
]).
to
be_empty
expect
(
subject
[
:errors
]).
to
be_empty
end
end
...
...
ee/spec/graphql/types/requirements_management/requirement_type_spec.rb
View file @
48f11f06
...
@@ -3,7 +3,7 @@
...
@@ -3,7 +3,7 @@
require
'spec_helper'
require
'spec_helper'
RSpec
.
describe
GitlabSchema
.
types
[
'Requirement'
]
do
RSpec
.
describe
GitlabSchema
.
types
[
'Requirement'
]
do
fields
=
%i[id iid title state project author created_at updated_at user_permissions test_reports]
fields
=
%i[id iid title state
last_test_report_state
project author created_at updated_at user_permissions test_reports]
it
{
expect
(
described_class
).
to
expose_permissions_using
(
Types
::
PermissionTypes
::
Requirement
)
}
it
{
expect
(
described_class
).
to
expose_permissions_using
(
Types
::
PermissionTypes
::
Requirement
)
}
...
...
ee/spec/models/requirements_management/requirement_spec.rb
View file @
48f11f06
...
@@ -77,4 +77,50 @@ RSpec.describe RequirementsManagement::Requirement do
...
@@ -77,4 +77,50 @@ RSpec.describe RequirementsManagement::Requirement do
end
end
end
end
end
end
describe
'#last_test_report_state'
do
let_it_be
(
:requirement
)
{
create
(
:requirement
)
}
context
'when latest test report is passing'
do
it
'returns passing'
do
create
(
:test_report
,
requirement:
requirement
,
state: :passed
,
build:
nil
)
expect
(
requirement
.
last_test_report_state
).
to
eq
(
'passed'
)
end
end
context
'when latest test report is failing'
do
it
'returns failing'
do
create
(
:test_report
,
requirement:
requirement
,
state: :failed
,
build:
nil
)
expect
(
requirement
.
last_test_report_state
).
to
eq
(
'failed'
)
end
end
context
'when there are no test reports'
do
it
'returns nil'
do
expect
(
requirement
.
last_test_report_state
).
to
eq
(
nil
)
end
end
end
describe
'#status_manually_updated'
do
let_it_be
(
:requirement
)
{
create
(
:requirement
)
}
context
'when latest test report has a build'
do
it
'returns false'
do
create
(
:test_report
,
requirement:
requirement
,
state: :passed
)
expect
(
requirement
.
last_test_report_manually_created?
).
to
eq
(
false
)
end
end
context
'when latest test report does not have a build'
do
it
'returns true'
do
create
(
:test_report
,
requirement:
requirement
,
state: :passed
,
build:
nil
)
expect
(
requirement
.
last_test_report_manually_created?
).
to
eq
(
true
)
end
end
end
end
end
ee/spec/models/requirements_management/test_report_spec.rb
View file @
48f11f06
...
@@ -96,4 +96,36 @@ RSpec.describe RequirementsManagement::TestReport do
...
@@ -96,4 +96,36 @@ RSpec.describe RequirementsManagement::TestReport do
end
end
end
end
end
end
describe
'.build_report'
do
let_it_be
(
:user
)
{
create
(
:user
)
}
let_it_be
(
:build_author
)
{
create
(
:user
)
}
let_it_be
(
:build
)
{
create
(
:ci_build
,
author:
build_author
)
}
let_it_be
(
:requirement
)
{
create
(
:requirement
,
state: :opened
)
}
let
(
:now
)
{
Time
.
current
}
context
'when build is passed as argument'
do
it
'builds test report with correct attributes'
do
test_report
=
described_class
.
build_report
(
requirement:
requirement
,
author:
user
,
state:
'failed'
,
build:
build
,
timestamp:
now
)
expect
(
test_report
.
author
).
to
eq
(
build
.
author
)
expect
(
test_report
.
build
).
to
eq
(
build
)
expect
(
test_report
.
requirement
).
to
eq
(
requirement
)
expect
(
test_report
.
state
).
to
eq
(
'failed'
)
expect
(
test_report
.
created_at
).
to
eq
(
now
)
end
end
context
'when build is not passed as argument'
do
it
'builds test report with correct attributes'
do
test_report
=
described_class
.
build_report
(
requirement:
requirement
,
author:
user
,
state:
'passed'
,
timestamp:
now
)
expect
(
test_report
.
author
).
to
eq
(
user
)
expect
(
test_report
.
build
).
to
eq
(
nil
)
expect
(
test_report
.
requirement
).
to
eq
(
requirement
)
expect
(
test_report
.
state
).
to
eq
(
'passed'
)
expect
(
test_report
.
created_at
).
to
eq
(
now
)
end
end
end
end
end
ee/spec/requests/api/graphql/mutations/requirements_management/update_requirement_spec.rb
View file @
48f11f06
...
@@ -81,7 +81,7 @@ RSpec.describe 'Updating a Requirement' do
...
@@ -81,7 +81,7 @@ RSpec.describe 'Updating a Requirement' do
let
(
:attributes
)
{
{}
}
let
(
:attributes
)
{
{}
}
it_behaves_like
'a mutation that returns top-level errors'
,
it_behaves_like
'a mutation that returns top-level errors'
,
errors:
[
'title
or
state argument is required'
]
errors:
[
'title
, state or last_test_report_
state argument is required'
]
end
end
context
'when requirements_management flag is disabled'
do
context
'when requirements_management flag is disabled'
do
...
...
ee/spec/services/requirements_management/update_requirement_service_spec.rb
View file @
48f11f06
...
@@ -38,6 +38,46 @@ RSpec.describe RequirementsManagement::UpdateRequirementService do
...
@@ -38,6 +38,46 @@ RSpec.describe RequirementsManagement::UpdateRequirementService do
author_id:
params
[
:author_id
]
author_id:
params
[
:author_id
]
)
)
end
end
context
'when updating last test report state'
do
context
'as passing'
do
it
'creates passing test report with null build_id'
do
service
=
described_class
.
new
(
project
,
user
,
{
last_test_report_state:
'passed'
})
expect
{
service
.
execute
(
requirement
)
}.
to
change
{
RequirementsManagement
::
TestReport
.
count
}.
from
(
0
).
to
(
1
)
test_report
=
requirement
.
test_reports
.
last
expect
(
requirement
.
last_test_report_state
).
to
eq
(
'passed'
)
expect
(
requirement
.
last_test_report_manually_created?
).
to
eq
(
true
)
expect
(
test_report
.
state
).
to
eq
(
'passed'
)
expect
(
test_report
.
build
).
to
eq
(
nil
)
expect
(
test_report
.
author
).
to
eq
(
user
)
end
end
context
'as failed'
do
it
'creates failing test report with null build_id'
do
service
=
described_class
.
new
(
project
,
user
,
{
last_test_report_state:
'failed'
})
expect
{
service
.
execute
(
requirement
)
}.
to
change
{
RequirementsManagement
::
TestReport
.
count
}.
from
(
0
).
to
(
1
)
test_report
=
requirement
.
test_reports
.
last
expect
(
requirement
.
last_test_report_state
).
to
eq
(
'failed'
)
expect
(
requirement
.
last_test_report_manually_created?
).
to
eq
(
true
)
expect
(
test_report
.
state
).
to
eq
(
'failed'
)
expect
(
test_report
.
build
).
to
eq
(
nil
)
expect
(
test_report
.
author
).
to
eq
(
user
)
end
end
context
'when user cannot create test reports'
do
it
'does not create test report'
do
allow
(
Ability
).
to
receive
(
:allowed?
).
and_call_original
allow
(
Ability
).
to
receive
(
:allowed?
).
with
(
user
,
:create_requirement_test_report
,
project
).
and_return
(
false
)
service
=
described_class
.
new
(
project
,
user
,
{
last_test_report_state:
'failed'
})
expect
{
service
.
execute
(
requirement
)
}.
not_to
change
{
RequirementsManagement
::
TestReport
.
count
}
end
end
end
end
end
context
'when user is not allowed to update requirements'
do
context
'when user is not allowed to update requirements'
do
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment