shipit-engine 0.39.0 → 0.40.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 (315) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +40 -1
  3. data/Rakefile +2 -1
  4. data/app/assets/javascripts/shipit/continuous_delivery_schedule.js.coffee +15 -0
  5. data/app/controllers/concerns/shipit/active_model_serializers_patch.rb +1 -0
  6. data/app/controllers/concerns/shipit/api/cacheable.rb +1 -0
  7. data/app/controllers/concerns/shipit/api/paginable.rb +3 -2
  8. data/app/controllers/concerns/shipit/api/rendering.rb +1 -0
  9. data/app/controllers/concerns/shipit/authentication.rb +1 -0
  10. data/app/controllers/concerns/shipit/pagination.rb +3 -2
  11. data/app/controllers/shipit/api/base_controller.rb +10 -8
  12. data/app/controllers/shipit/api/ccmenu_controller.rb +2 -1
  13. data/app/controllers/shipit/api/commits_controller.rb +2 -3
  14. data/app/controllers/shipit/api/deploys_controller.rb +2 -1
  15. data/app/controllers/shipit/api/hooks_controller.rb +4 -3
  16. data/app/controllers/shipit/api/locks_controller.rb +1 -0
  17. data/app/controllers/shipit/api/merge_requests_controller.rb +6 -5
  18. data/app/controllers/shipit/api/outputs_controller.rb +1 -0
  19. data/app/controllers/shipit/api/release_statuses_controller.rb +2 -1
  20. data/app/controllers/shipit/api/rollbacks_controller.rb +1 -0
  21. data/app/controllers/shipit/api/stacks_controller.rb +15 -14
  22. data/app/controllers/shipit/api/tasks_controller.rb +6 -5
  23. data/app/controllers/shipit/api_clients_controller.rb +6 -7
  24. data/app/controllers/shipit/ccmenu_url_controller.rb +3 -2
  25. data/app/controllers/shipit/commit_checks_controller.rb +2 -1
  26. data/app/controllers/shipit/commits_controller.rb +1 -0
  27. data/app/controllers/shipit/continuous_delivery_schedules_controller.rb +42 -0
  28. data/app/controllers/shipit/deploys_controller.rb +6 -5
  29. data/app/controllers/shipit/github_authentication_controller.rb +6 -0
  30. data/app/controllers/shipit/merge_requests_controller.rb +1 -0
  31. data/app/controllers/shipit/merge_status_controller.rb +30 -26
  32. data/app/controllers/shipit/release_statuses_controller.rb +1 -0
  33. data/app/controllers/shipit/repositories_controller.rb +4 -7
  34. data/app/controllers/shipit/rollbacks_controller.rb +2 -1
  35. data/app/controllers/shipit/shipit_controller.rb +1 -0
  36. data/app/controllers/shipit/stacks_controller.rb +27 -31
  37. data/app/controllers/shipit/status_controller.rb +1 -0
  38. data/app/controllers/shipit/tasks_controller.rb +3 -1
  39. data/app/controllers/shipit/webhooks_controller.rb +2 -1
  40. data/app/helpers/shipit/api_clients_helper.rb +1 -0
  41. data/app/helpers/shipit/chunks_helper.rb +3 -1
  42. data/app/helpers/shipit/deploys_helper.rb +7 -3
  43. data/app/helpers/shipit/github_url_helper.rb +5 -4
  44. data/app/helpers/shipit/merge_status_helper.rb +1 -0
  45. data/app/helpers/shipit/shipit_helper.rb +11 -10
  46. data/app/helpers/shipit/stacks_helper.rb +10 -11
  47. data/app/helpers/shipit/tasks_helper.rb +2 -1
  48. data/app/jobs/shipit/background_job/unique.rb +3 -2
  49. data/app/jobs/shipit/background_job.rb +9 -1
  50. data/app/jobs/shipit/cache_deploy_spec_job.rb +2 -1
  51. data/app/jobs/shipit/chunk_rollup_job.rb +1 -0
  52. data/app/jobs/shipit/clear_git_cache_job.rb +1 -0
  53. data/app/jobs/shipit/continuous_delivery_job.rb +5 -0
  54. data/app/jobs/shipit/create_on_github_job.rb +1 -0
  55. data/app/jobs/shipit/create_release_statuses_job.rb +2 -0
  56. data/app/jobs/shipit/deferred_touch_job.rb +1 -0
  57. data/app/jobs/shipit/deliver_hook_job.rb +1 -0
  58. data/app/jobs/shipit/destroy_job.rb +1 -0
  59. data/app/jobs/shipit/destroy_repository_job.rb +1 -0
  60. data/app/jobs/shipit/destroy_stack_job.rb +36 -15
  61. data/app/jobs/shipit/emit_event_job.rb +1 -0
  62. data/app/jobs/shipit/fetch_commit_stats_job.rb +1 -0
  63. data/app/jobs/shipit/fetch_deployed_revision_job.rb +1 -0
  64. data/app/jobs/shipit/github_sync_job.rb +4 -2
  65. data/app/jobs/shipit/mark_deploy_healthy_job.rb +1 -0
  66. data/app/jobs/shipit/perform_commit_checks_job.rb +1 -0
  67. data/app/jobs/shipit/perform_task_job.rb +1 -0
  68. data/app/jobs/shipit/process_merge_requests_job.rb +2 -0
  69. data/app/jobs/shipit/purge_old_deliveries_job.rb +1 -0
  70. data/app/jobs/shipit/reap_dead_tasks_job.rb +1 -0
  71. data/app/jobs/shipit/refresh_check_runs_job.rb +1 -0
  72. data/app/jobs/shipit/refresh_github_user_job.rb +1 -0
  73. data/app/jobs/shipit/refresh_merge_request_job.rb +1 -0
  74. data/app/jobs/shipit/refresh_statuses_job.rb +1 -0
  75. data/app/jobs/shipit/setup_github_hook_job.rb +1 -0
  76. data/app/jobs/shipit/update_estimated_deploy_duration_job.rb +1 -0
  77. data/app/jobs/shipit/update_github_last_deployed_ref_job.rb +6 -7
  78. data/app/models/concerns/shipit/deferred_touch.rb +5 -2
  79. data/app/models/shipit/anonymous_user.rb +4 -5
  80. data/app/models/shipit/api_client.rb +4 -2
  81. data/app/models/shipit/application_record.rb +1 -0
  82. data/app/models/shipit/check_run.rb +7 -6
  83. data/app/models/shipit/command_line_user.rb +4 -5
  84. data/app/models/shipit/commit.rb +46 -32
  85. data/app/models/shipit/commit_checks.rb +4 -2
  86. data/app/models/shipit/commit_deployment.rb +7 -5
  87. data/app/models/shipit/commit_deployment_status.rb +5 -2
  88. data/app/models/shipit/commit_message.rb +2 -0
  89. data/app/models/shipit/continuous_delivery_schedule.rb +84 -0
  90. data/app/models/shipit/delivery.rb +4 -3
  91. data/app/models/shipit/deploy.rb +46 -26
  92. data/app/models/shipit/deploy_spec/bundler_discovery.rb +3 -1
  93. data/app/models/shipit/deploy_spec/capistrano_discovery.rb +1 -0
  94. data/app/models/shipit/deploy_spec/file_system.rb +35 -16
  95. data/app/models/shipit/deploy_spec/kubernetes_discovery.rb +4 -3
  96. data/app/models/shipit/deploy_spec/lerna_discovery.rb +32 -31
  97. data/app/models/shipit/deploy_spec/npm_discovery.rb +18 -13
  98. data/app/models/shipit/deploy_spec/pypi_discovery.rb +5 -4
  99. data/app/models/shipit/deploy_spec/rubygems_discovery.rb +1 -0
  100. data/app/models/shipit/deploy_spec.rb +25 -30
  101. data/app/models/shipit/deploy_stats.rb +6 -1
  102. data/app/models/shipit/duration.rb +5 -3
  103. data/app/models/shipit/ephemeral_commit_checks.rb +8 -7
  104. data/app/models/shipit/github_hook.rb +1 -0
  105. data/app/models/shipit/github_status.rb +1 -0
  106. data/app/models/shipit/hook.rb +8 -6
  107. data/app/models/shipit/membership.rb +1 -0
  108. data/app/models/shipit/merge_request.rb +26 -16
  109. data/app/models/shipit/output_chunk.rb +1 -0
  110. data/app/models/shipit/provisioning_handler.rb +1 -0
  111. data/app/models/shipit/pull_request.rb +1 -1
  112. data/app/models/shipit/record.rb +1 -0
  113. data/app/models/shipit/release_status.rb +4 -3
  114. data/app/models/shipit/repository.rb +12 -11
  115. data/app/models/shipit/review_stack.rb +3 -1
  116. data/app/models/shipit/review_stack_provisioning_queue.rb +2 -2
  117. data/app/models/shipit/rollback.rb +2 -0
  118. data/app/models/shipit/stack.rb +59 -56
  119. data/app/models/shipit/status/common.rb +1 -0
  120. data/app/models/shipit/status/group.rb +5 -3
  121. data/app/models/shipit/status/missing.rb +2 -1
  122. data/app/models/shipit/status/unknown.rb +1 -0
  123. data/app/models/shipit/status.rb +5 -4
  124. data/app/models/shipit/task.rb +33 -28
  125. data/app/models/shipit/task_definition.rb +10 -7
  126. data/app/models/shipit/task_execution_strategy/default.rb +13 -13
  127. data/app/models/shipit/team.rb +13 -12
  128. data/app/models/shipit/undeployed_commit.rb +8 -3
  129. data/app/models/shipit/unlimited_api_client.rb +2 -2
  130. data/app/models/shipit/user.rb +21 -16
  131. data/app/models/shipit/variable_definition.rb +2 -1
  132. data/app/models/shipit/webhooks/handlers/check_suite_handler.rb +1 -0
  133. data/app/models/shipit/webhooks/handlers/handler.rb +1 -0
  134. data/app/models/shipit/webhooks/handlers/membership_handler.rb +1 -0
  135. data/app/models/shipit/webhooks/handlers/pull_request/assigned_handler.rb +10 -10
  136. data/app/models/shipit/webhooks/handlers/pull_request/closed_handler.rb +1 -1
  137. data/app/models/shipit/webhooks/handlers/pull_request/edited_handler.rb +10 -10
  138. data/app/models/shipit/webhooks/handlers/pull_request/label_capturing_handler.rb +2 -2
  139. data/app/models/shipit/webhooks/handlers/pull_request/labeled_handler.rb +2 -2
  140. data/app/models/shipit/webhooks/handlers/pull_request/reopened_handler.rb +1 -1
  141. data/app/models/shipit/webhooks/handlers/pull_request/review_stack_adapter.rb +3 -3
  142. data/app/models/shipit/webhooks/handlers/pull_request/unlabeled_handler.rb +1 -1
  143. data/app/models/shipit/webhooks/handlers/push_handler.rb +2 -1
  144. data/app/models/shipit/webhooks/handlers/status_handler.rb +1 -0
  145. data/app/models/shipit/webhooks.rb +3 -2
  146. data/app/serializers/concerns/shipit/conditional_attributes.rb +1 -0
  147. data/app/serializers/shipit/anonymous_user_serializer.rb +1 -0
  148. data/app/serializers/shipit/command_line_user_serializer.rb +1 -0
  149. data/app/serializers/shipit/commit_serializer.rb +2 -1
  150. data/app/serializers/shipit/deploy_serializer.rb +1 -0
  151. data/app/serializers/shipit/hook_serializer.rb +1 -0
  152. data/app/serializers/shipit/merge_request_serializer.rb +2 -1
  153. data/app/serializers/shipit/rollback_serializer.rb +1 -0
  154. data/app/serializers/shipit/short_commit_serializer.rb +1 -0
  155. data/app/serializers/shipit/stack_serializer.rb +4 -3
  156. data/app/serializers/shipit/tail_task_serializer.rb +4 -1
  157. data/app/serializers/shipit/task_serializer.rb +1 -0
  158. data/app/serializers/shipit/user_serializer.rb +1 -0
  159. data/app/validators/ascii_only_validator.rb +4 -3
  160. data/app/validators/subset_validator.rb +1 -0
  161. data/app/views/shipit/ccmenu/project.xml.builder +2 -1
  162. data/app/views/shipit/continuous_delivery_schedules/show.html.erb +59 -0
  163. data/app/views/shipit/stacks/_settings_form.erb +1 -0
  164. data/config/initializers/inflections.rb +1 -0
  165. data/config/locales/en.yml +1 -0
  166. data/config/routes.rb +21 -18
  167. data/db/migrate/20240821003007_add_continuous_delivery_schedules.rb +13 -0
  168. data/db/migrate/20250207203053_embiggen_github_ids.rb +8 -0
  169. data/lib/shipit/cast_value.rb +1 -0
  170. data/lib/shipit/command.rb +29 -9
  171. data/lib/shipit/commands.rb +4 -2
  172. data/lib/shipit/csv_serializer.rb +3 -0
  173. data/lib/shipit/deploy_commands.rb +2 -1
  174. data/lib/shipit/engine.rb +5 -4
  175. data/lib/shipit/environment_variables.rb +2 -0
  176. data/lib/shipit/first_parent_commits_iterator.rb +2 -3
  177. data/lib/shipit/flock.rb +11 -9
  178. data/lib/shipit/github_app.rb +14 -15
  179. data/lib/shipit/github_http_cache_middleware.rb +1 -0
  180. data/lib/shipit/null_serializer.rb +1 -0
  181. data/lib/shipit/octokit_check_runs.rb +1 -0
  182. data/lib/shipit/octokit_iterator.rb +2 -0
  183. data/lib/shipit/paginator.rb +1 -0
  184. data/lib/shipit/rollback_commands.rb +2 -1
  185. data/lib/shipit/same_site_cookie_middleware.rb +1 -0
  186. data/lib/shipit/simple_message_verifier.rb +1 -0
  187. data/lib/shipit/stack_commands.rb +34 -26
  188. data/lib/shipit/stat.rb +1 -0
  189. data/lib/shipit/task_commands.rb +7 -6
  190. data/lib/shipit/version.rb +2 -1
  191. data/lib/shipit.rb +29 -16
  192. data/lib/tasks/cron.rake +2 -1
  193. data/lib/tasks/dev.rake +3 -2
  194. data/lib/tasks/shipit.rake +3 -2
  195. data/lib/tasks/teams.rake +3 -2
  196. data/test/controllers/api/base_controller_test.rb +1 -0
  197. data/test/controllers/api/ccmenu_controller_test.rb +4 -3
  198. data/test/controllers/api/commits_controller_test.rb +1 -0
  199. data/test/controllers/api/deploys_controller_test.rb +2 -1
  200. data/test/controllers/api/hooks_controller_test.rb +6 -5
  201. data/test/controllers/api/locks_controller_test.rb +1 -0
  202. data/test/controllers/api/merge_requests_controller_test.rb +1 -0
  203. data/test/controllers/api/outputs_controller_test.rb +1 -0
  204. data/test/controllers/api/release_statuses_controller_test.rb +4 -3
  205. data/test/controllers/api/rollback_controller_test.rb +3 -2
  206. data/test/controllers/api/stacks_controller_test.rb +13 -12
  207. data/test/controllers/api/tasks_controller_test.rb +7 -6
  208. data/test/controllers/api_clients_controller_test.rb +10 -10
  209. data/test/controllers/ccmenu_controller_test.rb +1 -0
  210. data/test/controllers/commit_checks_controller_test.rb +1 -0
  211. data/test/controllers/commits_controller_test.rb +9 -8
  212. data/test/controllers/continuous_delivery_schedules_controller_test.rb +66 -0
  213. data/test/controllers/deploys_controller_test.rb +4 -2
  214. data/test/controllers/github_authentication_controller_test.rb +6 -4
  215. data/test/controllers/merge_requests_controller_test.rb +1 -0
  216. data/test/controllers/merge_status_controller_test.rb +5 -4
  217. data/test/controllers/release_statuses_controller_test.rb +1 -0
  218. data/test/controllers/repositories_controller_test.rb +6 -5
  219. data/test/controllers/rollbacks_controller_test.rb +3 -2
  220. data/test/controllers/stacks_controller_test.rb +7 -5
  221. data/test/controllers/status_controller_test.rb +1 -0
  222. data/test/controllers/tasks_controller_test.rb +5 -4
  223. data/test/controllers/webhooks_controller_test.rb +10 -9
  224. data/test/dummy/config/application.rb +1 -1
  225. data/test/dummy/db/schema.rb +33 -6
  226. data/test/fixtures/shipit/commits.yml +7 -7
  227. data/test/fixtures/shipit/stacks.yml +4 -10
  228. data/test/fixtures/shipit/tasks.yml +3 -3
  229. data/test/helpers/api_helper.rb +2 -3
  230. data/test/helpers/fixture_aliases_helper.rb +1 -0
  231. data/test/helpers/hooks_helper.rb +1 -0
  232. data/test/helpers/json_helper.rb +4 -3
  233. data/test/helpers/links_helper.rb +2 -1
  234. data/test/helpers/payloads_helper.rb +1 -0
  235. data/test/helpers/queries_helper.rb +4 -3
  236. data/test/jobs/cache_deploy_spec_job_test.rb +3 -2
  237. data/test/jobs/chunk_rollup_job_test.rb +3 -2
  238. data/test/jobs/deliver_hook_job_test.rb +1 -0
  239. data/test/jobs/destroy_repository_job_test.rb +1 -0
  240. data/test/jobs/destroy_stack_job_test.rb +12 -0
  241. data/test/jobs/emit_event_job_test.rb +1 -0
  242. data/test/jobs/fetch_commit_stats_job_test.rb +1 -0
  243. data/test/jobs/fetch_deployed_revision_job_test.rb +1 -0
  244. data/test/jobs/github_sync_job_test.rb +22 -21
  245. data/test/jobs/mark_deploy_healthy_job_test.rb +1 -0
  246. data/test/jobs/perform_task_job_test.rb +3 -3
  247. data/test/jobs/process_merge_requests_job_test.rb +7 -6
  248. data/test/jobs/purge_old_deliveries_job_test.rb +1 -0
  249. data/test/jobs/reap_dead_tasks_job_test.rb +1 -0
  250. data/test/jobs/refresh_github_user_job_test.rb +1 -0
  251. data/test/jobs/refresh_status_job_test.rb +1 -0
  252. data/test/jobs/shipit/background_job_test.rb +35 -0
  253. data/test/jobs/shipit/continuous_delivery_job_test.rb +31 -0
  254. data/test/jobs/unique_job_test.rb +3 -1
  255. data/test/jobs/update_github_last_deployed_ref_job_test.rb +1 -0
  256. data/test/middleware/same_site_cookie_middleware_test.rb +2 -2
  257. data/test/models/api_client_test.rb +1 -0
  258. data/test/models/commit_checks_test.rb +2 -1
  259. data/test/models/commit_deployment_status_test.rb +2 -1
  260. data/test/models/commit_deployment_test.rb +4 -3
  261. data/test/models/commits_test.rb +72 -70
  262. data/test/models/delivery_test.rb +3 -2
  263. data/test/models/deploy_spec_test.rb +113 -109
  264. data/test/models/deploy_stats_test.rb +1 -0
  265. data/test/models/deploys_test.rb +65 -56
  266. data/test/models/duration_test.rb +1 -1
  267. data/test/models/github_hook_test.rb +1 -0
  268. data/test/models/hook_test.rb +7 -4
  269. data/test/models/membership_test.rb +1 -0
  270. data/test/models/merge_request_test.rb +23 -20
  271. data/test/models/release_statuses_test.rb +2 -1
  272. data/test/models/rollbacks_test.rb +4 -3
  273. data/test/models/shipit/check_run_test.rb +16 -15
  274. data/test/models/shipit/continuous_delivery_schedule_test.rb +109 -0
  275. data/test/models/shipit/deploy_spec/file_system_test.rb +54 -10
  276. data/test/models/shipit/pull_request_test.rb +9 -9
  277. data/test/models/shipit/repository_test.rb +3 -2
  278. data/test/models/shipit/review_stack_provisioning_queue_test.rb +2 -2
  279. data/test/models/shipit/stack_test.rb +30 -29
  280. data/test/models/shipit/webhooks/handlers/pull_request/closed_handler_test.rb +36 -34
  281. data/test/models/shipit/webhooks/handlers/pull_request/label_capturing_handler_test.rb +28 -28
  282. data/test/models/shipit/webhooks/handlers/pull_request/labeled_handler_test.rb +42 -42
  283. data/test/models/shipit/webhooks/handlers/pull_request/opened_handler_test.rb +33 -33
  284. data/test/models/shipit/webhooks/handlers/pull_request/reopened_handler_test.rb +37 -37
  285. data/test/models/shipit/webhooks/handlers/pull_request/review_stack_adapter_test.rb +1 -1
  286. data/test/models/shipit/webhooks/handlers/pull_request/unlabeled_handler_test.rb +44 -42
  287. data/test/models/shipit/webhooks/handlers_test.rb +1 -0
  288. data/test/models/status/group_test.rb +3 -2
  289. data/test/models/status/missing_test.rb +1 -0
  290. data/test/models/status_test.rb +2 -1
  291. data/test/models/task_definitions_test.rb +7 -6
  292. data/test/models/tasks_test.rb +5 -4
  293. data/test/models/team_test.rb +5 -4
  294. data/test/models/undeployed_commits_test.rb +10 -9
  295. data/test/models/users_test.rb +21 -20
  296. data/test/test_command_integration.rb +1 -1
  297. data/test/test_helper.rb +11 -9
  298. data/test/unit/anonymous_user_serializer_test.rb +1 -0
  299. data/test/unit/command_test.rb +10 -1
  300. data/test/unit/commands_test.rb +1 -0
  301. data/test/unit/commit_serializer_test.rb +1 -0
  302. data/test/unit/csv_serializer_test.rb +3 -2
  303. data/test/unit/deploy_commands_test.rb +33 -23
  304. data/test/unit/deploy_serializer_test.rb +1 -0
  305. data/test/unit/environment_variables_test.rb +2 -1
  306. data/test/unit/github_app_test.rb +10 -9
  307. data/test/unit/github_apps_test.rb +19 -18
  308. data/test/unit/github_url_helper_test.rb +1 -0
  309. data/test/unit/line_buffer_test.rb +1 -1
  310. data/test/unit/rollback_commands_test.rb +2 -1
  311. data/test/unit/shipit_helper_test.rb +1 -0
  312. data/test/unit/shipit_test.rb +47 -1
  313. data/test/unit/user_serializer_test.rb +1 -0
  314. data/test/unit/variable_definition_test.rb +4 -3
  315. metadata +53 -43
