PageRenderTime 24ms CodeModel.GetById 16ms RepoModel.GetById 0ms app.codeStats 0ms

/lib/gitlab/quick_actions/issue_actions.rb

https://gitlab.com/hvlad/gitlab-ce
Ruby | 217 lines | 200 code | 15 blank | 2 comment | 8 complexity | e3981ac30be9125d5d4d4323c20a22a6 MD5 | raw file
  1. # frozen_string_literal: true
  2. module Gitlab
  3. module QuickActions
  4. module IssueActions
  5. extend ActiveSupport::Concern
  6. include Gitlab::QuickActions::Dsl
  7. included do
  8. # Issue only quick actions definition
  9. desc _('Set due date')
  10. explanation do |due_date|
  11. _("Sets the due date to %{due_date}.") % { due_date: due_date.strftime('%b %-d, %Y') } if due_date
  12. end
  13. execution_message do |due_date|
  14. _("Set the due date to %{due_date}.") % { due_date: due_date.strftime('%b %-d, %Y') } if due_date
  15. end
  16. params '<in 2 days | this Friday | December 31st>'
  17. types Issue
  18. condition do
  19. quick_action_target.respond_to?(:due_date) &&
  20. current_user.can?(:"admin_#{quick_action_target.to_ability_name}", project)
  21. end
  22. parse_params do |due_date_param|
  23. Chronic.parse(due_date_param).try(:to_date)
  24. end
  25. command :due do |due_date|
  26. if due_date
  27. @updates[:due_date] = due_date
  28. else
  29. @execution_message[:due] = _('Failed to set due date because the date format is invalid.')
  30. end
  31. end
  32. desc _('Remove due date')
  33. explanation _('Removes the due date.')
  34. execution_message _('Removed the due date.')
  35. types Issue
  36. condition do
  37. quick_action_target.persisted? &&
  38. quick_action_target.respond_to?(:due_date) &&
  39. quick_action_target.due_date? &&
  40. current_user.can?(:"admin_#{quick_action_target.to_ability_name}", project)
  41. end
  42. command :remove_due_date do
  43. @updates[:due_date] = nil
  44. end
  45. desc _('Move issue from one column of the board to another')
  46. explanation do |target_list_name|
  47. label = find_label_references(target_list_name).first
  48. _("Moves issue to %{label} column in the board.") % { label: label } if label
  49. end
  50. params '~"Target column"'
  51. types Issue
  52. condition do
  53. current_user.can?(:"update_#{quick_action_target.to_ability_name}", quick_action_target) &&
  54. quick_action_target.project.boards.count == 1
  55. end
  56. command :board_move do |target_list_name|
  57. labels = find_labels(target_list_name)
  58. label_ids = labels.map(&:id)
  59. if label_ids.size > 1
  60. message = _('Failed to move this issue because only a single label can be provided.')
  61. elsif !Label.on_project_board?(quick_action_target.project_id, label_ids.first)
  62. message = _('Failed to move this issue because label was not found.')
  63. else
  64. label_id = label_ids.first
  65. @updates[:remove_label_ids] =
  66. quick_action_target.labels.on_project_boards(quick_action_target.project_id).where.not(id: label_id).pluck(:id) # rubocop: disable CodeReuse/ActiveRecord
  67. @updates[:add_label_ids] = [label_id]
  68. message = _("Moved issue to %{label} column in the board.") % { label: labels_to_reference(labels).first }
  69. end
  70. @execution_message[:board_move] = message
  71. end
  72. desc _('Mark this issue as a duplicate of another issue')
  73. explanation do |duplicate_reference|
  74. _("Marks this issue as a duplicate of %{duplicate_reference}.") % { duplicate_reference: duplicate_reference }
  75. end
  76. params '#issue'
  77. types Issue
  78. condition do
  79. quick_action_target.persisted? &&
  80. current_user.can?(:"update_#{quick_action_target.to_ability_name}", quick_action_target)
  81. end
  82. command :duplicate do |duplicate_param|
  83. canonical_issue = extract_references(duplicate_param, :issue).first
  84. if canonical_issue.present?
  85. @updates[:canonical_issue_id] = canonical_issue.id
  86. message = _("Marked this issue as a duplicate of %{duplicate_param}.") % { duplicate_param: duplicate_param }
  87. else
  88. message = _('Failed to mark this issue as a duplicate because referenced issue was not found.')
  89. end
  90. @execution_message[:duplicate] = message
  91. end
  92. desc _('Move this issue to another project.')
  93. explanation do |path_to_project|
  94. _("Moves this issue to %{path_to_project}.") % { path_to_project: path_to_project }
  95. end
  96. params 'path/to/project'
  97. types Issue
  98. condition do
  99. quick_action_target.persisted? &&
  100. current_user.can?(:"admin_#{quick_action_target.to_ability_name}", project)
  101. end
  102. command :move do |target_project_path|
  103. target_project = Project.find_by_full_path(target_project_path)
  104. if target_project.present?
  105. @updates[:target_project] = target_project
  106. message = _("Moved this issue to %{path_to_project}.") % { path_to_project: target_project_path }
  107. else
  108. message = _("Failed to move this issue because target project doesn't exist.")
  109. end
  110. @execution_message[:move] = message
  111. end
  112. desc _('Make issue confidential')
  113. explanation do
  114. _('Makes this issue confidential.')
  115. end
  116. execution_message do
  117. _('Made this issue confidential.')
  118. end
  119. types Issue
  120. condition do
  121. !quick_action_target.confidential? &&
  122. current_user.can?(:"admin_#{quick_action_target.to_ability_name}", quick_action_target)
  123. end
  124. command :confidential do
  125. @updates[:confidential] = true
  126. end
  127. desc _('Create a merge request')
  128. explanation do |branch_name = nil|
  129. if branch_name
  130. _("Creates branch '%{branch_name}' and a merge request to resolve this issue.") % { branch_name: branch_name }
  131. else
  132. _('Creates a branch and a merge request to resolve this issue.')
  133. end
  134. end
  135. execution_message do |branch_name = nil|
  136. if branch_name
  137. _("Created branch '%{branch_name}' and a merge request to resolve this issue.") % { branch_name: branch_name }
  138. else
  139. _('Created a branch and a merge request to resolve this issue.')
  140. end
  141. end
  142. params "<branch name>"
  143. types Issue
  144. condition do
  145. current_user.can?(:create_merge_request_in, project) && current_user.can?(:push_code, project)
  146. end
  147. command :create_merge_request do |branch_name = nil|
  148. @updates[:create_merge_request] = {
  149. branch_name: branch_name,
  150. issue_iid: quick_action_target.iid
  151. }
  152. end
  153. desc _('Add Zoom meeting')
  154. explanation _('Adds a Zoom meeting')
  155. params '<Zoom URL>'
  156. types Issue
  157. condition do
  158. zoom_link_service.can_add_link?
  159. end
  160. parse_params do |link|
  161. zoom_link_service.parse_link(link)
  162. end
  163. command :zoom do |link|
  164. result = zoom_link_service.add_link(link)
  165. if result.success?
  166. @updates[:description] = result.payload[:description]
  167. end
  168. @execution_message[:zoom] = result.message
  169. end
  170. desc _('Remove Zoom meeting')
  171. explanation _('Remove Zoom meeting')
  172. execution_message _('Zoom meeting removed')
  173. types Issue
  174. condition do
  175. zoom_link_service.can_remove_link?
  176. end
  177. command :remove_zoom do
  178. result = zoom_link_service.remove_link
  179. if result.success?
  180. @updates[:description] = result.payload[:description]
  181. end
  182. @execution_message[:remove_zoom] = result.message
  183. end
  184. private
  185. def zoom_link_service
  186. Issues::ZoomLinkService.new(quick_action_target, current_user)
  187. end
  188. end
  189. end
  190. end
  191. end