shipit-engine 0.32.0 → 0.33.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (176) hide show
  1. checksums.yaml +4 -4
  2. data/app/assets/images/magic-solid.svg +1 -0
  3. data/app/assets/javascripts/shipit/repositories_search.js.coffee +60 -0
  4. data/app/assets/javascripts/shipit/{search.js.coffee → stack_search.js.coffee} +0 -0
  5. data/app/assets/stylesheets/_pages/_repositories.scss +148 -0
  6. data/app/assets/stylesheets/_pages/_stacks.scss +19 -0
  7. data/app/assets/stylesheets/shipit.scss +1 -0
  8. data/app/controllers/shipit/api/{pull_requests_controller.rb → merge_requests_controller.rb} +8 -8
  9. data/app/controllers/shipit/api/stacks_controller.rb +14 -1
  10. data/app/controllers/shipit/deploys_controller.rb +2 -2
  11. data/app/controllers/shipit/merge_requests_controller.rb +31 -0
  12. data/app/controllers/shipit/merge_status_controller.rb +15 -15
  13. data/app/controllers/shipit/repositories_controller.rb +74 -0
  14. data/app/controllers/shipit/tasks_controller.rb +4 -4
  15. data/app/helpers/shipit/chunks_helper.rb +2 -2
  16. data/app/helpers/shipit/github_url_helper.rb +8 -0
  17. data/app/helpers/shipit/stacks_helper.rb +4 -0
  18. data/app/jobs/shipit/create_on_github_job.rb +1 -0
  19. data/app/jobs/shipit/destroy_repository_job.rb +24 -0
  20. data/app/jobs/shipit/destroy_stack_job.rb +2 -2
  21. data/app/jobs/shipit/perform_task_job.rb +4 -98
  22. data/app/jobs/shipit/process_merge_requests_job.rb +32 -0
  23. data/app/jobs/shipit/refresh_merge_request_job.rb +11 -0
  24. data/app/models/shipit/anonymous_user.rb +4 -0
  25. data/app/models/shipit/check_run.rb +2 -2
  26. data/app/models/shipit/command_line_user.rb +4 -0
  27. data/app/models/shipit/commit.rb +11 -11
  28. data/app/models/shipit/commit_checks.rb +1 -0
  29. data/app/models/shipit/deploy.rb +1 -0
  30. data/app/models/shipit/deploy_spec.rb +16 -4
  31. data/app/models/shipit/deploy_spec/file_system.rb +11 -5
  32. data/app/models/shipit/hook.rb +2 -0
  33. data/app/models/shipit/merge_request.rb +302 -0
  34. data/app/models/shipit/provisioning_handler.rb +32 -0
  35. data/app/models/shipit/provisioning_handler/base.rb +30 -0
  36. data/app/models/shipit/provisioning_handler/unregistered_provisioning_handler.rb +35 -0
  37. data/app/models/shipit/pull_request.rb +25 -264
  38. data/app/models/shipit/pull_request_assignment.rb +10 -0
  39. data/app/models/shipit/repository.rb +54 -0
  40. data/app/models/shipit/review_stack.rb +116 -0
  41. data/app/models/shipit/review_stack_provisioning_queue.rb +39 -0
  42. data/app/models/shipit/stack.rb +22 -8
  43. data/app/models/shipit/task.rb +56 -7
  44. data/app/models/shipit/task_execution_strategy/base.rb +20 -0
  45. data/app/models/shipit/task_execution_strategy/default.rb +110 -0
  46. data/app/models/shipit/user.rb +6 -1
  47. data/app/models/shipit/webhooks.rb +10 -0
  48. data/app/models/shipit/webhooks/handlers/pull_request/assigned_handler.rb +74 -0
  49. data/app/models/shipit/webhooks/handlers/pull_request/closed_handler.rb +68 -0
  50. data/app/models/shipit/webhooks/handlers/pull_request/edited_handler.rb +74 -0
  51. data/app/models/shipit/webhooks/handlers/pull_request/label_capturing_handler.rb +127 -0
  52. data/app/models/shipit/webhooks/handlers/pull_request/labeled_handler.rb +106 -0
  53. data/app/models/shipit/webhooks/handlers/pull_request/opened_handler.rb +83 -0
  54. data/app/models/shipit/webhooks/handlers/pull_request/reopened_handler.rb +88 -0
  55. data/app/models/shipit/webhooks/handlers/pull_request/review_stack_adapter.rb +103 -0
  56. data/app/models/shipit/webhooks/handlers/pull_request/unlabeled_handler.rb +107 -0
  57. data/app/serializers/shipit/deploy_serializer.rb +6 -0
  58. data/app/serializers/shipit/merge_request_serializer.rb +21 -0
  59. data/app/serializers/shipit/pull_request_serializer.rb +5 -8
  60. data/app/serializers/shipit/review_stack_serializer.rb +7 -0
  61. data/app/serializers/shipit/stack_serializer.rb +7 -6
  62. data/app/serializers/shipit/tail_task_serializer.rb +10 -2
  63. data/app/serializers/shipit/task_serializer.rb +1 -1
  64. data/app/views/shipit/merge_requests/_merge_request.html.erb +29 -0
  65. data/app/views/shipit/{pull_requests → merge_requests}/index.html.erb +2 -2
  66. data/app/views/shipit/merge_requests/merge_requests/_pull_request.html.erb +29 -0
  67. data/app/views/shipit/merge_requests/merge_requests/index.html.erb +20 -0
  68. data/app/views/shipit/merge_status/_merge_queue_button.html.erb +3 -3
  69. data/app/views/shipit/merge_status/backlogged.html.erb +1 -1
  70. data/app/views/shipit/merge_status/failure.html.erb +1 -1
  71. data/app/views/shipit/merge_status/locked.html.erb +1 -1
  72. data/app/views/shipit/merge_status/success.html.erb +2 -2
  73. data/app/views/shipit/repositories/_header.html.erb +19 -0
  74. data/app/views/shipit/repositories/index.html.erb +31 -0
  75. data/app/views/shipit/repositories/new.html.erb +23 -0
  76. data/app/views/shipit/repositories/settings.html.erb +53 -0
  77. data/app/views/shipit/repositories/show.html.erb +30 -0
  78. data/app/views/shipit/stacks/_banners.html.erb +13 -0
  79. data/app/views/shipit/stacks/_header.html.erb +5 -2
  80. data/app/views/shipit/stacks/_stack.html.erb +8 -0
  81. data/app/views/shipit/stacks/index.html.erb +2 -1
  82. data/app/views/shipit/stacks/settings.html.erb +5 -5
  83. data/app/views/shipit/stacks/show.html.erb +1 -1
  84. data/app/views/shipit/tasks/_task_output.html.erb +1 -1
  85. data/config/routes.rb +15 -5
  86. data/db/migrate/20200706145406_add_review_stacks.rb +12 -0
  87. data/db/migrate/20200804144639_rename_pull_request_to_merge_request.rb +7 -0
  88. data/db/migrate/20200804161512_rename_commits_pull_request_id_to_merge_request_id.rb +5 -0
  89. data/db/migrate/20200813134712_recreate_shipit_pull_requests.rb +22 -0
  90. data/db/migrate/20200813194056_create_pull_request_assignments.rb +8 -0
  91. data/db/migrate/20201001125502_add_provision_pr_stacks_flag_to_repositories.rb +7 -0
  92. data/db/migrate/20201008145809_add_retry_attempt_to_tasks.rb +5 -0
  93. data/db/migrate/20201008152744_add_max_retries_to_tasks.rb +5 -0
  94. data/lib/shipit.rb +11 -1
  95. data/lib/shipit/github_app.rb +1 -1
  96. data/lib/shipit/review_stack_commands.rb +8 -0
  97. data/lib/shipit/stack_commands.rb +6 -1
  98. data/lib/shipit/task_commands.rb +1 -0
  99. data/lib/shipit/version.rb +1 -1
  100. data/lib/tasks/cron.rake +11 -2
  101. data/test/controllers/api/{pull_requests_controller_test.rb → merge_requests_controller_test.rb} +12 -12
  102. data/test/controllers/api/outputs_controller_test.rb +1 -0
  103. data/test/controllers/api/rollback_controller_test.rb +1 -1
  104. data/test/controllers/api/stacks_controller_test.rb +21 -1
  105. data/test/controllers/{pull_requests_controller_test.rb → merge_requests_controller_test.rb} +6 -6
  106. data/test/controllers/repositories_controller_test.rb +71 -0
  107. data/test/controllers/stacks_controller_test.rb +9 -1
  108. data/test/controllers/tasks_controller_test.rb +14 -2
  109. data/test/controllers/webhooks_controller_test.rb +1 -1
  110. data/test/dummy/config/application.rb +6 -1
  111. data/test/dummy/config/environments/development.rb +0 -3
  112. data/test/dummy/config/environments/test.rb +0 -5
  113. data/test/dummy/db/schema.rb +52 -14
  114. data/test/dummy/db/seeds.rb +1 -1
  115. data/test/fixtures/payloads/check_suite_master.json +2 -2
  116. data/test/fixtures/payloads/invalid_pull_request.json +117 -0
  117. data/test/fixtures/payloads/provision_disabled_pull_request.json +454 -0
  118. data/test/fixtures/payloads/pull_request_assigned.json +480 -0
  119. data/test/fixtures/payloads/pull_request_closed.json +454 -0
  120. data/test/fixtures/payloads/pull_request_labeled.json +461 -0
  121. data/test/fixtures/payloads/pull_request_opened.json +454 -0
  122. data/test/fixtures/payloads/pull_request_reopened.json +454 -0
  123. data/test/fixtures/payloads/pull_request_unlabeled.json +454 -0
  124. data/test/fixtures/payloads/pull_request_with_no_repo.json +454 -0
  125. data/test/fixtures/shipit/commits.yml +15 -2
  126. data/test/fixtures/shipit/merge_requests.yml +141 -0
  127. data/test/fixtures/shipit/pull_request_assignments.yml +3 -0
  128. data/test/fixtures/shipit/pull_requests.yml +10 -131
  129. data/test/fixtures/shipit/repositories.yml +1 -0
  130. data/test/fixtures/shipit/stacks.yml +145 -0
  131. data/test/fixtures/shipit/statuses.yml +9 -0
  132. data/test/fixtures/shipit/tasks.yml +3 -0
  133. data/test/fixtures/shipit/users.yml +7 -0
  134. data/test/helpers/payloads_helper.rb +4 -0
  135. data/test/jobs/chunk_rollup_job_test.rb +15 -1
  136. data/test/jobs/destroy_repository_job_test.rb +27 -0
  137. data/test/jobs/perform_task_job_test.rb +8 -8
  138. data/test/jobs/{merge_pull_requests_job_test.rb → process_merge_requests_job_test.rb} +18 -18
  139. data/test/lib/shipit/deploy_commands_test.rb +16 -0
  140. data/test/lib/shipit/task_commands_test.rb +17 -0
  141. data/test/models/commits_test.rb +22 -13
  142. data/test/models/deploy_spec_test.rb +57 -24
  143. data/test/models/deploys_test.rb +148 -14
  144. data/test/models/{pull_request_test.rb → merge_request_test.rb} +30 -30
  145. data/test/models/pull_request_assignment_test.rb +16 -0
  146. data/test/models/shipit/provisioning_handler/base_test.rb +33 -0
  147. data/test/models/shipit/provisioning_handler/unregistered_provisioning_handler_test.rb +49 -0
  148. data/test/models/shipit/provisioning_handler_test.rb +64 -0
  149. data/test/models/shipit/pull_request_test.rb +52 -0
  150. data/test/models/shipit/repository_test.rb +5 -1
  151. data/test/models/shipit/review_stack_provision_status_test.rb +77 -0
  152. data/test/models/shipit/review_stack_provisioning_queue_test.rb +63 -0
  153. data/test/models/shipit/review_stack_test.rb +59 -0
  154. data/test/models/{stacks_test.rb → shipit/stacks_test.rb} +10 -4
  155. data/test/models/shipit/webhooks/handlers/pull_request/assigned_handler_test.rb +45 -0
  156. data/test/models/shipit/webhooks/handlers/pull_request/closed_handler_test.rb +192 -0
  157. data/test/models/shipit/webhooks/handlers/pull_request/edited_handler_test.rb +47 -0
  158. data/test/models/shipit/webhooks/handlers/pull_request/label_capturing_handler_test.rb +209 -0
  159. data/test/models/shipit/webhooks/handlers/pull_request/labeled_handler_test.rb +332 -0
  160. data/test/models/shipit/webhooks/handlers/pull_request/opened_handler_test.rb +238 -0
  161. data/test/models/shipit/webhooks/handlers/pull_request/reopened_handler_test.rb +282 -0
  162. data/test/models/shipit/webhooks/handlers/pull_request/review_stack_adapter_test.rb +83 -0
  163. data/test/models/shipit/webhooks/handlers/pull_request/unlabeled_handler_test.rb +324 -0
  164. data/test/models/shipit/{wehbooks → webhooks}/handlers_test.rb +0 -0
  165. data/test/models/tasks_test.rb +44 -3
  166. data/test/serializers/shipit/pull_request_serializer_test.rb +29 -0
  167. data/test/unit/command_test.rb +3 -3
  168. data/test/unit/github_url_helper_test.rb +5 -0
  169. data/test/unit/shipit_task_execution_strategy_test.rb +47 -0
  170. metadata +260 -154
  171. data/app/controllers/shipit/pull_requests_controller.rb +0 -31
  172. data/app/jobs/shipit/merge_pull_requests_job.rb +0 -32
  173. data/app/jobs/shipit/refresh_pull_request_job.rb +0 -11
  174. data/app/views/shipit/pull_requests/_pull_request.html.erb +0 -29
  175. data/test/fixtures/shipit/output_chunks.yml +0 -47
  176. data/test/models/output_chunk_test.rb +0 -21