@@ -1,13 +1,14 @@
1
1
  # frozen_string_literal: true
2
+
2
3
  module Shipit
3
4
  class MergeRequest < ApplicationRecord
4
5
  include DeferredTouch
5
6
 
6
7
  MERGE_REQUEST_FIELD = 'Merge-Requested-By'
7
8
 
8
- WAITING_STATUSES = %w(fetching pending).freeze
9
- QUEUED_STATUSES = %w(pending revalidating).freeze
10
- REJECTION_REASONS = %w(ci_missing ci_failing merge_conflict requires_rebase).freeze
9
+ WAITING_STATUSES = %w[fetching pending].freeze
10
+ QUEUED_STATUSES = %w[pending revalidating].freeze
11
+ REJECTION_REASONS = %w[ci_missing ci_failing merge_conflict requires_rebase].freeze
11
12
  InvalidTransition = Class.new(StandardError)
12
13
  NotReady = Class.new(StandardError)
13
14
 
@@ -85,14 +86,14 @@ module Shipit
85
86
  end
86
87
 
87
88
  event :retry do
88
- transition %i(rejected canceled revalidating) => :pending
89
+ transition %i[rejected canceled revalidating] => :pending
89
90
  end
90
91
 
91
92
  before_transition rejected: any do |pr|
