2021-05-05 15:36:11 +00:00
|
|
|
class Integrations::Dialogflow::ProcessorService
|
|
|
|
pattr_initialize [:event_name!, :hook!, :event_data!]
|
|
|
|
|
|
|
|
def perform
|
|
|
|
message = event_data[:message]
|
|
|
|
return if message.private?
|
|
|
|
return unless processable_message?(message)
|
2021-07-21 16:32:43 +00:00
|
|
|
return unless message.conversation.pending?
|
2021-05-05 15:36:11 +00:00
|
|
|
|
2021-09-15 12:42:56 +00:00
|
|
|
content = message_content(message)
|
|
|
|
response = get_dialogflow_response(message.conversation.contact_inbox.source_id, content) if content.present?
|
|
|
|
process_response(message, response) if response.present?
|
2021-05-05 15:36:11 +00:00
|
|
|
end
|
|
|
|
|
|
|
|
private
|
|
|
|
|
|
|
|
def message_content(message)
|
2021-09-15 12:42:56 +00:00
|
|
|
# TODO: might needs to change this to a way that we fetch the updated value from event data instead
|
|
|
|
# cause the message.updated event could be that that the message was deleted
|
|
|
|
|
2021-10-14 07:47:09 +00:00
|
|
|
return message.content_attributes['submitted_values']&.first&.dig('value') if event_name == 'message.updated'
|
2021-05-05 15:36:11 +00:00
|
|
|
|
|
|
|
message.content
|
|
|
|
end
|
|
|
|
|
|
|
|
def processable_message?(message)
|
2021-08-23 16:30:47 +00:00
|
|
|
# TODO: change from reportable and create a dedicated method for this?
|
2021-05-05 15:36:11 +00:00
|
|
|
return unless message.reportable?
|
|
|
|
return if message.outgoing? && !processable_outgoing_message?(message)
|
|
|
|
|
|
|
|
true
|
|
|
|
end
|
|
|
|
|
|
|
|
def processable_outgoing_message?(message)
|
|
|
|
event_name == 'message.updated' && ['input_select'].include?(message.content_type)
|
|
|
|
end
|
|
|
|
|
|
|
|
def get_dialogflow_response(session_id, message)
|
|
|
|
Google::Cloud::Dialogflow.configure { |config| config.credentials = hook.settings['credentials'] }
|
|
|
|
session_client = Google::Cloud::Dialogflow.sessions
|
|
|
|
session = session_client.session_path project: hook.settings['project_id'], session: session_id
|
|
|
|
query_input = { text: { text: message, language_code: 'en-US' } }
|
|
|
|
session_client.detect_intent session: session, query_input: query_input
|
|
|
|
end
|
|
|
|
|
|
|
|
def process_response(message, response)
|
2021-07-07 04:34:48 +00:00
|
|
|
fulfillment_messages = response.query_result['fulfillment_messages']
|
|
|
|
fulfillment_messages.each do |fulfillment_message|
|
|
|
|
content_params = generate_content_params(fulfillment_message)
|
|
|
|
if content_params['action'].present?
|
|
|
|
process_action(message, content_params['action'])
|
|
|
|
else
|
|
|
|
create_conversation(message, content_params)
|
|
|
|
end
|
|
|
|
end
|
|
|
|
end
|
2021-05-05 15:36:11 +00:00
|
|
|
|
2021-07-07 04:34:48 +00:00
|
|
|
def generate_content_params(fulfillment_message)
|
|
|
|
text_response = fulfillment_message['text'].to_h
|
|
|
|
content_params = { content: text_response[:text].first } if text_response[:text].present?
|
|
|
|
content_params ||= fulfillment_message['payload'].to_h
|
|
|
|
content_params
|
2021-05-05 15:36:11 +00:00
|
|
|
end
|
|
|
|
|
|
|
|
def create_conversation(message, content_params)
|
|
|
|
return if content_params.blank?
|
|
|
|
|
|
|
|
conversation = message.conversation
|
|
|
|
conversation.messages.create(content_params.merge({
|
|
|
|
message_type: :outgoing,
|
|
|
|
account_id: conversation.account_id,
|
|
|
|
inbox_id: conversation.inbox_id
|
|
|
|
}))
|
|
|
|
end
|
|
|
|
|
|
|
|
def process_action(message, action)
|
|
|
|
case action
|
|
|
|
when 'handoff'
|
|
|
|
message.conversation.open!
|
|
|
|
end
|
|
|
|
end
|
|
|
|
end
|