Class: CollavreLinear::OutboundCommentUpdateJob

Inherits:
ApplicationJob
  • Object
show all
Defined in:
app/jobs/collavre_linear/outbound_comment_update_job.rb

Overview

Pushes a local edit of a Collavre::Comment to its mirrored Linear comment.

CollavreLinear::OutboundCommentUpdateJob.perform_later(comment.id)

No-op when the comment (or its CommentLink) is gone: a delete may have raced ahead, and the delete job owns tearing down the Linear comment.

Instance Method Summary collapse

Instance Method Details

#perform(comment_id) ⇒ Object



15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
# File 'app/jobs/collavre_linear/outbound_comment_update_job.rb', line 15

def perform(comment_id)
  comment = ::Collavre::Comment.find(comment_id)

  comment_link = CollavreLinear::CommentLink.find_by(comment_id: comment.id)
  return unless comment_link

  # Serialize edits of the same mirrored comment. Two quick edits enqueue two
  # jobs; without the lock one can read body A, the other body B, and if B's
  # Linear call completes first the older job overwrites Linear back to A while
  # advancing the baseline — leaving Linear stale until the next edit. Locking
  # the CommentLink and reloading the comment inside the lock means every run
  # pushes the current committed body in enqueue order, so the last write wins.
  comment_link.with_lock do
    comment.reload

    # Re-check visibility under the lock: the comment may have been made
    # private or moved out of Main between enqueue and now. The observer
    # enqueues a delete for that change, but with multiple workers this update
    # could run first and leak the now-hidden body. The delete job owns
    # teardown; no-op.
    return unless CollavreLinear::CommentSyncability.syncable?(comment)

     = comment_link.issue_link.project_link.
    return unless 

    result = CollavreLinear::Client.new().update_comment(
      id:   comment_link.linear_comment_id,
      body: CollavreLinear::CommentFormatter.outbound_body(comment)
    )

    # Advance the synced baseline so the echo of this edit (and any stale echo
    # of an earlier body) is recognised as ours by the inbound applier.
    comment_link.update!(remote_updated_at: result[:updatedAt]) if result[:updatedAt].present?
  end
rescue ActiveRecord::RecordNotFound
  Rails.logger.info(
    "[CollavreLinear::OutboundCommentUpdateJob] Comment #{comment_id} not found; skipping"
  )
end