Skip to content

Instantly share code, notes, and snippets.

@plusplus
Last active December 19, 2015 20:59
Show Gist options
  • Save plusplus/6016725 to your computer and use it in GitHub Desktop.
Save plusplus/6016725 to your computer and use it in GitHub Desktop.
ActiveMerchant NAB Transact scratching

Some notes:

  • This is very much a skeleton that goes JUST as far as we needed it to.
  • It's using the redirect method for the return url, rather than the proxying style. I need to think a little more about whether the POST and proxy our redirect to the client is better/worse.
  • This may not be a super correct AM integration, like I said, JUST as far as we needed to go :)
module ActiveMerchant #:nodoc:
module Billing #:nodoc:
module Integrations #:nodoc:
module NabTransactDirectPost
class Helper < ActiveMerchant::Billing::Integrations::Helper
self.country_format = :alpha3
def initialize(order, account, options = {})
super
add_field 'EPS_AMOUNT', "%.2f" % options[:amount].to_f.round(2)
add_field 'EPS_TXNTYPE', '0'
add_field 'EPS_TIMESTAMP', Time.now.utc.strftime("%Y%m%d%H%M%S")
add_field 'EPS_REDIRECT', 'TRUE'
end
mapping :order, 'EPS_REFERENCEID'
mapping :account, 'EPS_MERCHANT'
mapping :return_url, 'EPS_RESULTURL'
mapping :notify_url, 'EPS_CALLBACKURL'
def fingerprint( transaction_password )
inputs = [
form_fields['EPS_MERCHANT'],
transaction_password,
form_fields['EPS_TXNTYPE'],
form_fields['EPS_REFERENCEID'],
form_fields['EPS_AMOUNT'],
form_fields['EPS_TIMESTAMP']
]
add_field 'EPS_FINGERPRINT', Digest::SHA1.hexdigest( inputs.join("|") )
end
end
end
end
end
end
module ActiveMerchant #:nodoc:
module Billing #:nodoc:
module Integrations #:nodoc:
module NabTransactDirectPost
autoload :Return, 'active_merchant/billing/integrations/nab_transact_direct_post/return.rb'
autoload :Notification, 'active_merchant/billing/integrations/nab_transact_direct_post/notification.rb'
autoload :Helper, 'active_merchant/billing/integrations/pxpay/helper.rb'
# Overwrite this if you want to change the production url
mattr_accessor :production_url
self.production_url = 'https://transact.nab.com.au/live/directpostv2/authorise'
mattr_accessor :test_url
self.test_url = 'https://transact.nab.com.au/test/directpostv2/authorise'
def self.service_url
# mode isn't relevant as you choose what gateway via the merchant code
# TODO fill this in - we're not using the global AM test/live mode stuff
end
def self.helper( order, account, options = {})
Helper.new(order, account, options)
end
def self.notification(post, options = {})
Notification.new(post, options)
end
def self.return(query_string, options = {})
Return.new(query_string, options)
end
end
end
end
end
module ActiveMerchant #:nodoc:
module Billing #:nodoc:
module Integrations #:nodoc:
module NabTransactDirectPost
class Notification < ActiveMerchant::Billing::Integrations::Notification
def complete?
summarycode == '1'
end
def message
restext
end
def item_id
refid
end
def transaction_id
txnid
end
def status
summarycode
end
def currency
'AUD'
end
def test?
false
end
def signature_valid?
fingerprint == generate_sha1_check
end
PARAMS = [
:sig,
:summarycode,
:refid,
:rescode,
:restext,
:txnid,
:authid,
:settdate,
:preauthid,
:pan,
:expirydate,
:merchant,
:timestamp,
:fingerprint,
:callback_status_code]
PARAMS.each do |attr|
define_method(attr) do
params[attr.to_s]
end
end
SHA1_CHECK_FIELDS = [
:merchant,
:password,
:refid,
:original_amount,
:timestamp,
:summarycode
]
def generate_sha1_string
SHA1_CHECK_FIELDS.map {|f| send(f)}.join("|")
end
def generate_sha1_check
Digest::SHA1.hexdigest generate_sha1_string
end
def password
@options[:password]
end
def original_amount
cents = @options[:original_amount_cents]
if cents
"#{cents / 100}.#{'%02i' % (cents % 100)}"
end
end
def acknowledge
signature_valid?
end
end
end
end
end
end
require 'digest/sha1'
module ActiveMerchant #:nodoc:
module Billing #:nodoc:
module Integrations #:nodoc:
module NabTransactDirectPost #:nodoc:
class Return < ActiveMerchant::Billing::Integrations::Return
def initialize( query_string, options )
@notification = Notification.new( query_string, options )
end
def success?
@notification.complete? && signature_valid?
end
def message
@notification.message
end
def test?
false
end
def signature_valid?
@notification.acknowledge
end
end
end
end
end
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment