Moved to background job for sending twitter messages.
This commit is contained in:
parent
3b9f7b28df
commit
081034a15a
3 changed files with 126 additions and 42 deletions
|
@ -17,48 +17,7 @@ class Observer::Ticket::Article::CommunicateTwitter < ActiveRecord::Observer
|
|||
type = Ticket::Article::Type.lookup(id: record.type_id)
|
||||
return if type['name'] !~ /\Atwitter/i
|
||||
|
||||
ticket = Ticket.lookup(id: record.ticket_id)
|
||||
raise "Can't find ticket.preferences for Ticket.find(#{record.ticket_id})" if !ticket.preferences
|
||||
raise "Can't find ticket.preferences['channel_id'] for Ticket.find(#{record.ticket_id})" if !ticket.preferences['channel_id']
|
||||
channel = Channel.lookup(id: ticket.preferences['channel_id'])
|
||||
raise "No such channel id #{ticket.preferences['channel_id']}" if !channel
|
||||
raise "Channel.find(#{channel.id}) isn't a twitter channel!" if channel.options[:adapter] !~ /\Atwitter/i
|
||||
tweet = channel.deliver(
|
||||
type: type['name'],
|
||||
to: record.to,
|
||||
body: record.body,
|
||||
in_reply_to: record.in_reply_to
|
||||
)
|
||||
|
||||
# fill article with tweet info
|
||||
|
||||
# direct message
|
||||
if tweet.class == Twitter::DirectMessage
|
||||
record.from = "@#{tweet.sender.screen_name}"
|
||||
record.to = "@#{tweet.recipient.screen_name}"
|
||||
|
||||
# regular tweet
|
||||
elsif tweet.class == Twitter::Tweet
|
||||
record.from = "@#{tweet.user.screen_name}"
|
||||
if tweet.user_mentions
|
||||
to = ''
|
||||
twitter_mention_ids = []
|
||||
tweet.user_mentions.each {|user|
|
||||
if to != ''
|
||||
to += ' '
|
||||
end
|
||||
to += "@#{user.screen_name}"
|
||||
twitter_mention_ids.push user.id
|
||||
}
|
||||
record.to = to
|
||||
record.preferences[:twitter_mention_ids] = twitter_mention_ids
|
||||
end
|
||||
else
|
||||
raise "Unknown tweet type '#{tweet.class}'"
|
||||
end
|
||||
|
||||
record.message_id = tweet.id
|
||||
record.save
|
||||
Delayed::Job.enqueue(Observer::Ticket::Article::CommunicateTwitter::BackgroundJob.new(record.id))
|
||||
end
|
||||
|
||||
end
|
||||
|
|
|
@ -0,0 +1,109 @@
|
|||
class Observer::Ticket::Article::CommunicateTwitter::BackgroundJob
|
||||
def initialize(id)
|
||||
@article_id = id
|
||||
end
|
||||
|
||||
def perform
|
||||
article = Ticket::Article.find(@article_id)
|
||||
|
||||
# set retry count
|
||||
if !article.preferences['delivery_retry']
|
||||
article.preferences['delivery_retry'] = 0
|
||||
end
|
||||
article.preferences['delivery_retry'] += 1
|
||||
|
||||
ticket = Ticket.lookup(id: article.ticket_id)
|
||||
log_error(article, "Can't find ticket.preferences for Ticket.find(#{article.ticket_id})") if !ticket.preferences
|
||||
log_error(article, "Can't find ticket.preferences['channel_id'] for Ticket.find(#{article.ticket_id})") if !ticket.preferences['channel_id']
|
||||
channel = Channel.lookup(id: ticket.preferences['channel_id'])
|
||||
log_error(article, "No such channel id #{ticket.preferences['channel_id']}") if !channel
|
||||
log_error(article, "Channel.find(#{channel.id}) isn't a twitter channel!") if channel.options[:adapter] !~ /\Atwitter/i
|
||||
|
||||
begin
|
||||
tweet = channel.deliver(
|
||||
type: article.type.name,
|
||||
to: article.to,
|
||||
body: article.body,
|
||||
in_reply_to: article.in_reply_to
|
||||
)
|
||||
rescue => e
|
||||
log_error(article, e.message)
|
||||
return
|
||||
end
|
||||
if !tweet
|
||||
log_error(article, 'Unable to send message to twitter')
|
||||
return
|
||||
end
|
||||
|
||||
# fill article with tweet info
|
||||
|
||||
# direct message
|
||||
if tweet.class == Twitter::DirectMessage
|
||||
article.from = "@#{tweet.sender.screen_name}"
|
||||
article.to = "@#{tweet.recipient.screen_name}"
|
||||
|
||||
# regular tweet
|
||||
elsif tweet.class == Twitter::Tweet
|
||||
article.from = "@#{tweet.user.screen_name}"
|
||||
if tweet.user_mentions
|
||||
to = ''
|
||||
twitter_mention_ids = []
|
||||
tweet.user_mentions.each {|user|
|
||||
if to != ''
|
||||
to += ' '
|
||||
end
|
||||
to += "@#{user.screen_name}"
|
||||
twitter_mention_ids.push user.id
|
||||
}
|
||||
article.to = to
|
||||
article.preferences[:twitter_mention_ids] = twitter_mention_ids
|
||||
end
|
||||
else
|
||||
raise "Unknown tweet type '#{tweet.class}'"
|
||||
end
|
||||
|
||||
# set delivery status
|
||||
article.preferences['delivery_status_message'] = nil
|
||||
article.preferences['delivery_status'] = 'success'
|
||||
article.preferences['delivery_status_date'] = Time.zone.now
|
||||
|
||||
article.message_id = tweet.id.to_s
|
||||
article.save
|
||||
|
||||
end
|
||||
|
||||
def log_error(local_record, message)
|
||||
local_record.preferences['delivery_status'] = 'fail'
|
||||
local_record.preferences['delivery_status_message'] = message
|
||||
local_record.preferences['delivery_status_date'] = Time.zone.now
|
||||
local_record.save
|
||||
Rails.logger.error message
|
||||
|
||||
if local_record.preferences['delivery_retry'] > 3
|
||||
Ticket::Article.create(
|
||||
ticket_id: local_record.ticket_id,
|
||||
content_type: 'text/plain',
|
||||
body: "Unable to send tweet: #{message}",
|
||||
internal: true,
|
||||
sender: Ticket::Article::Sender.find_by(name: 'System'),
|
||||
type: Ticket::Article::Type.find_by(name: 'note'),
|
||||
updated_by_id: 1,
|
||||
created_by_id: 1,
|
||||
)
|
||||
return
|
||||
end
|
||||
|
||||
raise message
|
||||
end
|
||||
|
||||
def max_attempts
|
||||
4
|
||||
end
|
||||
|
||||
def reschedule_at(current_time, attempts)
|
||||
if Rails.env.production?
|
||||
return current_time + attempts * 120.seconds
|
||||
end
|
||||
current_time + 5.seconds
|
||||
end
|
||||
end
|
|
@ -125,6 +125,10 @@ class TwitterTest < ActiveSupport::TestCase
|
|||
updated_by_id: 1,
|
||||
created_by_id: 1,
|
||||
)
|
||||
|
||||
Scheduler.worker(true)
|
||||
|
||||
article = Ticket::Article.find(article.id)
|
||||
assert(article, "outbound article created, text: #{text}")
|
||||
assert_equal(system_login, article.from, 'ticket article from')
|
||||
assert_equal('', article.to, 'ticket article to')
|
||||
|
@ -223,6 +227,10 @@ class TwitterTest < ActiveSupport::TestCase
|
|||
updated_by_id: 1,
|
||||
created_by_id: 1,
|
||||
)
|
||||
|
||||
Scheduler.worker(true)
|
||||
|
||||
article = Ticket::Article.find(article.id)
|
||||
assert(article, "outbound article created, text: #{reply_text}")
|
||||
assert_equal(system_login, article.from, 'ticket article from')
|
||||
assert_equal(customer_login, article.to, 'ticket article to')
|
||||
|
@ -306,6 +314,10 @@ class TwitterTest < ActiveSupport::TestCase
|
|||
updated_by_id: 1,
|
||||
created_by_id: 1,
|
||||
)
|
||||
|
||||
Scheduler.worker(true)
|
||||
|
||||
outbound_article = Ticket::Article.find(outbound_article.id)
|
||||
assert(outbound_article, 'outbound article created')
|
||||
assert_equal(2, outbound_article.ticket.articles.count, 'ticket article outbound count')
|
||||
assert_equal(system_login, outbound_article.from, 'ticket article from')
|
||||
|
@ -445,6 +457,10 @@ class TwitterTest < ActiveSupport::TestCase
|
|||
updated_by_id: 1,
|
||||
created_by_id: 1,
|
||||
)
|
||||
|
||||
Scheduler.worker(true)
|
||||
|
||||
article = Ticket::Article.find(article.id)
|
||||
assert(article, "outbound article created, text: #{reply_text}")
|
||||
assert_equal(system_login, article.from, 'ticket article from')
|
||||
assert_equal('', article.to, 'ticket article to')
|
||||
|
|
Loading…
Reference in a new issue