92
93
  pr.rejection_reason = nil
93
94
  end
94
95
 
95
- before_transition %i(fetching rejected canceled) => :pending do |pr|
96
+ before_transition %i[fetching rejected canceled] => :pending do |pr|
96
97
  pr.merge_requested_at = Time.now.utc
97
98
  end
98
99
 
@@ -100,7 +101,7 @@ module Shipit
100
101
  pr.revalidated_at = Time.now.utc
101
102
  end
102
103
 
103
- before_transition %i(pending) => :merged do |pr|
104
+ before_transition %i[pending] => :merged do |pr|
104
105
  Stack.increment_counter(:undeployed_commits_count, pr.stack_id)
105
106
  end
106
107
  end
@@ -117,6 +118,7 @@ module Shipit
117
118
  when %r{\Ahttps://#{Regexp.escape(Shipit.github(organization: org).domain)}/([^/]+)/([^/]+)/pull/(\d+)}
118
119
  return unless $1.downcase == stack.repo_owner.downcase
119
120
  return unless $2.downcase == stack.repo_name.downcase
121
+
120
122
  $3.to_i
121
123
  end
122
124
  end
@@ -126,10 +128,10 @@ module Shipit
126
128
  merge_request = begin
127
129
  create_with(
128
130
  merge_requested_at: now,
129
- merge_requested_by: user.presence,
131
+ merge_requested_by: user.presence
130
132
  ).find_or_create_by!(
131
- stack: stack,
132
- number: number,
133
+ stack:,
134
+ number:
133
135
  )
134
136
  rescue ActiveRecord::RecordNotUnique
135
137
  retry
@@ -144,6 +146,7 @@ module Shipit
144
146
  unless REJECTION_REASONS.include?(reason)
145
147
  raise ArgumentError, "invalid reason: #{reason.inspect}, must be one of: #{REJECTION_REASONS.inspect}"
146
148
  end
149
+
147
150
  self.rejection_reason = reason.presence
148
151
  super()
149
152
  true
@@ -154,6 +157,7 @@ module Shipit
154
157
  return reject!('ci_missing') if any_status_checks_missing?
155
158
  return reject!('ci_failing') if any_status_checks_failed?
156
159
  return reject!('requires_rebase') if stale?
160
+
157
161
  false
158
162
  end
159
163
 
@@ -168,7 +172,7 @@ module Shipit
168
172
  merge_message,
169
173
  sha: head.sha,
170
174
  commit_message: 'Merged by Shipit',
171
- merge_method: stack.merge_method,
175
+ merge_method: stack.merge_method
172
176
  )
