# frozen_string_literal: true class Subscription < ApplicationRecord include SetUnusedAddressFields ALLOWED_PAYMENT_METHOD_TYPES = ["Spree::PaymentMethod::Check", "Spree::Gateway::StripeSCA"].freeze self.belongs_to_required_by_default = false searchable_attributes :shop_id, :canceled_at, :paused_at searchable_associations :shop searchable_scopes :active, :not_ended, :not_paused, :not_canceled belongs_to :shop, class_name: 'Enterprise' belongs_to :customer belongs_to :schedule belongs_to :shipping_method, class_name: 'Spree::ShippingMethod' belongs_to :payment_method, class_name: 'Spree::PaymentMethod' belongs_to :bill_address, class_name: "Spree::Address" belongs_to :ship_address, class_name: "Spree::Address" has_many :subscription_line_items, inverse_of: :subscription, dependent: :destroy has_many :order_cycles, through: :schedule has_many :proxy_orders, dependent: :destroy has_many :orders, through: :proxy_orders alias_method :billing_address, :bill_address alias_method :billing_address=, :bill_address= alias_method :shipping_address, :ship_address alias_method :shipping_address=, :ship_address= accepts_nested_attributes_for :subscription_line_items, allow_destroy: true accepts_nested_attributes_for :bill_address, :ship_address scope :not_ended, -> { where('subscriptions.ends_at > (?) OR subscriptions.ends_at IS NULL', Time.zone.now) } scope :not_canceled, -> { where(subscriptions: { canceled_at: nil }) } scope :not_paused, -> { where(subscriptions: { paused_at: nil }) } scope :active, -> { not_canceled.not_ended.not_paused.where('subscriptions.begins_at <= (?)', Time.zone.now) } def closed_proxy_orders proxy_orders.closed end def not_closed_proxy_orders proxy_orders.not_closed end def cancel(keep_ids = []) transaction do update_column(:canceled_at, Time.zone.now) proxy_orders.reject{ |o| keep_ids.include? o.id }.each(&:cancel) true end end def canceled? canceled_at.present? end def paused? paused_at.present? end def state # NOTE: the order is important here %w(canceled paused pending ended).each do |state| return state if __send__("#{state}?") end "active" end # Used to calculators to estimate fees def line_items subscription_line_items end private def pending? return true unless begins_at begins_at > Time.zone.now end def ended? return false unless ends_at ends_at < Time.zone.now end end