diff options
Diffstat (limited to 'app/services/notes')
-rw-r--r-- | app/services/notes/copy_service.rb | 68 | ||||
-rw-r--r-- | app/services/notes/create_service.rb | 7 | ||||
-rw-r--r-- | app/services/notes/quick_actions_service.rb | 5 | ||||
-rw-r--r-- | app/services/notes/update_service.rb | 2 |
4 files changed, 78 insertions, 4 deletions
diff --git a/app/services/notes/copy_service.rb b/app/services/notes/copy_service.rb new file mode 100644 index 00000000000..6e5b4596602 --- /dev/null +++ b/app/services/notes/copy_service.rb @@ -0,0 +1,68 @@ +# frozen_string_literal: true + +# This service copies Notes from one Noteable to another. +# +# It expects the calling code to have performed the necessary authorization +# checks in order to allow the copy to happen. +module Notes + class CopyService + def initialize(current_user, from_noteable, to_noteable) + raise ArgumentError, 'Noteables must be different' if from_noteable == to_noteable + + @current_user = current_user + @from_noteable = from_noteable + @to_noteable = to_noteable + @from_project = from_noteable.project + @new_discussion_ids = {} + end + + def execute + from_noteable.notes_with_associations.find_each do |note| + copy_note(note) + end + + ServiceResponse.success + end + + private + + attr_reader :from_noteable, :to_noteable, :from_project, :current_user, :new_discussion_ids + + def copy_note(note) + new_note = note.dup + new_params = params_from_note(note, new_note) + new_note.update!(new_params) + + copy_award_emoji(note, new_note) + end + + def params_from_note(note, new_note) + new_discussion_ids[note.discussion_id] ||= Discussion.discussion_id(new_note) + rewritten_note = MarkdownContentRewriterService.new(current_user, note.note, from_project, to_noteable.resource_parent).execute + + new_params = { + project: to_noteable.project, + noteable: to_noteable, + discussion_id: new_discussion_ids[note.discussion_id], + note: rewritten_note, + note_html: nil, + created_at: note.created_at, + updated_at: note.updated_at + } + + if note.system_note_metadata + new_params[:system_note_metadata] = note.system_note_metadata.dup + + # TODO: Implement copying of description versions when an issue is moved + # https://gitlab.com/gitlab-org/gitlab/issues/32300 + new_params[:system_note_metadata].description_version = nil + end + + new_params + end + + def copy_award_emoji(from_note, to_note) + AwardEmojis::CopyService.new(from_note, to_note).execute + end + end +end diff --git a/app/services/notes/create_service.rb b/app/services/notes/create_service.rb index 935dbfb72dd..4f2329a42f2 100644 --- a/app/services/notes/create_service.rb +++ b/app/services/notes/create_service.rb @@ -54,7 +54,8 @@ module Notes def when_saved(note) if note.part_of_discussion? && note.discussion.can_convert_to_discussion? - note.discussion.convert_to_discussion!(save: true) + note.discussion.convert_to_discussion!.save + note.clear_memoization(:discussion) end todo_service.new_note(note, current_user) @@ -66,13 +67,13 @@ module Notes Gitlab::Tracking.event('Notes::CreateService', 'execute', tracking_data_for(note)) end - if Feature.enabled?(:merge_ref_head_comments, project) && note.for_merge_request? && note.diff_note? && note.start_of_discussion? + if Feature.enabled?(:merge_ref_head_comments, project, default_enabled: true) && note.for_merge_request? && note.diff_note? && note.start_of_discussion? Discussions::CaptureDiffNotePositionService.new(note.noteable, note.diff_file&.paths).execute(note.discussion) end end def do_commands(note, update_params, message, only_commands) - return if quick_actions_service.commands_executed_count.to_i.zero? + return if quick_actions_service.commands_executed_count.to_i == 0 if update_params.present? quick_actions_service.apply_updates(update_params, note) diff --git a/app/services/notes/quick_actions_service.rb b/app/services/notes/quick_actions_service.rb index c670f01e502..36d9f1d7867 100644 --- a/app/services/notes/quick_actions_service.rb +++ b/app/services/notes/quick_actions_service.rb @@ -50,6 +50,11 @@ module Notes return if update_params.empty? return unless supported?(note) + # We need the `id` after the note is persisted + if update_params[:spend_time] + update_params[:spend_time][:note_id] = note.id + end + self.class.noteable_update_service(note).new(note.resource_parent, current_user, update_params).execute(note.noteable) end end diff --git a/app/services/notes/update_service.rb b/app/services/notes/update_service.rb index 047848fd1a3..193d3080078 100644 --- a/app/services/notes/update_service.rb +++ b/app/services/notes/update_service.rb @@ -25,7 +25,7 @@ module Notes note.note = content end - unless only_commands + unless only_commands || note.for_personal_snippet? note.create_new_cross_references!(current_user) update_todos(note, old_mentioned_users) |