173
177
  begin
174
178
  if stack.github_api.pull_requests(stack.github_repo_name, base: branch).empty?
@@ -188,6 +192,7 @@ module Shipit
188
192
 
189
193
  def all_status_checks_passed?
190
194
  return false unless head
195
+
191
196
  StatusChecker.new(head, head.statuses_and_check_runs, stack.cached_deploy_spec).success?
192
197
  end
193
198
 
@@ -207,6 +212,7 @@ module Shipit
207
212
  def need_revalidation?
208
213
  timeout = stack.cached_deploy_spec&.revalidate_merge_requests_after
209
214
  return false unless timeout
215
+
210
216
  (revalidated_at + timeout).past?
211
217
  end
212
218
 
@@ -255,18 +261,21 @@ module Shipit
255
261
 
256
262
  def merge_message
257
263
  return title unless merge_requested_by
264
+
258
265
  "#{title}\n\n#{MERGE_REQUEST_FIELD}: #{merge_requested_by.login}\n"
259
266
  end
260
267
 
261
268
  def stale?
262
269
  return false unless base_commit
270
+
263
271
  spec = stack.cached_deploy_spec
264
- if max_branch_age = spec.max_divergence_age
265
- return true if Time.now.utc - head.committed_at > max_branch_age
272
+ if (max_branch_age = spec.max_divergence_age) && (Time.now.utc - head.committed_at > max_branch_age)
273
+ return true
266
274
  end