@@ -0,0 +1,47 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "test_helper"
4
+
5
+ module Shipit
6
+ module Webhooks
7
+ module Handlers
8
+ module PullRequest
9
+ class EditedHandlerTest < ActiveSupport::TestCase
10
+ test "validates payload" do
11
+ assert_raise(StandardError) { EditedHandler.new(payload_parsed(:invalid_pull_request)) }
12
+ end
13
+
14
+ test "updates the existing PullRequest" do
15
+ pull_request = shipit_pull_requests(:review_stack_review)
16
+ payload = payload_parsed(:pull_request_opened)
17
+ payload["action"] = "edited"
18
+ payload["number"] = pull_request.number
19
+ payload["pull_request"]["title"] = "New Title"
20
+
21
+ assert_changes -> { pull_request.reload.title }, to: "New Title" do
22
+ EditedHandler.new(payload).process
23
+ end
24
+ end
25
+
26
+ test "does not attempt to update when PullRequest does not exist" do
27
+ unknown_pull_request_number = 999
28
+ payload = payload_parsed(:pull_request_opened)
29
+ payload["number"] = unknown_pull_request_number
30
+ payload["action"] = "edited"
31
+ payload["pull_request"]["title"] = "New Title"
32
+
33
+ assert_no_enqueued_jobs do
34
+ EditedHandler.new(payload).process
35
+ end
36
+ end
37
+
38
+ test "ignores non pull_request 'edited' webhooks" do
39
+ assert_no_difference -> { Shipit::Stack.not_archived.count } do
40
+ EditedHandler.new(payload_parsed(:pull_request_opened).merge(action: "assigned")).process
41
+ end
42
+ end
43
+ end
44
+ end
45
+ end
46
+ end
47
+ end
@@ -0,0 +1,209 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "test_helper"
4
+
5
+ module Shipit
6
+ module Webhooks
7
+ module Handlers
8
+ module PullRequest
9
+ class LabelCapturingHandlerTest < ActiveSupport::TestCase
10
+ test "captures labels when opening a pull request for a known stack" do
11
+ payload = payload_parsed(:pull_request_opened)
12
+ payload["pull_request"]["labels"] = [{ "name" => "expected-label" }]
13
+ stack = create_stack
14
+
15
+ LabelCapturingHandler.new(payload).process
16
+
17
+ assert_has_label stack, "expected-label"
18
+ end
19
+
20
+ test "does not create stacks when opening new pull requests" do
21
+ payload = payload_parsed(:pull_request_opened)
22
+ payload["pull_request"]["labels"] = [{ "name" => "expected-label" }]
23
+
24
+ assert_no_difference -> { Shipit::Stack.count } do
25
+ LabelCapturingHandler.new(payload).process
26
+ end
27
+ end
28
+
29
+ test "captures labels when labels are applied to stacks which are not archived" do
30
+ payload = payload_parsed(:pull_request_labeled)
31
+ payload["pull_request"]["labels"] = [{ "name" => "expected-label" }]
32
+ stack = create_stack
33
+
34
+ LabelCapturingHandler.new(payload).process
35
+
36
+ assert_has_label stack, "expected-label"
37
+ end
38
+
39
+ test "does not capture labels when labels are applied to archived stacks" do
40
+ payload = payload_parsed(:pull_request_labeled)
41
+ payload["pull_request"]["labels"] = [{ "name" => "expected-label" }]
42
+ stack = create_archived_stack
43
+
44
+ LabelCapturingHandler.new(payload).process
45
+
46
+ assert_empty stack.reload.pull_request.labels
47
+ end
48
+
49
+ test "ignores unknown stacks when labels are added" do
50
+ payload = payload_parsed(:pull_request_labeled)
51
+ payload["repository"]["full_name"] = "unknown/repository"
52
+ payload["pull_request"]["labels"] = [{ "name" => "expected-label" }]
53
+
54
+ assert_no_difference -> { Shipit::Stack.count } do
55
+ LabelCapturingHandler.new(payload).process
56
+ end
57
+ end
58
+
59
+ test "captures labels when labels are removed from stack which are not archived" do
60
+ stack = create_stack
61
+ stack.pull_request.labels << "label-to-be-removed"
62
+ payload = payload_parsed(:pull_request_unlabeled)
63
+ payload["pull_request"]["labels"] = [{ "name" => "expected-label" }]
64
+
65
+ LabelCapturingHandler.new(payload).process
66
+
67
+ stack.reload
68
+ assert_does_not_have_label stack, "label-to-be-removed"
69
+ assert_has_label stack, "expected-label"
70
+ end
71
+
72
+ test "does not capture labels when labels are removed from archived stacks" do
73
+ payload = payload_parsed(:pull_request_unlabeled)
74
+ payload["pull_request"]["labels"] = [{ "name" => "expected-label" }]
75
+ stack = create_archived_stack
76
+
77
+ LabelCapturingHandler.new(payload).process
78
+
79
+ assert_empty stack.reload.pull_request.labels
80
+ end
81
+
82
+ test "ignores unknown stacks when labels are removed" do
83
+ payload = payload_parsed(:pull_request_unlabeled)
84
+ payload["repository"]["full_name"] = "unknown/repository"
85
+ payload["pull_request"]["labels"] = [{ "name" => "expected-label" }]
86
+
87
+ assert_no_difference -> { Shipit::Stack.count } do
88
+ LabelCapturingHandler.new(payload).process
89
+ end
90
+ end
91
+
92
+ test "captures labels when reopening a pull request" do
93
+ payload = payload_parsed(:pull_request_reopened)
94
+ payload["pull_request"]["labels"] = [{ "name" => "expected-label" }]
95
+ stack = create_stack
96
+
97
+ LabelCapturingHandler.new(payload).process
98
+
99
+ assert_has_label stack, "expected-label"
100
+ end
101
+
102
+ test "does not capture labels when reopening a pull request with an archived stack" do
103
+ payload = payload_parsed(:pull_request_reopened)
104
+ payload["pull_request"]["labels"] = [{ "name" => "expected-label" }]
105
+ stack = create_archived_stack
106
+
107
+ LabelCapturingHandler.new(payload).process
108
+
109
+ assert_empty stack.reload.pull_request.labels
110
+ end
111
+
112
+ test "ignores reopening a pull request with an unknown repository" do
113
+ payload = payload_parsed(:pull_request_reopened)
114
+ payload["repository"]["full_name"] = "unknown/repository"
115
+ payload["pull_request"]["labels"] = [{ "name" => "expected-label" }]
116
+
117
+ assert_no_difference -> { Shipit::Stack.count } do
118
+ LabelCapturingHandler.new(payload).process
119
+ end
120
+ end
121
+
122
+ test "accepts extended unicode characters (emoji) in label names" do
123
+ payload = payload_parsed(:pull_request_opened)
124
+ payload["pull_request"]["labels"] = [{ "name" => "Shipit 🚢" }]
125
+ stack = create_stack
126
+
127
+ LabelCapturingHandler.new(payload).process
128
+
129
+ assert_has_label stack, "Shipit 🚢"
130
+ end
131
+
132
+ def create_archived_stack
133
+ stack = create_stack
134
+ stack.archive!(shipit_users(:codertocat))
135
+
136
+ stack
137
+ end
138
+
139
+ def create_stack
140
+ repository = shipit_repositories(:shipit)
141
+ repository.provisioning_behavior = :allow_all
142
+ repository.save!
143
+
144
+ payload = payload_parsed(:pull_request_opened)
145
+
146
+ OpenedHandler.new(payload).process
147
+
148
+ stack = repository.stacks.last
149
+ complete_active_tasks(stack)
150
+
151
+ stack
152
+ end
153
+
154
+ def complete_active_tasks(stack)
155
+ active_tasks = stack
156
+ .tasks
157
+ .active
158
+
159
+ active_tasks.map(&:run)
160
+ active_tasks.reload
161
+ active_tasks.map(&:complete)
162
+ end
163
+
164
+ def assert_has_label(stack, label_name)
165
+ assert_includes(stack.pull_request.labels, label_name)
166
+ end
167
+
168
+ def assert_does_not_have_label(stack, label_name)
169
+ assert_not_includes(stack.pull_request.labels, label_name)
170
+ end
171
+
172
+ def environment_for(payload)
173
+ "pr#{payload['number']}"
174
+ end
175
+
176
+ setup do
177
+ Shipit.github.api.stubs(:commit)
178
+ .with("shopify/shipit-engine", "ec26c3e57ca3a959ca5aad62de7213c562f8c821")
179
+ .returns(
180
+ resource(
181
+ {
182
+ sha: "ec26c3e57ca3a959ca5aad62de7213c562f8c821",
183
+ commit: {
184
+ author: {
185
+ name: "Codertocat",
186
+ email: "21031067+Codertocat@users.noreply.github.com",
187
+ date: "2019-05-15 15:20:30",
188
+ },
189
+ committer: {
190
+ name: "Codertocat",
191
+ email: "21031067+Codertocat@users.noreply.github.com",
192
+ date: "2019-05-15 15:20:30",
193
+ },
194
+ message: "Update README.md",
195
+ },
196
+ stats: {
197
+ total: 2,
198
+ additions: 1,
199
+ deletions: 1,
200
+ },
201
+ }
202
+ )
203
+ )
204
+ end
205
+ end
206
+ end
207
+ end
208
+ end
209
+ end
@@ -0,0 +1,332 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "test_helper"
4
+
5
+ module Shipit
6
+ module Webhooks
7
+ module Handlers
8
+ module PullRequest
9
+ class LabeledHandlerTest < ActiveSupport::TestCase
10
+ test "validates payload" do
11
+ assert_raise(StandardError) { LabeledHandler.new(payload_parsed(:invalid_pull_request)) }
12
+ end
13
+
14
+ test "ignores Github webhooks when the event is NOT 'labeled'" do
15
+ assert_no_difference -> { Shipit::Stack.count } do
16
+ LabeledHandler.new(payload_parsed(:pull_request_labeled).merge(action: "assigned")).process
17
+ end
18
+ end
19
+
20
+ test "ignores Github PullRequest webhooks by default" do
21
+ assert_no_difference -> { Shipit::Stack.count } do
22
+ LabeledHandler.new(payload_parsed(:pull_request_with_no_repo)).process
23
+ end
24
+ end
25
+
26
+ test "ignores Github PullRequest webhooks when the Repository has disabled the Review Stacks feature" do
27
+ repository = shipit_repositories(:shipit)
28
+ configure_provisioning_behavior(
29
+ repository: repository,
30
+ provisioning_enabled: false,
31
+ behavior: :allow_with_label,
32
+ label: "pull-requests-label"
33
+ )
34
+
35
+ assert_no_difference -> { Shipit::Stack.count } do
36
+ LabeledHandler.new(payload_parsed(:pull_request_labeled)).process
37
+ end
38
+ end
39
+
40
+ test "ignores Github PullRequest webhooks when the repository allows_all PullRequests to create ReviewStacks" do
41
+ repository = shipit_repositories(:shipit)
42
+ configure_provisioning_behavior(
43
+ repository: repository,
44
+ behavior: :allow_all
45
+ )
46
+
47
+ assert_no_difference -> { Shipit::Stack.count } do
48
+ LabeledHandler.new(payload_parsed(:pull_request_labeled)).process
49
+ end
50
+ end
51
+
52
+ test "unarchives existing review stack when the repository creates ReviewStacks with allow_with_label and the label is present" do
53
+ stack = create_archived_stack
54
+ repository = shipit_repositories(:shipit)
55
+ configure_provisioning_behavior(
56
+ repository: repository,
57
+ behavior: :allow_with_label,
58
+ label: "pull-requests-label"
59
+ )
60
+ payload = payload_parsed(:pull_request_labeled)
61
+ payload["pull_request"]["labels"] << { "name" => "pull-requests-label" }
62
+
63
+ LabeledHandler.new(payload_parsed(:pull_request_labeled)).process
64
+
65
+ assert_not stack.reload.archived?, "Expected stack to be NOT be archived"
66
+ assert_pending_provision(stack)
67
+ end
68
+
69
+ test "creates and provisions a new review stack when the repository creates ReviewStacks with allow_with_label and the label is present" do
70
+ repository = shipit_repositories(:shipit)
71
+ configure_provisioning_behavior(
72
+ repository: repository,
73
+ behavior: :allow_with_label,
74
+ label: "pull-requests-label"
75
+ )
76
+ payload = payload_parsed(:pull_request_labeled)
77
+ payload["pull_request"]["labels"] = [{ "name" => "pull-requests-label" }]
78
+
79
+ LabeledHandler.new(payload).process
80
+
81
+ stack = shipit_repositories(:shipit).stacks.last
82
+ assert_equal stack.environment, "pr#{payload['number']}"
83
+ assert_equal stack.continuous_deployment, false
84
+ assert_equal stack.ignore_ci, false
85
+ assert_equal stack.branch, payload["pull_request"]["head"]["ref"]
86
+ assert_not stack.archived?, "Expected stack to be NOT be archived"
87
+ assert_pending_provision(stack)
88
+ end
89
+
90
+ test "archives an existing review stack when the repository creates ReviewStacks with allow_with_label and the label is absent" do
91
+ stack = create_stack
92
+ repository = shipit_repositories(:shipit)
93
+ configure_provisioning_behavior(
94
+ repository: repository,
95
+ behavior: :allow_with_label,
96
+ label: "pull-requests-label"
97
+ )
98
+ payload = payload_parsed(:pull_request_labeled)
99
+ payload["pull_request"]["labels"] = []
100
+
101
+ LabeledHandler.new(payload).process
102
+
103
+ assert stack.reload.archived?, "Expected stack to be archived"
104
+ end
105
+
106
+ test "deprovisions an existing review stack when the repository creates ReviewStacks with allow_with_label and the label is absent" do
107
+ stack = create_stack
108
+ repository = shipit_repositories(:shipit)
109
+ configure_provisioning_behavior(
110
+ repository: repository,
111
+ behavior: :allow_with_label,
112
+ label: "pull-requests-label"
113
+ )
114
+ payload = payload_parsed(:pull_request_labeled)
115
+ payload["pull_request"]["labels"] = []
116
+
117
+ LabeledHandler.new(payload).process
118
+
119
+ assert_equal stack.reload.provision_status, "deprovisioning"
120
+ end
121
+
122
+ test "ignores Github PullRequest webhooks when the repository allow_with_label to create ReviewStacks and the label is absent" do
123
+ repository = shipit_repositories(:shipit)
124
+ configure_provisioning_behavior(
125
+ repository: repository,
126
+ behavior: :allow_with_label,
127
+ label: "pull-requests-label"
128
+ )
129
+ payload = payload_parsed(:pull_request_labeled)
130
+ payload["pull_request"]["labels"] = []
131
+
132
+ assert_no_difference -> { Shipit::Stack.count } do
133
+ LabeledHandler.new(payload).process
134
+ end
135
+ end
136
+
137
+ test "archives an existing review stack when the repository creates ReviewStacks with prevent_with_label and the label is present" do
138
+ stack = create_stack
139
+ repository = shipit_repositories(:shipit)
140
+ configure_provisioning_behavior(
141
+ repository: repository,
142
+ behavior: :prevent_with_label,
143
+ label: "pull-requests-label"
144
+ )
145
+
146
+ LabeledHandler.new(payload_parsed(:pull_request_labeled)).process
147
+
148
+ assert stack.reload.archived?, "Expected stack to be archived"
149
+ end
150
+
151
+ test "deprovisions an existing review stack when the repository creates ReviewStacks with prevent_with_label and the label is present" do
152
+ stack = create_stack
153
+ repository = shipit_repositories(:shipit)
154
+ configure_provisioning_behavior(
155
+ repository: repository,
156
+ behavior: :prevent_with_label,
157
+ label: "pull-requests-label"
158
+ )
159
+
160
+ LabeledHandler.new(payload_parsed(:pull_request_labeled)).process
161
+
162
+ assert_equal stack.reload.provision_status, "deprovisioning"
163
+ end
164
+
165
+ test "ignores Github PullRequest webhooks when the repository prevent_with_label to create ReviewStacks and the label is present" do
166
+ repository = shipit_repositories(:shipit)
167
+ configure_provisioning_behavior(
168
+ repository: repository,
169
+ behavior: :prevent_with_label,
170
+ label: "pull-requests-label"
171
+ )
172
+
173
+ assert_no_difference -> { Shipit::Stack.count } do
174
+ LabeledHandler.new(payload_parsed(:pull_request_labeled)).process
175
+ end
176
+ end
177
+
178
+ test "unarchives an existing review stack when the repository creates ReviewStacks with prevent_with_label and the label is absent" do
179
+ stack = create_archived_stack
180
+ repository = shipit_repositories(:shipit)
181
+ configure_provisioning_behavior(
182
+ repository: repository,
183
+ behavior: :prevent_with_label,
184
+ label: "pull-requests-label"
185
+ )
186
+ payload = payload_parsed(:pull_request_labeled)
187
+ payload["pull_request"]["labels"] = []
188
+
189
+ LabeledHandler.new(payload).process
190
+
191
+ assert_not stack.reload.archived?, "Expected stack to NOT be archived"
192
+ assert_pending_provision(stack)
193
+ end
194
+
195
+ test "creates and provisions a new review stack when the repository creates ReviewStacks with prevent_with_label and the label is absent" do
196
+ repository = shipit_repositories(:shipit)
197
+ configure_provisioning_behavior(
198
+ repository: repository,
199
+ behavior: :prevent_with_label,
200
+ label: "pull-requests-label"
201
+ )
202
+ payload = payload_parsed(:pull_request_labeled)
203
+ payload["pull_request"]["labels"] = []
204
+
205
+ LabeledHandler.new(payload).process
206
+
207
+ stack = shipit_repositories(:shipit).stacks.last
208
+ assert_equal stack.environment, "pr#{payload['number']}"
209
+ assert_equal stack.continuous_deployment, false
210
+ assert_equal stack.ignore_ci, false
211
+ assert_equal stack.branch, payload["pull_request"]["head"]["ref"]
212
+ assert_not stack.archived?, "Expected stack to be NOT be archived"
213
+ assert_pending_provision(stack)
214
+ end
215
+
216
+ test "assigns the PullRequest to newly created stacks" do
217
+ repository = shipit_repositories(:shipit)
218
+ configure_provisioning_behavior(
219
+ repository: repository,
220
+ behavior: :prevent_with_label,
221
+ label: "pull-requests-label"
222
+ )
223
+ payload = payload_parsed(:pull_request_labeled)
224
+ payload["pull_request"]["labels"] = []
225
+
226
+ assert_difference -> { Shipit::PullRequest.count } do
227
+ LabeledHandler.new(payload).process
228
+ end
229
+ end
230
+
231
+ test "ignores Github Webhooks for closed PullRequests" do
232
+ create_archived_stack
233
+ repository = shipit_repositories(:shipit)
234
+ configure_provisioning_behavior(
235
+ repository: repository,
236
+ behavior: :allow_with_label,
237
+ label: "pull-requests-label"
238
+ )
239
+ payload = payload_parsed(:pull_request_labeled)
240
+ payload["pull_request"]["labels"] << { "name" => "pull-requests-label" }
241
+ payload["pull_request"]["state"] = "closed"
242
+
243
+ Shipit::ReviewStackProvisioningQueue.expects(:add).never
244
+
245
+ LabeledHandler.new(payload).process
246
+ end
247
+
248
+ def configure_provisioning_behavior(repository:, provisioning_enabled: true, behavior: :allow_all, label: nil)
249
+ repository.review_stacks_enabled = provisioning_enabled
250
+ repository.provisioning_behavior = behavior
251
+ repository.provisioning_label_name = label
252
+ repository.save!
253
+
254
+ repository
255
+ end
256
+
257
+ def create_archived_stack
258
+ stack = create_stack
259
+ stack.update(provision_status: :deprovisioned)
260
+ stack.archive!(shipit_users(:codertocat))
261
+
262
+ stack
263
+ end
264
+
265
+ def create_stack
266
+ repository = shipit_repositories(:shipit)
267
+ repository.provisioning_behavior = :allow_all
268
+ repository.save!
269
+
270
+ payload = payload_parsed(:pull_request_labeled)
271
+ payload["action"] = "opened"
272
+
273
+ OpenedHandler.new(payload).process
274
+
275
+ stack = repository.review_stacks.last
276
+ stack.update(provision_status: :provisioned)
277
+ complete_active_tasks(stack)
278
+
279
+ stack
280
+ end
281
+
282
+ def complete_active_tasks(stack)
283
+ active_tasks = stack
284
+ .tasks
285
+ .active
286
+
287
+ active_tasks.map(&:run)
288
+ active_tasks.reload
289
+ active_tasks.map(&:complete)
290
+ end
291
+
292
+ def assert_pending_provision(stack)
293
+ stack.reload
294
+
295
+ assert(stack.awaiting_provision?, "Stack #{stack.environment} should be in the provisioning queue")
296
+ assert(stack.deprovisioned?, "Stack #{stack.environment} should be pending provision")
297
+ end
298
+
299
+ setup do
300
+ Shipit.github.api.stubs(:commit)
301
+ .with("shopify/shipit-engine", "ec26c3e57ca3a959ca5aad62de7213c562f8c821")
302
+ .returns(
303
+ resource(
304
+ {
305
+ sha: "ec26c3e57ca3a959ca5aad62de7213c562f8c821",
306
+ commit: {
307
+ author: {
308
+ name: "Codertocat",
309
+ email: "21031067+Codertocat@users.noreply.github.com",
310
+ date: "2019-05-15 15:20:30",
311
+ },
312
+ committer: {
313
+ name: "Codertocat",
314
+ email: "21031067+Codertocat@users.noreply.github.com",
315
+ date: "2019-05-15 15:20:30",
316
+ },
317
+ message: "Update README.md",
318
+ },
319
+ stats: {
320
+ total: 2,
321
+ additions: 1,
322
+ deletions: 1,
323
+ },
324
+ }
325
+ )
326
+ )
327
+ end
328
+ end
329
+ end
330
+ end
331
+ end
332
+ end