{"id":22706820,"url":"https://github.com/bigbinary/binary_merchant","last_synced_at":"2025-03-29T20:43:37.701Z","repository":{"id":66807135,"uuid":"2346533","full_name":"bigbinary/binary_merchant","owner":"bigbinary","description":"A payment processing utility tool built on top of Active Merchant","archived":false,"fork":false,"pushed_at":"2012-04-14T16:05:25.000Z","size":146,"stargazers_count":2,"open_issues_count":0,"forks_count":1,"subscribers_count":2,"default_branch":"master","last_synced_at":"2025-02-04T21:43:26.666Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":"","language":"Ruby","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/bigbinary.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null}},"created_at":"2011-09-08T05:14:23.000Z","updated_at":"2017-05-21T05:29:58.000Z","dependencies_parsed_at":"2023-02-20T12:01:00.049Z","dependency_job_id":null,"html_url":"https://github.com/bigbinary/binary_merchant","commit_stats":null,"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/bigbinary%2Fbinary_merchant","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/bigbinary%2Fbinary_merchant/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/bigbinary%2Fbinary_merchant/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/bigbinary%2Fbinary_merchant/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/bigbinary","download_url":"https://codeload.github.com/bigbinary/binary_merchant/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":246243565,"owners_count":20746307,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":[],"created_at":"2024-12-10T10:09:48.339Z","updated_at":"2025-03-29T20:43:37.680Z","avatar_url":"https://github.com/bigbinary.png","language":"Ruby","readme":"# BinaryMerchant\n\n### Update: This gem has been discontinued. Please do not use this gem ###\n\nIt is a payment processing utility tool built on top of [Active Merchant](https://github.com/shopify/active_merchant) .\n\nCurrently BinaryMerchant supports \u003cstrong\u003eAuthorizeNetGateway\u003c/strong\u003e and \u003cstrong\u003eAuthorizeNetCimGateway\u003c/strong\u003e gateways.\n\nThe API provided by Authorize.net CIM could be a bit confusing. Active Merchant has good job of hiding the complexity. However BinaryMerchant makes it even simpler.\n\n## Show me an example of how BinaryMerchant is simpler than ActiveMerchant\n\nLet's say you are making an authorization request with Authorize.net using \u003ctt\u003eAuthorizeNetCimGateway\u003c/tt\u003e . Using ActiveMechant your code will look like this.\n\n```ruby\noptions = { transaction: { type: :auth_only, amount: amount,\n                           customer_profile_id: customer_profile_id,\n                           customer_payment_profile_id: customer_payment_profile_id }}\nresponse = gateway.create_customer_profile_transaction(options)\nif response.success?\n  transaction_id = response.params['direct_response']['transaction_id']\nelse\n  transaction_id = nil\nend\n```\n\nIn the above case method named \u003ctt\u003ecreate_customer_profile_transaction\u003c/tt\u003e was invoked. Also when you get the response object you\nneed to do \u003ctt\u003eresponse.params['direct_response']['transaction_id']\u003c/tt\u003e .\n\nWith BinaryMerchant above could could be written as\n\n```ruby\noptions = {amount: amount, customer_profile_id: customer_profile_id, customer_payment_id: customer_payment_id}\ntransaction_id, response = *gateway.authorize(options)\n```\n\nIn the above case you are calling a method called \u003ctt\u003eauthorize\u003c/tt\u003e which is much better to look at than a method named \u003ctt\u003ecreate_customer_profile_transaction\u003c/tt\u003e. If the authorization was a success then \u003ctt\u003etransaction_id\u003c/tt\u003e will have a value. If authorization fails then transaction_id will be nil.\n\n## Testing with BinaryMerchant without hitting the Authorize.net server\n\nYou have built your application using \u003cstrong\u003eAuthorizeNetCimGateway\u003c/strong\u003e. Now you want to test your code. Howver you do not want to hit Authorize.net server during tests. Well you can mock the requests with stub . But before that you need to know what params to expect in response. BinaryMerchant has figured all that out for you.\n\nThis gem provides a gateway called \u003ctt\u003eAuthorizeNetCimMockedGateway\u003c/tt\u003e and this gateway returns predefined responses and does not hit Authorize.net server.\n\nPut the following code at \u003ctt\u003econfig/intializers/binary_merchant.rb\u003c/tt\u003e and now in test you are using mocked gateway.\n\n```ruby\ncredentials = { login: login_id_provided_by_authorize_dot_net,\n                password: transaction_key_provided_by_authorize_net }\n\nActiveMerchant::Billing::Base.mode = Rails.env.production? ? :production : :test\n\ngateway_klass = if Rails.env.test?\n  ActiveMerchant::Billing::AuthorizeNetCimMockedGateway\nelse\n  ActiveMerchant::Billing::AuthorizeNetCimGateway\nend\n\ngateway_klass.logger = Rails.logger\n\n::ADNCIMP = BinaryMerchant::AuthorizeNetCimGateway.new( gateway_klass.new(credentials) )\n```\n\nAbove we configured the gateway. Now let's see a concrete example. Let's say whenver a user record is created we want to create \u003ctt\u003ecustomer_profile_id\u003c/tt\u003e for that record. The code would look something like this.\n\n```\nclass User \u003c ActiveRecord::Base\n  before_create :create_customer_profile_id\n\n  private\n\n  def create_customer_profile_id\n   _vault_id, response = *(ADNCIMP.add_user(email: self.email))\n   if _vault_id\n     self.vault_id = _vault_id\n   else\n     raise \"customer_profile_id could not be created\"\n   end\n  end\nend\n```\n\nTest for above code would be like\n\n```\ndescribe User do\n  context \"customer_profile_id\" do\n    it \"without roundtrip\" do\n      user = Factory(:user)\n      user.vault_id.should_not be_nil\n      user.vault_id.should == ActiveMerchant::Billing::AuthorizeNetCimMockedGateway::CUSTOMER_PROFILE_ID\n    end\n  end\nend\n```\n\nIn the above case the call to gateway is intercepted and a response object is returned.\n\n## Testing with BinaryMerchnat with full roundtrip\n\nTesting using above mechanism works. However it has one issue. ActiveMerchant does a number of validation checks while building the xml. In the above case xml is never built. To do exhaustive testing we would like xml to be built. Howver that xml should not be sent to Authorize.net .  Here is how you can do full roundtrip testing.\n\n```\ndescribe User do\n  before do\n    ADNCIMP.gateway.make_roundtrip = false\n  end\n  context \"customer_profile_id\" do\n    it \"with roundtrip\" do\n      ADNCIMP.gateway.make_roundtrip = true\n      user = Factory(:user)\n      user.vault_id.should_not be_nil\n      user.vault_id.should == \"4581836\"\n    end\n    it \"without roundtrip\" do\n      user = Factory(:user)\n      user.vault_id.should_not be_nil\n      user.vault_id.should == ActiveMerchant::Billing::AuthorizeNetCimMockedGateway::CUSTOMER_PROFILE_ID\n    end\n  end\nend\n```\n\nBy default \u003ctt\u003emake_roundtrip\u003c/tt\u003e value is false.\n\n## Stronger validations\n\nActiveMerchant has validations to ensure that needed require fields are passed. For example when update the customer profile using \u003ctt\u003eAuthorizeNetCimGateway\u003c/tt\u003e the method should look like this\n\n```ruby\ngateway.update_customer_profile({customer_profile_id: '2358805854', email: 'newemail@example.com'})\n```\n\nIn the above code if you forget to pass the key \u003ctt\u003ecustomer_profile_id\u003c/tt\u003e then ActiveMerchant will raise an error indicating that key \u003ctt\u003ecustomer_profile_id\u003c/tt\u003e is required.\n\nHowever if you pass the value \u003ctt\u003enil\u003c/tt\u003e for key \u003ctt\u003ecustomer_profile_id\u003c/tt\u003e then ActiveMerchant will not complain during validations. However the code fails somewhere deep down and I had to spend some time debugging it. BinaryMerchant strengthenes that validations by ensuring that for every required key the value passed must also be not nil.\n\n## Tip: Logging of xml in development\n\nIn development you can see the xml that is sent to gateway and the response that is received from the gateway by adding\nfollowing line.\n\n```ruby\ngateway_klass.logger = Rails.logger\n","funding_links":[],"categories":[],"sub_categories":[],"project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fbigbinary%2Fbinary_merchant","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fbigbinary%2Fbinary_merchant","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fbigbinary%2Fbinary_merchant/lists"}