fix(whatsapp): resolve replies across scoped message ids
This commit is contained in:
@@ -0,0 +1,37 @@
|
||||
class Whatsapp::InReplyToMessageFinder
|
||||
MESSAGE_TOKEN_PATTERN = /(?<![0-9a-f])(?:[0-9a-f]{32}|[0-9a-f]{20})(?![0-9a-f])/i
|
||||
|
||||
pattr_initialize [:conversation!, :source_id!]
|
||||
|
||||
def perform
|
||||
exact_match || matching_scoped_message
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
def exact_match
|
||||
conversation.messages.find_by(source_id: source_id)
|
||||
end
|
||||
|
||||
def matching_scoped_message
|
||||
token = message_token(source_id)
|
||||
return if token.blank?
|
||||
|
||||
# Phone-scoped and BSUID-scoped WAMIDs can carry the same message token
|
||||
# even when their complete source IDs differ.
|
||||
matches = conversation.messages.where('source_id LIKE ?', 'wamid.%').select(:id, :source_id).select do |message|
|
||||
message_token(message.source_id) == token
|
||||
end
|
||||
|
||||
matches.one? ? matches.first : nil
|
||||
end
|
||||
|
||||
def message_token(message_id)
|
||||
return unless message_id.start_with?('wamid.')
|
||||
|
||||
tokens = Base64.strict_decode64(message_id.delete_prefix('wamid.')).scan(MESSAGE_TOKEN_PATTERN)
|
||||
tokens.one? ? tokens.first.downcase : nil
|
||||
rescue ArgumentError
|
||||
nil
|
||||
end
|
||||
end
|
||||
@@ -174,6 +174,7 @@ class Whatsapp::IncomingMessageBaseService
|
||||
|
||||
def message_content_attributes(message)
|
||||
content_attrs = outgoing_echo ? { external_echo: true } : {}
|
||||
content_attrs[:in_reply_to] = @in_reply_to_message_id if @in_reply_to_message_id.present?
|
||||
content_attrs[:in_reply_to_external_id] = @in_reply_to_external_id if @in_reply_to_external_id.present?
|
||||
referral_content_attrs = referral_attributes(message)
|
||||
content_attrs[:referral] = referral_content_attrs if referral_content_attrs.present?
|
||||
|
||||
@@ -69,6 +69,12 @@ module Whatsapp::IncomingMessageServiceHelpers
|
||||
|
||||
def process_in_reply_to(message)
|
||||
@in_reply_to_external_id = message['context']&.[]('id')
|
||||
return if @in_reply_to_external_id.blank?
|
||||
|
||||
@in_reply_to_message_id = Whatsapp::InReplyToMessageFinder.new(
|
||||
conversation: @conversation,
|
||||
source_id: @in_reply_to_external_id
|
||||
).perform&.id
|
||||
end
|
||||
|
||||
def referral_attributes(message)
|
||||
|
||||
Reference in New Issue
Block a user