class SolidusSubscriptions::Processor

Attributes

users[R]

@return [Array<Spree.user_class>]

Public Class Methods

new(users) click to toggle source

Get a new instance of the SolidusSubscriptions::Processor

@param users [Array<Spree.user_class>] A list of users with actionable

subscriptions or installments

@return [SolidusSubscriptions::Processor]

# File lib/solidus_subscriptions/processor.rb, line 51
def initialize(users)
  @users = users
  @installments = {}
end
run() click to toggle source

Find all actionable subscriptions and intallments, group them together by user, and schedule a processing job for the group as a batch

# File lib/solidus_subscriptions/processor.rb, line 15
def run
  batched_users_to_be_processed.each { |batch| new(batch).build_jobs }
end

Private Class Methods

batched_users_to_be_processed() click to toggle source
# File lib/solidus_subscriptions/processor.rb, line 21
def batched_users_to_be_processed
  subscriptions = SolidusSubscriptions::Subscription.arel_table
  installments = SolidusSubscriptions::Installment.arel_table

  Spree::User.
    joins(:subscriptions).
    joins(
      subscriptions.
        join(installments, Arel::Nodes::OuterJoin).
        on(subscriptions[:id].eq(installments[:subscription_id])).
        join_sources
    ).
    where(
      SolidusSubscriptions::Subscription.actionable.arel.constraints.reduce(:and).
        or(SolidusSubscriptions::Installment.actionable.arel.constraints.reduce(:and))
    ).
    distinct.
    find_in_batches
end

Public Instance Methods

build_jobs() click to toggle source

Create `ProcessInstallmentsJob`s for the users used to initalize the instance

# File lib/solidus_subscriptions/processor.rb, line 58
def build_jobs
  users.map do |user|
    installemts_by_address_and_user = installments(user).group_by do |i|
      i.subscription.shipping_address_id
    end

    installemts_by_address_and_user.values.each do |grouped_installments|
      ProcessInstallmentsJob.perform_later grouped_installments.map(&:id)
    end
  end
end

Private Instance Methods

installments(user) click to toggle source
# File lib/solidus_subscriptions/processor.rb, line 88
def installments(user)
  @installments[user.id] ||= retry_installments.fetch(user.id, []) + new_installments(user)
end
new_installments(user) click to toggle source
# File lib/solidus_subscriptions/processor.rb, line 92
def new_installments(user)
  ActiveRecord::Base.transaction do
    subscriptions_by_id.fetch(user.id, []).map do |sub|
      sub.successive_skip_count = 0
      sub.advance_actionable_date
      sub.cancel! if sub.pending_cancellation?
      sub.deactivate! if sub.can_be_deactivated?
      sub.installments.create!
    end
  end
end
retry_installments() click to toggle source
# File lib/solidus_subscriptions/processor.rb, line 80
def retry_installments
  @failed_installments ||= Installment.
    actionable.
    includes(:subscription).
    where(solidus_subscriptions_subscriptions: { user_id: user_ids }).
    group_by { |i| i.subscription.user_id }
end
subscriptions_by_id() click to toggle source
# File lib/solidus_subscriptions/processor.rb, line 72
def subscriptions_by_id
  @subscriptions_by_id ||= Subscription.
    actionable.
    includes(:line_items, :user).
    where(user_id: user_ids).
    group_by(&:user_id)
end
user_ids() click to toggle source
# File lib/solidus_subscriptions/processor.rb, line 104
def user_ids
  @user_ids ||= users.map(&:id)
end