267
- if commit_count_limit = spec.max_divergence_commits
268
- return true if comparison.behind_by > commit_count_limit
275
+ if (commit_count_limit = spec.max_divergence_commits) && (comparison.behind_by > commit_count_limit)
276
+ return true
269
277
  end
278
+
270
279
  false
271
280
  end
272
281
 
@@ -274,7 +283,7 @@ module Shipit
274
283
  @comparison ||= stack.github_api.compare(
275
284
  stack.github_repo_name,
276
285
  base_ref,
277
- head.sha,
286
+ head.sha
278
287
  )
279
288
  end
280
289
 
@@ -286,8 +295,9 @@ module Shipit
286
295
 
287
296
  def emit_hooks
288
297
  return unless @merge_status_changed
298
+
289
299
  @merge_status_changed = nil
290
- Hook.emit('merge', stack, merge_request: self, status: merge_status, stack: stack)
300
+ Hook.emit('merge', stack, merge_request: self, status: merge_status, stack:)
291
301
  end
292
302
 
293
303
  def find_or_create_commit_from_github_by_sha!(sha, attributes)
@@ -1,4 +1,5 @@
1
1
  # frozen_string_literal: true
2
+
2
3
  module Shipit
3
4
  class OutputChunk < Record
4
5
  belongs_to :task
@@ -17,6 +17,7 @@ module Shipit
17
17
 
18
18
  def fetch(name)
19
19
  return default if name.blank?
20
+
20
21
  registry.fetch(name) { ProvisioningHandler::UnregisteredProvisioningHandler }
21
22
  end
22
23
 
@@ -30,7 +30,7 @@ module Shipit
30
30
  end
31
31
 
32
32
  def emit_hooks(reason)
33
- Hook.emit('pull_request', stack, action: reason, pull_request: self, stack: stack)
33
+ Hook.emit('pull_request', stack, action: reason, pull_request: self, stack:)
34
34
  end
35
35
 
36
36
  def github_pull_request=(github_pull_request)
@@ -1,4 +1,5 @@
1
1
  # frozen_string_literal: true
2
+
2
3
  module Shipit
3
4
  class Record < ActiveRecord::Base
4
5
  self.abstract_class = true
@@ -1,4 +1,5 @@
1
1
  # frozen_string_literal: true
2
+
2
3
  module Shipit
3
4
  class ReleaseStatus < Record
4
5
  MAX_DESCRIPTION_LENGTH = 140
@@ -13,7 +14,7 @@ module Shipit
13
14
 
14
15
  scope :to_be_created, -> { where(github_id: nil).order(id: :asc) }
15
16
 
16
- STATES = %w(pending success failure error).freeze
17
+ STATES = %w[pending success failure error].freeze
17
18
  validates :state, presence: true, inclusion: { in: STATES }
18
19
 
19
20
  def create_status_on_github!
@@ -30,8 +31,8 @@ module Shipit
30
31
  commit.sha,
31
32
  state,
32
33
  context: stack.release_status_context,
33
- target_url: target_url,
34
- description: description&.truncate(MAX_DESCRIPTION_LENGTH),
34
+ target_url:,
35
+ description: description&.truncate(MAX_DESCRIPTION_LENGTH)
35
36
  )
36
37
  end
37
38
 
@@ -1,4 +1,5 @@
1
1
  # frozen_string_literal: true
2
+
2
3
  module Shipit
3
4
  class NullRepository
4
5
  def id
@@ -37,29 +38,29 @@ module Shipit
37
38
  NAME_MAX_SIZE = 100
38
39
  private_constant :NAME_MAX_SIZE
39
40
 
40
- validates :name, uniqueness: { scope: %i(owner), case_sensitive: false,
41
- message: 'cannot be used more than once', }
41
+ validates :name, uniqueness: { scope: %i[owner], case_sensitive: false,
42
+ message: 'cannot be used more than once' }
42
43
  validates :owner, :name, presence: true, ascii_only: true
