* This change abstracts the DatadogStatsClient into a ForemStatsClient. The purpose of this abstraction is to set the foundation for a subsequent PR that will allow one to use New Relic for recording Forem stats, instead of Datadog, if there is a New Relic configuration found. This specific change creates an abstraction layer that can be built upon, without changing any actual default behavior. All specs still pass. * Use delegate instead of explicit methods. * Delegate instead of explicit methods. * Fix the error. * Refactor according to the suggestions in the comments. * Ooops. Stats work better when all of the code is committed. * Removing the alias of count to increment since that was done in error.
72 lines
2.3 KiB
Ruby
72 lines
2.3 KiB
Ruby
module TwitterClient
|
|
# Twitter client (users twitter gem as a backend)
|
|
class Client
|
|
class << self
|
|
# adapted from https://api.rubyonrails.org/classes/Module.html#method-i-delegate_missing_to
|
|
def method_missing(method, *args, &block)
|
|
return super unless target.respond_to?(method, false)
|
|
|
|
request do
|
|
target.public_send(method, *args, &block)
|
|
end
|
|
end
|
|
|
|
# adapted from https://api.rubyonrails.org/classes/Module.html#method-i-delegate_missing_to
|
|
def respond_to_missing?(method, _include_all = false)
|
|
target.respond_to?(method, false) || super
|
|
end
|
|
|
|
private
|
|
|
|
def request
|
|
Honeycomb.add_field("name", "twitter.client")
|
|
yield
|
|
rescue Twitter::Error => e
|
|
record_error(e)
|
|
handle_error(e)
|
|
end
|
|
|
|
def record_error(exception)
|
|
class_name = exception.class.name.demodulize
|
|
|
|
Honeycomb.add_field("twitter.result", "error")
|
|
Honeycomb.add_field("twitter.error", class_name)
|
|
ForemStatsClient.increment(
|
|
"twitter.errors",
|
|
tags: ["error:#{class_name}", "message:#{exception.message}"],
|
|
)
|
|
end
|
|
|
|
def handle_error(exception)
|
|
class_name = exception.class.name.demodulize
|
|
|
|
# raise specific error if known, generic one if unknown
|
|
error_class = "::TwitterClient::Errors::#{class_name}".safe_constantize
|
|
raise error_class, exception.message if error_class
|
|
|
|
error_class = if exception.class < Twitter::Error::ClientError
|
|
TwitterClient::Errors::ClientError
|
|
elsif exception.class < Twitter::Error::ServerError
|
|
TwitterClient::Errors::ServerError
|
|
else
|
|
TwitterClient::Errors::Error
|
|
end
|
|
|
|
raise error_class, exception.message
|
|
end
|
|
|
|
def target
|
|
Twitter::REST::Client.new(
|
|
consumer_key: SiteConfig.twitter_key.presence || ApplicationConfig["TWITTER_KEY"],
|
|
consumer_secret: SiteConfig.twitter_secret.presence || ApplicationConfig["TWITTER_SECRET"],
|
|
user_agent: "TwitterRubyGem/#{Twitter::Version} (#{URL.url})",
|
|
timeouts: {
|
|
connect: 5,
|
|
read: 5,
|
|
write: 5
|
|
},
|
|
)
|
|
end
|
|
end
|
|
end
|
|
end
|