module JamRuby class EmailBatch < ActiveRecord::Base self.table_name = "email_batches" has_many :email_batch_sets, :class_name => 'JamRuby::EmailBatchSet', :dependent => :destroy has_many :email_errors, :class_name => 'JamRuby::EmailError' attr_accessible :from_email, :subject, :test_emails, :body attr_accessible :lock_version, :qualified_count, :sent_count, :started_at, :completed_at VAR_FIRST_NAME = '@FIRSTNAME' VAR_LAST_NAME = '@LASTNAME' DEFAULT_SENDER = "support@jamkazam.com" BODY_TEMPLATE =<Pellentesque facilisis metus ac cursus varius. Nunc laoreet diam mauris, et rhoncus quam commodo vel. Vestibulum nec diam lobortis, posuere sapien id, faucibus nulla. Vivamus vitae pellentesque massa. Proin quis nibh eu nibh imperdiet porttitor.

Vestibulum mollis enim eu fringilla vulputate. Nam tincidunt, enim eget fringilla blandit, mi neque dictum dolor, non pellentesque libero erat sed massa. Morbi sodales lobortis eros, sed feugiat eros euismod eget. Nulla vulputate lobortis porttitor.

Thanks for using JamKazam!

The JamKazam Team FOO include AASM aasm do state :pending, :initial => true state :testing state :tested state :batching state :batched state :disabled event :enable do transitions :from => :disabled, :to => :pending end event :reset do transitions :from => [:disabled, :testing, :tested, :batching, :batched, :pending], :to => :pending end event :do_test_run, :before => :running_tests do transitions :from => [:pending, :tested, :batched], :to => :testing end event :did_test_run, :after => :ran_tests do transitions :from => :testing, :to => :tested end event :do_batch_run, :before => :running_batch do transitions :from => [:tested, :pending, :batched], :to => :batching end event :did_batch_run, :after => :ran_batch do transitions :from => :batching, :to => :batched end event :disable do transitions :from => [:pending, :tested, :batched], :to => :disabled end end def self.create_with_params(params) obj = self.new params.each { |kk,vv| vv.strip! } params[:body] = BODY_TEMPLATE if params[:body].empty? obj.update_with_conflict_validation(params) obj end def deliver_batch self.perform_event('do_batch_run!') User.email_opt_in.find_in_batches(batch_size: 1000) do |users| self.email_batch_sets << EmailBatchSet.deliver_set(self, users.map(&:id)) # BatchMailer.send_batch_email(self.id, users.map(&:id)).deliver end end def test_count self.test_emails.split(',').count end def test_users self.test_emails.split(',').collect do |ee| ee.strip! uu = User.new uu.email = ee uu.first_name = ee.match(/^(.*)@/)[1].to_s uu.last_name = 'Test' uu end end def send_test_batch self.perform_event('do_test_run!') self.email_batch_sets << EmailBatchSet.deliver_test(self) end def merged_body(user) body.gsub(VAR_FIRST_NAME, user.first_name).gsub(VAR_LAST_NAME, user.last_name) end def did_send(emails) self.update_with_conflict_validation({ :sent_count => self.sent_count + emails.size }) if self.sent_count >= self.qualified_count if batching? self.perform_event('did_batch_run!') elsif testing? self.perform_event('did_test_run!') end end end def perform_event(event_name) num_try = 0 self.send(event_name) rescue ActiveRecord::StaleObjectError num_try += 1 if 5 > num_try self.reload retry end end def update_with_conflict_validation(*args) num_try = 0 update_attributes(*args) rescue ActiveRecord::StaleObjectError num_try += 1 if 5 > num_try self.reload retry end end def running_batch self.update_with_conflict_validation({:qualified_count => User.email_opt_in.count, :sent_count => 0, :started_at => Time.now }) end def running_tests self.update_with_conflict_validation({:qualified_count => self.test_count, :sent_count => 0, :started_at => Time.now }) end def ran_tests self.update_with_conflict_validation({ :completed_at => Time.now }) end def ran_batch self.update_with_conflict_validation({ :completed_at => Time.now }) end end end