Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add way to define Sidekiq sender class #57

Open
wants to merge 4 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions lib/vero.rb
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
require 'json'
require 'rest-client'
require 'vero/utility/ext'

Expand Down
5 changes: 1 addition & 4 deletions lib/vero/api/base_api.rb
Original file line number Diff line number Diff line change
@@ -1,6 +1,3 @@
require 'json'
require 'rest-client'

module Vero
module Api
module Workers
Expand Down Expand Up @@ -65,4 +62,4 @@ def options_with_symbolized_keys(val)
end
end
end
end
end
6 changes: 4 additions & 2 deletions lib/vero/config.rb
Original file line number Diff line number Diff line change
Expand Up @@ -3,10 +3,12 @@
module Vero
class Config
attr_writer :domain
attr_accessor :api_key, :secret, :development_mode, :async, :disabled, :logging
attr_accessor :api_key, :secret, :development_mode, :async, :disabled
attr_accessor :logging, :sender_class

def self.available_attributes
[:api_key, :secret, :development_mode, :async, :disabled, :logging, :domain]
[:api_key, :secret, :development_mode, :async, :disabled, :logging,
:domain, :sender_class]
end

def initialize
Expand Down
4 changes: 1 addition & 3 deletions lib/vero/sender.rb
Original file line number Diff line number Diff line change
@@ -1,5 +1,3 @@
require 'json'

module Vero
class SenderHash < ::Hash
def [](key)
Expand Down Expand Up @@ -39,7 +37,7 @@ def self.send(api_class, sender_strategy, domain, options)
else
self.senders[false]
end

(sender_class.new).call(api_class, domain, options)
rescue => e
options_s = JSON.dump(options)
Expand Down
7 changes: 2 additions & 5 deletions lib/vero/senders/base.rb
Original file line number Diff line number Diff line change
@@ -1,14 +1,11 @@
require 'json'

module Vero
module Senders
class Base
def call(api_class, domain, options)
response = api_class.perform(domain, options)
options_s = JSON.dump(options)
Vero::App.log(self, "method: #{api_class.name}, options: #{options_s}, response: job performed")
Vero::App.log(self, "method: #{api_class.name}, options: #{JSON.dump(options)}, response: job performed")
response
end
end
end
end
end
6 changes: 2 additions & 4 deletions lib/vero/senders/delayed_job.rb
Original file line number Diff line number Diff line change
@@ -1,13 +1,11 @@
require 'json'
require 'delayed_job'

module Vero
module Senders
class DelayedJob
def call(api_class, domain, options)
response = ::Delayed::Job.enqueue api_class.new(domain, options)
options_s = JSON.dump(options)
Vero::App.log(self, "method: #{api_class.name}, options: #{options_s}, response: delayed job queued")
Vero::App.log(self, "method: #{api_class.name}, options: #{JSON.dump(options)}, response: delayed job queued")
response
rescue => e
if e.message == "Could not find table 'delayed_jobs'"
Expand All @@ -18,4 +16,4 @@ def call(api_class, domain, options)
end
end
end
end
end
13 changes: 5 additions & 8 deletions lib/vero/senders/resque.rb
Original file line number Diff line number Diff line change
@@ -1,19 +1,16 @@
require 'json'
require 'resque'

module Vero
class ResqueWorker
@queue = :vero

def self.perform(api_class_name, domain, options)
api_class = eval(api_class_name)
def self.perform(api_class, domain, options)
api_class = eval(api_class.to_s)
new_options = {}
options.each do |k,v|
new_options[k.to_sym] = v
end
options.each { |k,v| new_options[k.to_sym] = v }

api_class.new(domain, new_options).perform
Vero::App.log(self, "method: #{api_class.name}, options: #{options.to_json}, response: resque job queued")
Vero::App.log(self, "method: #{api_class.name}, options: #{JSON.dump(options)}, response: resque job queued")
end
end

Expand All @@ -24,4 +21,4 @@ def call(api_class, domain, options)
end
end
end
end
end
31 changes: 25 additions & 6 deletions lib/vero/senders/sidekiq.rb
Original file line number Diff line number Diff line change
@@ -1,23 +1,42 @@
require 'json'
require 'sidekiq'

module Vero
class SidekiqWorker
include ::Sidekiq::Worker

def perform(api_class, domain, options)
api_class.constantize.new(domain, options).perform
Vero::App.log(self, "method: #{api_class}, options: #{options.to_json}, response: sidekiq job queued")
send_to_vero(api_class, domain, options)
end

protected