43
- validates :owner, format: { with: /\A[a-z0-9_\-\.]+\z/ }, length: { maximum: OWNER_MAX_SIZE }
44
- validates :name, format: { with: /\A[a-z0-9_\-\.]+\z/ }, length: { maximum: NAME_MAX_SIZE }
44
+ validates :owner, format: { with: /\A[a-z0-9_\-.]+\z/ }, length: { maximum: OWNER_MAX_SIZE }
45
+ validates :name, format: { with: /\A[a-z0-9_\-.]+\z/ }, length: { maximum: NAME_MAX_SIZE }
45
46
 
46
47
  has_many :stacks, dependent: :destroy
47
48
  has_many :review_stacks, dependent: :destroy
48
49
 
49
- PROVISIONING_BEHAVIORS = %w(allow_all allow_with_label prevent_with_label).freeze
50
- enum provisioning_behavior: PROVISIONING_BEHAVIORS.zip(PROVISIONING_BEHAVIORS).to_h, _prefix: :provisioning_behavior
50
+ PROVISIONING_BEHAVIORS = %w[allow_all allow_with_label prevent_with_label].freeze
51
+ enum :provisioning_behavior, PROVISIONING_BEHAVIORS.zip(PROVISIONING_BEHAVIORS).to_h, prefix: :provisioning_behavior
51
52
 
52
53
  def self.from_github_repo_name(github_repo_name)
53
54
  repo_owner, repo_name = github_repo_name.downcase.split('/')
54
55
  find_by(owner: repo_owner, name: repo_name)
55
56
  end
56
57
 
57
- def name=(n)
58
- super(n&.downcase)
58
+ def name=(name_value)
59
+ super(name_value&.downcase)
59
60
  end
60
61
 
61
- def owner=(o)
62
- super(o&.downcase)
62
+ def owner=(owner_value)
63
+ super(owner_value&.downcase)
63
64
  end
64
65
 
65
66
  def github_repo_name
@@ -90,7 +91,7 @@ module Shipit
90
91
  repo_owner, repo_name = param.split('/')
91
92
  where(
92
93
  owner: repo_owner.downcase,
93
- name: repo_name.downcase,
94
+ name: repo_name.downcase
94
95
  ).first!
95
96
  end
96
97
 
@@ -102,11 +102,13 @@ module Shipit
102
102
 
103
103
  def enqueue_for_provisioning
104
104
  return if awaiting_provision
105
+
105
106
  update!(awaiting_provision: true)
106
107
  end
107
108
 
108
109
  def remove_from_provisioning_queue
109
110
  return unless awaiting_provision
111
+
110
112
  update!(awaiting_provision: false)
111
113
  end
112
114
 
@@ -119,7 +121,7 @@ module Shipit
119
121
  end
120
122
 
121
123
  def emit_updated_hooks
122
- changed = !(previous_changes.keys - %w(updated_at)).empty?
124
+ changed = !(previous_changes.keys - %w[updated_at]).empty?
123
125
  Hook.emit(:review_stack, self, action: :updated, review_stack: self) if changed
124
126
  end
125
127
 
@@ -20,8 +20,8 @@ module Shipit
20
20
 
21
21
  def queued_stacks
22
22
  @queued_stacks ||= Shipit::ReviewStack
23
- .with_provision_status(:deprovisioned)
24
- .where(awaiting_provision: true)
23
+ .with_provision_status(:deprovisioned)
24
+ .where(awaiting_provision: true)
25
25
  end
26
26
 
27
27
  private
@@ -1,4 +1,5 @@
1
1
  # frozen_string_literal: true
2
+
2
3
  module Shipit
3
4
  class Rollback < Deploy
4
5
  belongs_to :deploy, foreign_key: :parent_id, inverse_of: false
@@ -45,6 +46,7 @@ module Shipit
45
46
  # When we rollback to a certain revision, assume that all later deploys were faulty
46
47
  stack.deploys.newer_than(deploy.id).until(stack.last_completed_deploy.id).to_a.each do |deploy|
47
48
  next if deploy.id == id
49
+
48
50
  deploy.report_faulty!(description: "A rollback of #{stack.to_param} was triggered")
49
51
  end
50
52
  end
@@ -1,4 +1,5 @@
1
1
  # frozen_string_literal: true
2
+
2
3
  require 'fileutils'
3
4
 
4
5
  module Shipit
@@ -24,7 +25,7 @@ module Shipit
24
25
  end
25
26
 
26
27
  ENVIRONMENT_MAX_SIZE = 50
27
- REQUIRED_HOOKS = %i(push status).freeze
28
+ REQUIRED_HOOKS = %i[push status].freeze
28
29
 
29
30
  has_many :commits, dependent: :destroy
30
31
  has_many :merge_requests, dependent: :destroy
@@ -32,12 +33,13 @@ module Shipit
32
33
  has_many :deploys
33
34
  has_many :rollbacks
34
35
  has_many :deploys_and_rollbacks,
35
- -> { where(type: %w(Shipit::Deploy Shipit::Rollback)) },
36
- class_name: 'Task',
37
- inverse_of: :stack
36
+ -> { where(type: %w[Shipit::Deploy Shipit::Rollback]) },
37
+ class_name: 'Task',
38
+ inverse_of: :stack
38
39
  has_many :github_hooks, dependent: :destroy, class_name: 'Shipit::GithubHook::Repo'
39
40
  has_many :hooks, dependent: :destroy
40
41
  has_many :api_clients, dependent: :destroy
42
+ has_one :continuous_delivery_schedule, dependent: :destroy
41
43
  belongs_to :lock_author, class_name: :User, optional: true
42
44
  belongs_to :repository
43
45
  validates_associated :repository
@@ -56,7 +58,7 @@ module Shipit
56
58
  'GITHUB_REPO_OWNER' => repository.owner,
57
59
  'GITHUB_REPO_NAME' => repository.name,
58
60
  'DEPLOY_URL' => deploy_url,
59
- 'BRANCH' => branch,
61
+ 'BRANCH' => branch
60
62
  }
61
63
  end
62
64
 
@@ -86,17 +88,17 @@ module Shipit
86
88
  after_commit :sync_github_if_necessary, on: :update
87
89
 
88
90
  def sync_github_if_necessary
89
- if (archived_since_previously_changed? && archived_since.nil?) || branch_previously_changed?
90
- sync_github
91
- end
91
+ return unless (archived_since_previously_changed? && archived_since.nil?) || branch_previously_changed?
92
+
93
+ sync_github
92
94
  end
93
95
 
94
96
  validates :repository, uniqueness: {
95
- scope: %i(environment), case_sensitive: false,
96
- message: 'cannot be used more than once with this environment. Check archived stacks.',
97
+ scope: %i[environment], case_sensitive: false,
98
+ message: 'cannot be used more than once with this environment. Check archived stacks.'
97
99
  }
