var.rb 2.51 KB
require "var/version"
require 'conekta'

module Var
  @@valid_services = [:conekta]

  def self.valid_services
    @@valid_services
  end

  def self.create_charge(service, object, options = {})
    if(!@@valid_services.include?(service))
      return { error_message: 'Service is not supported' }
    end
    if(!object.respond_to?(:charge_with))
      return { error_message: "#{object.class.to_s} doesn't support charges"}
    end
    object.charge_with(:conekta, options)
  end
end

module ActsAsChargeable
  extend ActiveSupport::Concern

  module ClassMethods
    def acts_as_chargeable(keys = {})
      include ChargeableInstanceMethods
      cattr_accessor :sync_attributes
      self.sync_attributes = keys
    end
  end

  module ChargeableInstanceMethods
    def charge_with(service, options)
      begin
        self.send("charge_with_#{service.to_s}", options)
      rescue => exception
        return { error_message: exception.message }
      end
    end

    def charge_with_conekta(options)
      if(!options.include? :card_token)
        error_message = "Conekta needs a card token sent as a third paramater"
        return { error_message: error_message}
      end
      @charge ||= Conekta::Charge.create({
        description: self.sync_attribute('description'),
        amount: self.sync_attribute('amount'),
        currency: "MXN",
        reference_id: self.sync_attribute('reference_id'),
        card: options[:card_token],
        details: {
          name: self.sync_attribute('details_name'),
          email: self.sync_attribute('details_email'),
          line_items: [{
            name: self.sync_attribute('details_name'),
            description: self.sync_attribute('description'),
            unit_price: self.sync_attribute('amount'),
            quantity: 1,
          }]
        }
      })
    end

    def find_charge(service)
      begin
        if(!Var.valid_services.include?(service))
          return { error_message: 'Service is not supported' }
        end
        self.send("find_#{service.to_s}_charge")
      rescue => exception
        return { error_message: exception.message }
      end
    end

    def find_conekta_charge
      ref_id = self.sync_attribute('reference_id')
      Conekta::Charge.where({'status.ne'=>'paid', 'reference_id'=> ref_id})
    end

    def sync_attribute(key)
      return self.send(key) unless self.sync_attributes.include? key.to_sym
      self.send(sync_attributes[key.to_sym])
    end
  end
end

ActiveRecord::Base.send(:include, ActsAsChargeable) if defined? ActiveRecord::Base