def send_to_vero(api_class, domain, options)
api_klass(api_class).new(domain, options).perform
Vero::App.log(self, "method: #{api_class}, options: #{JSON.dump(options)}, response: sidekiq job performed")
end

def api_klass(api_class)
eval(api_class.to_s)
end
Comment on lines +18 to 20
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Using eval here introduces potential security risks since it executes arbitrary Ruby code. The safer approach is to use Rails' constantize method which is specifically designed for class name resolution: api_class.to_s.constantize

Spotted by Graphite Reviewer

Is this helpful? React 👍 or 👎 to let us know.

end

module Senders
class Sidekiq
def call(api_class, domain, options)
response = ::Vero::SidekiqWorker.perform_async(api_class.to_s, domain, options)
Vero::App.log(self, "method: #{api_class.name}, options: #{options.to_json}, response: sidekiq job queued")
response = sender_class.perform_async(api_class.to_s, domain, options)
Vero::App.log(self, "method: #{api_class.name}, options: #{JSON.dump(options)}, response: sidekiq job queued")
response
end

def sender_class
klass = Vero::App.default_context.config.sender_class

if klass && klass.new.is_a?(::Sidekiq::Worker)
klass
else
Vero::SidekiqWorker
end
end
end
end
end
end
5 changes: 2 additions & 3 deletions lib/vero/senders/thread.rb
Original file line number Diff line number Diff line change
@@ -1,4 +1,3 @@
require 'json'
require 'sucker_punch'

module Vero
Expand All @@ -11,9 +10,9 @@ def perform(api_class, domain, options)

begin
api_class.new(domain, new_options).perform
Vero::App.log(self, "method: #{api_class.name}, options: #{options.to_json}, response: job performed")
Vero::App.log(self, "method: #{api_class.name}, options: #{JSON.dump(options)}, response: job performed")
rescue => e
Vero::App.log(self, "method: #{api_class.name}, options: #{options.to_json}, response: #{e.message}")
Vero::App.log(self, "method: #{api_class.name}, options: #{JSON.dump(options)}, response: #{e.message}")
end
end
end
Expand Down
30 changes: 28 additions & 2 deletions spec/lib/senders/sidekiq_spec.rb
Original file line number Diff line number Diff line change
@@ -1,10 +1,36 @@
require 'spec_helper'

class SomeOtherSidekiqWorker < Vero::SidekiqWorker
end

describe Vero::Senders::Sidekiq do
subject { Vero::Senders::Sidekiq.new }
describe :call do
it "should perform_async a Vero::SidekiqWorker" do
Vero::SidekiqWorker.should_receive(:perform_async).with('Vero::Api::Workers::Events::TrackAPI', "abc", {:test => "abc"}).once
Vero::SidekiqWorker.should_receive(:perform_async)
.with('Vero::Api::Workers::Events::TrackAPI', "abc", {:test => "abc"})
.once

subject.call(Vero::Api::Workers::Events::TrackAPI, "abc", {:test => "abc"})
end

it "should default to Vero::SidekiqWorker when the sender_class is invalid" do
Vero::App.default_context.config.sender_class = String

Vero::SidekiqWorker.should_receive(:perform_async)
.with('Vero::Api::Workers::Events::TrackAPI', "abc", {:test => "abc"})
.once

subject.call(Vero::Api::Workers::Events::TrackAPI, "abc", {:test => "abc"})
end

it "should allow you to define a different Sidekiq sender class" do
Vero::App.default_context.config.sender_class = SomeOtherSidekiqWorker

SomeOtherSidekiqWorker.should_receive(:perform_async)
.with('Vero::Api::Workers::Events::TrackAPI', "abc", {:test => "abc"})
.once

subject.call(Vero::Api::Workers::Events::TrackAPI, "abc", {:test => "abc"})
end
end
Expand All @@ -22,4 +48,4 @@
subject.perform('Vero::Api::Workers::Events::TrackAPI', "abc", {:test => "abc"})
end
end
end
end
2 changes: 1 addition & 1 deletion spec/spec_helper.rb
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
require 'rubygems'
require 'bundler/setup'
require 'vero'
require 'json'
require 'sucker_punch/testing/inline'
# require 'byebug'

Dir[::File.expand_path('../support/**/*.rb', __FILE__)].each { |f| require f }

Expand Down
1 change: 1 addition & 0 deletions vero.gemspec
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ Gem::Specification.new do |s|
s.authors = ['James Lamont']

dependencies = [
[:development, 'byebug'],
[:development, 'rails', "~> 3.0"],
[:development, 'rspec'],
[:development, 'delayed_job', "~> 3.0.0"],
Expand Down