98
- validates :environment, format: { with: /\A[a-z0-9\-_\:]+\z/ }, length: { maximum: ENVIRONMENT_MAX_SIZE }
99
- validates :deploy_url, format: { with: URI.regexp(%w(http https ssh)) }, allow_blank: true
100
+ validates :environment, format: { with: /\A[a-z0-9\-_:]+\z/ }, length: { maximum: ENVIRONMENT_MAX_SIZE }
101
+ validates :deploy_url, format: { with: URI::DEFAULT_PARSER.make_regexp(%w[http https ssh]) }, allow_blank: true
100
102
  validates :branch, presence: true
101
103
 
102
104
  validates :lock_reason, length: { maximum: 4096 }
@@ -130,7 +132,7 @@ module Shipit
130
132
 
131
133
  def trigger_task(definition_id, user, env: nil, force: false)
132
134
  definition = find_task_definition(definition_id)
133
- env = env&.to_h || {}
135
+ env = env.to_h
134
136
 
135
137
  definition.variables_with_defaults.each do |variable|
136
138
  env[variable.name] ||= variable.default
@@ -139,12 +141,12 @@ module Shipit
139
141
  commit = last_deployed_commit.presence || commits.first
140
142
  task = tasks.create(
141
143
  user_id: user.id,
142
- definition: definition,
144
+ definition:,
143
145
  until_commit_id: commit.id,
144
146
  since_commit_id: commit.id,
145
147
  env: definition.filter_envs(env),
146
148
  allow_concurrency: definition.allow_concurrency? || force,
147
- ignored_safeties: force,
149
+ ignored_safeties: force
148
150
  )
149
151
  task.enqueue
150
152
  task
@@ -154,12 +156,12 @@ module Shipit
154
156
  since_commit = last_deployed_commit.presence || commits.first
155
157
  deploys.build(
156
158
  user_id: user.id,
157
- until_commit: until_commit,
158
- since_commit: since_commit,
159
- env: filter_deploy_envs(env&.to_h || {}),
160
- allow_concurrency: allow_concurrency,
159
+ until_commit:,
160
+ since_commit:,
161
+ env: filter_deploy_envs(env.to_h),
162
+ allow_concurrency:,
161
163
  ignored_safeties: force || !until_commit.deployable?,
162
- max_retries: retries_on_deploy,
164
+ max_retries: retries_on_deploy
163
165
  )
164
166
  end
165
167
 
@@ -235,17 +237,16 @@ module Shipit
235
237
  end
236
238
 
237
239
  def deployed_too_recently?
238
- if task = last_active_task
239
- return true if task.validating?
240
+ return unless task = last_active_task
241
+ return true if task.validating?
240
242
 
241
- task.ended_at? && (task.ended_at + pause_between_deploys).future?
242
- end
243
+ task.ended_at? && (task.ended_at + pause_between_deploys).future?
243
244
  end
244
245
 
245
246
  def async_refresh_deployed_revision
246
247
  async_refresh_deployed_revision!
247
- rescue => error
248
- logger.warn("Failed to dispatch FetchDeployedRevisionJob: [#{error.class.name}] #{error.message}")
248
+ rescue StandardError => e
249
+ logger.warn("Failed to dispatch FetchDeployedRevisionJob: [#{e.class.name}] #{e.message}")
249
250
  end
250
251
 
251
252
  def async_refresh_deployed_revision!
@@ -267,7 +268,7 @@ module Shipit
267
268
  deploys.create!(
268
269
  until_commit: actual_deployed_commit,
269
270
  since_commit: last_deployed_commit.presence || commits.first,
270
- status: 'success',
271
+ status: 'success'
271
272
  )
272
273
  end
273
274
  end
@@ -278,8 +279,9 @@ module Shipit
278
279
 
279
280
  def merge_status(backlog_leniency_factor: 2.0)
280
281
  return 'locked' if locked?
281
- return 'failure' if %w(failure error).freeze.include?(branch_status)
282
- return 'backlogged' if backlogged?(backlog_leniency_factor: backlog_leniency_factor)
282
+ return 'failure' if %w[failure error].freeze.include?(branch_status)
283
+ return 'backlogged' if backlogged?(backlog_leniency_factor:)
284
+
283
285
  'success'
284
286
  end
285
287
 
@@ -290,13 +292,14 @@ module Shipit
290
292
  def branch_status
291
293
  undeployed_commits.each do |commit|
292
294
  state = commit.status.simple_state
293
- return state unless %w(pending unknown missing).freeze.include?(state)
295
+ return state unless %w[pending unknown missing].freeze.include?(state)
294
296
  end
295
297
  'pending'
296
298
  end
297
299
 
298
300
  def status
299
301
  return :deploying if active_task?
302
+
300
303
  :default
301
304
  end
302
305
 
@@ -313,8 +316,8 @@ module Shipit
313
316
  next if commits_to_lock.empty?
314
317
 
315
318
  affected_rows += commits
316
- .where(id: commits_to_lock.map(&:id).uniq)
317
- .lock_all(revert.author)
319
+ .where(id: commits_to_lock.map(&:id).uniq)
320
+ .lock_all(revert.author)
318
321
  end
319
322
 
320
323
  touch if affected_rows > 1
@@ -396,13 +399,14 @@ module Shipit
396
399
  end
397
400
 
398
401
  def acquire_git_cache_lock(timeout: 15, &block)
399
- @git_cache_lock ||= Flock.new(git_path.to_s + '.lock')
400
- @git_cache_lock.lock(timeout: timeout, &block)
402
+ @git_cache_lock ||= Flock.new("#{git_path}.lock")
403
+ @git_cache_lock.lock(timeout:, &block)
401
404
  end
402
405
 
403
406
  def clear_git_cache!
404
407
  tmp_path = "#{git_path}-#{SecureRandom.hex}"
405
408
  return unless git_path.exist?
409
+
406
410
  acquire_git_cache_lock do
407
411
  git_path.rename(tmp_path)
408
412
  end
@@ -442,9 +446,7 @@ module Shipit
442
446
 
443
447
  def refresh_repository!
444
448
  resource = github_api.repo(github_repo_name)
445
- if resource.try(:message) == 'Moved Permanently'
446
- resource = github_api.get(resource.url)
447
- end
449
+ resource = github_api.get(resource.url) if resource.try(:message) == 'Moved Permanently'
448
450
  repository.update!(owner: resource.owner.login, name: resource.name)
449
451
  end
450
452
 
@@ -454,6 +456,7 @@ module Shipit
454
456
 
455
457
  def active_task
456
458
  return @active_task if defined?(@active_task)
459
+
457
460
  @active_task ||= tasks.current
458
461
  end
459
462
 
@@ -500,7 +503,7 @@ module Shipit
500
503
  env = stack.cached_deploy_spec.default_deploy_env
501
504
  current_user = Shipit::CommandLineUser.new
502
505
 
503
- stack.trigger_deploy(until_commit, current_user, env: env, force: true, run_now: true)
506
+ stack.trigger_deploy(until_commit, current_user, env:, force: true, run_now: true)
504
507
  end
505
508
 
506
509
  def self.from_param!(param)
@@ -509,16 +512,16 @@ module Shipit
509
512
  .where(
510
513
  repositories: {
511
514
  owner: repo_owner.downcase,
512
- name: repo_name.downcase,
515
+ name: repo_name.downcase
513
516
  },
514
- environment: environment,
517
+ environment:
515
518
  ).first!
516
519
  end
517
520
 
518
521
  delegate :plugins, :task_definitions, :hidden_statuses, :required_statuses, :soft_failing_statuses,
519
- :blocking_statuses, :deploy_variables, :filter_task_envs, :filter_deploy_envs,
520
- :maximum_commits_per_deploy, :pause_between_deploys, :retries_on_deploy, :retries_on_rollback,
521
- to: :cached_deploy_spec
522
+ :blocking_statuses, :deploy_variables, :filter_task_envs, :filter_deploy_envs,
523
+ :maximum_commits_per_deploy, :pause_between_deploys, :retries_on_deploy, :retries_on_rollback,
524
+ to: :cached_deploy_spec
522
525
 
523
526
  def monitoring?
524
527
  monitoring.present?
@@ -543,16 +546,16 @@ module Shipit
543
546
  end
544
547
 
545
548
  def update_latest_deployed_ref
546
- if Shipit.update_latest_deployed_ref
547
- UpdateGithubLastDeployedRefJob.perform_later(self)
548
- end
549
+ return unless Shipit.update_latest_deployed_ref
550
+
551
+ UpdateGithubLastDeployedRefJob.perform_later(self)
549
552
  end
550
553
 
551
554
  def broadcast_update
552
555
  Pubsubstub.publish(
553
556
  "stack.#{id}",
554
- { id: id, updated_at: updated_at }.to_json,
555
- name: 'update',
557
+ { id:, updated_at: }.to_json,
558
+ name: 'update'
556
559
  )
557
560
  end
558
561
 
@@ -624,10 +627,10 @@ module Shipit
624
627
  return unless previous_changes.include?('lock_reason')
625
628
 
626
629
  lock_details = if previous_changes['lock_reason'].last.blank?
627
- { from: previous_changes['locked_since'].first, until: Time.zone.now }
628
- end
630
+ { from: previous_changes['locked_since'].first, until: Time.zone.now }
631
+ end
629
632
 
630
- Hook.emit(:lock, self, locked: locked?, lock_details: lock_details, stack: self)
633
+ Hook.emit(:lock, self, locked: locked?, lock_details:, stack: self)
631
634
  end
632
635
 
633
636
  private
@@ -662,9 +665,9 @@ module Shipit
662
665
  end
663
666
 
664
667
  def schedule_merges_if_necessary
665
- if lock_reason_previously_changed? && lock_reason.blank?
666
- schedule_merges
667
- end
668
+ return unless lock_reason_previously_changed? && lock_reason.blank?
669
+
670
+ schedule_merges
668
671
  end
669
672
 
670
673
  def emit_added_hooks
@@ -672,7 +675,7 @@ module Shipit
672
675
  end
673
676
 
674
677
  def emit_updated_hooks
675
- changed = !(previous_changes.keys - %w(updated_at)).empty?
678
+ changed = !(previous_changes.keys - %w[updated_at]).empty?
676
679
  Hook.emit(:stack, self, action: :updated, stack: self) if changed
677
680
  end
678
681
 
@@ -681,7 +684,7 @@ module Shipit
681
684
  end
682
685
 
683
686
  def emit_merge_status_hooks
684
- Hook.emit(:merge_status, self, merge_status: merge_status, stack: self)
687
+ Hook.emit(:merge_status, self, merge_status:, stack: self)
685
688
  end
686
689
 
687
690
  def ci_enabled_cache_key
@@ -1,4 +1,5 @@
1
1
  # frozen_string_literal: true
2
+
2
3
  module Shipit
3
4
  class Status
4
5
  module Common
@@ -1,4 +1,5 @@
1
1
  # frozen_string_literal: true
2
+
2
3
  module Shipit
3
4
  class Status
4
5
  class Group
@@ -31,7 +32,7 @@ module Shipit
31
32
  end
32
33
 
33
34
  delegate :pending?, :success?, :error?, :failure?, :unknown?, :missing?, :state, :simple_state,
34
- to: :significant_status
35
+ to: :significant_status
35
36
  delegate :each, :size, :map, to: :statuses
36
37
  delegate :required_statuses, to: :commit
37
38
 
@@ -43,8 +44,7 @@ module Shipit
43
44
  "#{success_count} / #{statuses.count} checks OK"
44
45
  end
45
46
 
46
- def target_url
47
- end
47
+ def target_url; end
48
48
 
49
49
  def to_partial_path
50
50
  'statuses/group'
@@ -75,8 +75,10 @@ module Shipit
75
75
  def select_significant_status(statuses)
76
76
  statuses = reject_allowed_to_fail(statuses)
77
77
  return Status::Unknown.new(commit) if statuses.empty?
78
+
78
79
  non_success_statuses = statuses.reject(&:success?)
79
80
  return statuses.first if non_success_statuses.empty?
81
+
80
82
  non_success_statuses.reject(&:pending?).first || non_success_statuses.first || Status::Unknown.new(commit)
81
83
  end
82
84
 
@@ -1,4 +1,5 @@
1
1
  # frozen_string_literal: true
2
+
2
3
  module Shipit
3
4
  class Status
4
5
  class Missing
@@ -24,7 +25,7 @@ module Shipit
24
25
  end
25
26
 
26
27
  def description
27
- I18n.t('missing_status.description', context: context)
28
+ I18n.t('missing_status.description', context:)
28
29
  end
29
30
 
30
31
  def to_partial_path
@@ -1,4 +1,5 @@
1
1
  # frozen_string_literal: true
2
+
2
3
  module Shipit
3
4
  class Status
4
5
  class Unknown