Code Monkey home page Code Monkey logo

stymiee / authnetjson Goto Github PK

View Code? Open in Web Editor NEW
17.0 3.0 10.0 1.11 MB

Library that abstracts Authorize.Net's JSON APIs. This includes the Advanced Integration Method (AIM), Automated Recurring Billing (ARB), Customer Information Manager (CIM), Transaction Reporting, Simple Integration Method (SIM), and Webhooks.

Home Page: http://www.johnconde.net/blog/tutorial-integrate-all-authorize-net-json-apis-with-one-universal-php-class-aim-arb-cim-transaction-details/

License: Apache License 2.0

PHP 100.00%
php json-api webhook capture-transaction authorize-net authorizenet payment payment-gateway

authnetjson's Introduction

Latest Stable Version Total Downloads Scrutinizer Code Quality Build Status Code Coverage Maintainability License

AuthnetJSON

Library that abstracts Authorize.Net's JSON APIs.

Requirements

  • PHP 7.2+ (Support for PHP 7.2.0 - 8.*)
  • cURL PHP Extension
  • JSON PHP Extension
  • An Authorize.Net account

Support for PHP versions less than 7.2 has been removed from the master branch. There is a PHP 5.6 compatible branch available for development and releases for 5.6 may continue to be made as long as it is feasible to do so.

Installation

Simply add a dependency on stymiee/authnetjson to your project's composer.json file if you use Composer to manage the dependencies of your project.

Here is a minimal example of a composer.json file that just defines a dependency on AuthnetJSON:

{
    "require": {
        "stymiee/authnetjson": "~4.1"
    }
}

Basic Usage

Using this library usually consists of three steps:

  1. Initiate the library with the login credentials for your Authorize.Net account
  2. Make the API call passing any required parameters as an array
  3. Check for the results and use them appropriately

NOTE: If you are viewing any of the examples in a browser you will need to fill your Authorize.Net credentials in config.inc.php before usage

Simple usage:

$request = AuthnetApiFactory::getJsonApiHandler(AUTHNET_LOGIN, AUTHNET_TRANSKEY);
$response = $request->getTransactionDetailsRequest([
    'transId' => '2162566217'
]);
if ($response->isSuccessful()) {
    echo $response->transaction->transactionStatus;
}

The format of the array to be passed during the API call follows the structure outlined in Authorize.Net's Integration Guide.

Using the Authorize.Net Development Server

Authorize.Net provides a development environment for developers to test their integration against. To use this endpoint (as opposed to their production endpoint) set the optional third parameter of AuthnetApiFactory::getJsonApiHandler() to be 1 or use the built in class constant AuthnetApiFactory::USE_DEVELOPMENT_SERVER:

$json = AuthnetApiFactory::getJsonApiHandler(AUTHNET_LOGIN, AUTHNET_TRANSKEY, 
                                                AuthnetApiFactory::USE_DEVELOPMENT_SERVER);

Usage Examples

To help make how this library is used easier to understand example API calls are provided in the example directory. Examples for all of the current APIs calls are represented. You may need to make adjustments to get some to work as they may be dependent on valid values created from other API calls (i.e. a void will not work without a valid transaction ID).

Authorize and Capture (Basic)

$request = AuthnetApiFactory::getJsonApiHandler(AUTHNET_LOGIN, AUTHNET_TRANSKEY);
$response = $request->createTransactionRequest([
    'refId' => rand(1000000, 100000000),
    'transactionRequest' => [
        'transactionType' => 'authCaptureTransaction',
        'amount' => 5,
        'payment' => [
            'creditCard' => [
                'cardNumber' => '4111111111111111',
                'expirationDate' => '122026',
                'cardCode' => '999',
            ]
        ]
    ]
]);

if ($response->isSuccessful()) {
    echo $response->transactionResponse->authCode;
}

Authorize and Capture (Full)

$request = AuthnetApiFactory::getJsonApiHandler(AUTHNET_LOGIN, AUTHNET_TRANSKEY);
$response = $request->createTransactionRequest([
    'refId' => rand(1000000, 100000000),
    'transactionRequest' => [
        'transactionType' => 'authCaptureTransaction',
        'amount' => 5,
        'payment' => [
            'creditCard' => [
                'cardNumber' => '4111111111111111',
                'expirationDate' => '122026',
                'cardCode' => '999',
            ],
        ],
        'order' => [
            'invoiceNumber' => '1324567890',
            'description' => 'this is a test transaction',
        ],
        'lineItems' => [
            'lineItem' => [
                0 => [
                    'itemId' => '1',
                    'name' => 'vase',
                    'description' => 'Cannes logo',
                    'quantity' => '18',
                    'unitPrice' => '45.00'
                ],
                1 => [
                    'itemId' => '2',
                    'name' => 'desk',
                    'description' => 'Big Desk',
                    'quantity' => '10',
                    'unitPrice' => '85.00'
                ]
            ]
        ],
        'tax' => [
           'amount' => '4.26',
           'name' => 'level2 tax name',
           'description' => 'level2 tax',
        ],
        'duty' => [
           'amount' => '8.55',
           'name' => 'duty name',
           'description' => 'duty description',
        ],
        'shipping' => [
           'amount' => '4.26',
           'name' => 'level2 tax name',
           'description' => 'level2 tax',
        ],
        'poNumber' => '456654',
        'customer' => [
           'id' => '18',
           'email' => '[email protected]',
        ],
        'billTo' => [
           'firstName' => 'Ellen',
           'lastName' => 'Johnson',
           'company' => 'Souveniropolis',
           'address' => '14 Main Street',
           'city' => 'Pecan Springs',
           'state' => 'TX',
           'zip' => '44628',
           'country' => 'USA',
        ],
        'shipTo' => [
           'firstName' => 'China',
           'lastName' => 'Bayles',
           'company' => 'Thyme for Tea',
           'address' => '12 Main Street',
           'city' => 'Pecan Springs',
           'state' => 'TX',
           'zip' => '44628',
           'country' => 'USA',
        ],
        'customerIP' => '192.168.1.1',
        'transactionSettings' => [
            'setting' => [
                0 => [
                    'settingName' =>'allowPartialAuth',
                    'settingValue' => 'false'
                ],
                1 => [
                    'settingName' => 'duplicateWindow',
                    'settingValue' => '0'
                ],
                2 => [
                    'settingName' => 'emailCustomer',
                    'settingValue' => 'false'
                ],
                3 => [
                    'settingName' => 'recurringBilling',
                    'settingValue' => 'false'
                ],
                4 => [
                    'settingName' => 'testRequest',
                    'settingValue' => 'false'
                ]
            ]
        ],
        'userFields' => [
            'userField' => [
                0 => [
                    'name' => 'MerchantDefinedFieldName1',
                    'value' => 'MerchantDefinedFieldValue1',
                ],
                1 => [
                    'name' => 'favorite_color',
                    'value' => 'blue',
                ],
            ],
        ],
    ],
]);

if ($response->isSuccessful()) {
    echo $response->transactionResponse->authCode;
}

Create a Customer Profile

$request = AuthnetApiFactory::getJsonApiHandler(AUTHNET_LOGIN, AUTHNET_TRANSKEY);
$response = $request->createCustomerProfileRequest([
        'profile' => [
        'merchantCustomerId' => '12345',
        'email' => '[email protected]',
        'paymentProfiles' => [
            'billTo' => [
                'firstName' => 'John',
                'lastName' => 'Smith',
                'address' => '123 Main Street',
                'city' => 'Townsville',
                'state' => 'NJ',
                'zip' => '12345',
                'phoneNumber' => '800-555-1234'
            ],
            'payment' => [
                'creditCard' => [
                'cardNumber' => '4111111111111111',
                'expirationDate' => '2026-08',
                ],
            ],
        ],
        'shipToList' => [
            'firstName' => 'John',
            'lastName' => 'Smith',
            'address' => '123 Main Street',
            'city' => 'Townsville',
            'state' => 'NJ',
            'zip' => '12345',
            'phoneNumber' => '800-555-1234'
        ],
    ],
    'validationMode' => 'liveMode'
]);

if ($response->isSuccessful()) {
    echo $response->customerProfileId;
}

Create a Recurring Subscription

$request = AuthnetApiFactory::getJsonApiHandler(AUTHNET_LOGIN, AUTHNET_TRANSKEY);
$response = $request->ARBCreateSubscriptionRequest([
    'refId' => 'Sample',
    'subscription' => [
        'name' => 'Sample subscription',
        'paymentSchedule' => [
            'interval' => [
                'length' => '1',
                'unit' => 'months'
            ],
            'startDate' => '2020-04-18',
            'totalOccurrences' => '12',
            'trialOccurrences' => '1'
        ],
        'amount' => '10.29',
        'trialAmount' => '0.00',
        'payment' => [
            'creditCard' => [
                'cardNumber' => '4111111111111111',
                'expirationDate' => '2016-08'
            ]
        ],
        'billTo' => [
            'firstName' => 'John',
            'lastName' => 'Smith'
        ]
    ]
]);

if ($response->isSuccessful()) {
    echo $response->subscriptionId;
}

Get a List of Settled Batches

$request = AuthnetApiFactory::getJsonApiHandler(AUTHNET_LOGIN, AUTHNET_TRANSKEY);
$response = $request->getSettledBatchListRequest([
    'includeStatistics'   => 'true',
    'firstSettlementDate' => '2020-01-01T08:15:30',
    'lastSettlementDate'  => '2020-01-30T08:15:30',
]);

if ($response->isSuccessful()) {
    foreach ($response->batchList as $batch) {
        echo $batch->batchId;
    }
}

Get Transaction Detail From CIM API Calls

Some CIM API calls process an AUTH_CAPTURE transaction and return data similar to AIM AUTH_CAPTURE transactions. To access this information you can call AuthnetJsonResponse::getTransactionResponseField() using the field name or field number. For example, if you are looking for the transaction ID you can use:

$response->getTransactionResponseField('TransactionID');

or

$response->getTransactionResponseField(7);

Field name and number can be found in the Authorize.Net AIM Guide. Note that the field name has all spaces removed so TransactionID becomes TransactionID.

Create a Webhook

$response = $request->createWebhooks([
    "net.authorize.customer.subscription.expiring",
    "net.authorize.customer.subscription.suspended",
    "net.authorize.payment.authcapture.created",
    "net.authorize.payment.authorization.created",
    "net.authorize.payment.capture.created",
    "net.authorize.payment.fraud.approved",
    "net.authorize.payment.fraud.declined",
    "net.authorize.payment.fraud.held",
    "net.authorize.payment.priorAuthCapture.created",
    "net.authorize.payment.refund.created",
    "net.authorize.payment.void.created"
], 'http://www.example.com:55950/api/webhooks', 'active');

Validate and access a Webhook

$payload = file_get_contents("php://input");
$webhook = new AuthnetWebhook(AUTHNET_SIGNATURE, $payload);
if ($webhook->isValid()) {
    // Access notifcation values
    // echo $webhook->eventType;
}

If apache_request_headers()/getallheaders() are not available to you, you can will need to get the HTTP request headers and pass them as the third parameter to AuthnetWebhook().

$headers = yourGetHeadersFunction();
$payload = file_get_contents("php://input");
$webhook = new AuthnetWebhook(AUTHNET_SIGNATURE, $payload, $headers);
if ($webhook->isValid()) {
    // Access notifcation values
    // echo $webhook->eventType;
}

Accept.js

To see examples of an Accept.js powered self hosted payment form, an Authorize.Net hosted payment form, and a hosted customer profile page, visit the Accept.js examples directory.

Debugging

To assist with debugging the __toString() method has been overridden to output important elements pertaining to the usage of this library. Simple echo your AuthnetJSON object to see:

  • The API Login ID used
  • The API transaction Key used
  • The API endpoint the request was sent to
  • The request JSON
  • The response JSON

Basic Usage:

$request = AuthnetApiFactory::getJsonApiHandler(AUTHNET_LOGIN, AUTHNET_TRANSKEY);
$response = $request->getUnsettledTransactionListRequest();
echo $request, $response;

Support

If you require assistance using this library start by viewing the HELP.md file included in this package. It includes common problems and their solutions.

If you need additional assistance, I can be found at Stack Overflow. Be sure when you ask a question pertaining to the usage of this class be sure to tag your question with the PHP and Authorize.Net tags. Make sure you follow their guide for asking a good question as poorly asked questions will be closed and I will not be able to assist you.

Do not use Stack Overflow to report bugs. Bugs may be reported here.

authnetjson's People

Contributors

mmeyer2k avatar stymiee avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar

authnetjson's Issues

Fatal error: Unsupported operand types in authnetjson-php56\src\authnet\AuthnetJsonRequest.php on line 159

I have this error when create subscription by ARBCreateSubscriptionRequest

My data:

$charge = [
	'refId' => 'DNHKTXU5AWC7P3IB4',
        'subscription' => [
            'name' => 'DNHKTXU5AWC7P3IB4',
            'paymentSchedule' => [
                'interval' => [
			'length' => 1,
			'unit'   => 'months'
                ],
                'startDate' => date('Y-m-d'),
                'totalOccurrences' => 6,
                'trialOccurrences' => 0
            ],
            'trialAmount' => 0,
            'amount' => 9,
	    'payment' => [
	            'creditCard' => [
                            'cardNumber' => '4111111111111111',
                            'expirationDate' => '2022-10',
                            'cardCode' => '123'
                    ],
	        ],
            'order' => [
		'invoiceNumber' => 'DNHKTXU5AWC7P3IB4',
		'description'   => 'Sell Movie Tickets Online for VIP: Monthly',
            ]
        ]
];

AuthnetJsonResponse.php getErrorText() & getErrorCode() bug

I believe there is a bug based on Authorize.Net documentation. In both functions getErrorText() and getErrorCode() you have this code block:

if (@$this->transactionResponse->errors[0]->errorText) {
    $message = $this->transactionResponse->errors[0]->errorText;
}

Looking at the Authorize.Net documentation for the Response I see errors outlined as such:

errors | This element contains one or more error elements.

So I believe the above code block should be written as such:

if (@$this->transactionResponse->errors->error[0]->errorText) {
    $message = $this->transactionResponse->errors->error[0]->errorText;
}

Error when trying to create webhook or getting notification for ARB with webhooks

Authnetjson\AuthnetJsonResponse Object
(
    [response:Authnetjson\AuthnetJsonResponse:private] => stdClass Object
        (
            [messages] => stdClass Object
                (
                    [resultCode] => Error
                    [message] => Array
                        (
                            [0] => stdClass Object
                                (
                                    [code] => E00003
                                    [text] => The 'AnetApi/xml/v1/schema/AnetApiSchema.xsd:createWebhooks' element is not declared.
                                )

                        )

                )

        )

    [responseJson:Authnetjson\AuthnetJsonResponse:private] => {"messages":{"resultCode":"Error","message":[{"code":"E00003","text":"The 'AnetApi/xml/v1/schema/AnetApiSchema.xsd:createWebhooks' element is not declared."}]}}
    [transactionInfo:Authnetjson\AuthnetJsonResponse:private] => 
    [transactionInfoArray:Authnetjson\AuthnetJsonResponse:private] => 
)

code for creating webhook:

$request = AuthnetApiFactory::getJsonApiHandler(
                    MERCHANT_LOGIN_ID,
    				MERCHANT_TRANSACTION_KEY,
                    AuthnetApiFactory::USE_PRODUCTION_SERVER
                );
        $response = $request->createWebhooks([
            "net.authorize.customer.subscription.expiring",
            "net.authorize.customer.subscription.suspended",
            "net.authorize.payment.authcapture.created",
            "net.authorize.payment.authorization.created",
            "net.authorize.payment.capture.created",
            "net.authorize.payment.fraud.approved",
            "net.authorize.payment.fraud.declined",
            "net.authorize.payment.fraud.held",
            "net.authorize.payment.priorAuthCapture.created",
            "net.authorize.payment.refund.created",
            "net.authorize.payment.void.created"
        ], 'http://www.example.com:55950/api/webhooks', 'active');
        
        echo "<pre>";
        print_r($response);

Code for webhook Notification:

        $payload = file_get_contents("php://input");
        $webhook = new AuthnetWebhook(AUTHNET_SIGNATURE, $payload);
        if ($webhook->isValid()) {
            // Get the transaction ID
            $transactionId = $webhook->payload->id;
         
            // Here you can get more information about the transaction
            $request = AuthnetApiFactory::getJsonApiHandler(
                    MERCHANT_LOGIN_ID,
    				MERCHANT_TRANSACTION_KEY,
                    AuthnetApiFactory::USE_DEVELOPMENT_SERVER
                );
            $response = $request->getTransactionDetailsRequest([
                'transId' => $transactionId
            ]);
         
            /* You can put these response values in the database or whatever your business logic dictates.
            $response->transaction->transactionType
            $response->transaction->transactionStatus
            $response->transaction->authCode
            $response->transaction->AVSResponse
            */
        }

error at: $webhook = new AuthnetWebhook(AUTHNET_SIGNATURE, $payload); // code does not pass here.

getTransactionDetailsRequest Sample Code Not Working

I am having some difficulty with the getTransactionDetailsRequest part of your sample code. Whenever I run the following the results from transactionType and transactionStatus are empty:

$transactionId = $webhook->payload->id;
    $merchantrefid = $webhook->payload->merchantReferenceId;
    $eventtype = $webhook->eventType;
    // Here you can get more information about the transaction
    $request  = AuthnetApiFactory::getJsonApiHandler(\SampleCodeConstants::MERCHANT_LOGIN_ID, \SampleCodeConstants::MERCHANT_TRANSACTION_KEY);
    $response = $request->getTransactionDetailsRequest(array(
        'transId' => $transactionId,
    ));
    $transtype = $response->transaction->transactionType;
    $transstatus = $response->transaction->transactionStatus;
    if($eventtype == 'net.authorize.payment.authcapture.created')
    {
        print_log('TID = ' . $transactionId.' RefID = '.$merchantrefid.' EventType = '.$eventtype.' TransactionType = '.$transtype.' TransactionStatus = '.$transstatus);
    }

Suggestion: more robust error code / message handling

For transactions with response codes 2-4 I'm interested in logging the error/message code and text. AuthnetJsonResponse::getErrorCode() and getErrorText() is basically what I want, but those are conditional on isError().

In some of the transactions I'm seeing, the Authorize.net API call was successful, but the transaction failed (card declined). So the above functions return empty strings, even though there is a transactionResponse->errors or transactionResponse->messages in the response.

I'm not sure the best way to add this functionality, but perhaps adding something like getTransactionErrorCode and getTransactionErrorText functions that always return those values, regardless of the isError.

I can manually work around this for now, just wanted to make a suggestion.

Namespacing for Exception folder isn't quite right.

Changing namespaces was a big BC change and should have been done under a 5.0 release. Anyway, the new namespace isn't quite PSR-0/4 compliant. It should be:

"autoload": {
    "psr-4": {
        "Authnetjson\\": "src/Authnetjson/"
    }
},

And the namespace for the Exceptions folder should be:

namespace Authnetjson/Exception;

image

If you don't get to it, I'll try to make a PR by the end of the week.

CURL Class not found

Hii

Im using authnet
when i run /examples/aim/createTransactionRequest_authCapture.php file ....

giving an error

Class 'Curl\Curl' not found in src\authnet\AuthnetApiFactory.php on line 63

Webhook returned as not valid if apache_request_headers isn't defined

The getAllHeaders() method in AuthnetWebhook provides a workaround for situations where apache_request_headers() isn't defined, but it's incorrect.

protected function getAllHeaders()
    {
        if (function_exists('apache_request_headers')) {
            $headers = apache_request_headers();
        } else {
            $headers = array_filter($_SERVER, function($key) {
                return strpos($key, 'HTTP_') === 0;
            }, ARRAY_FILTER_USE_KEY);
        }
        return $headers;
    }

The headers array when using the non-Apache method is different to the Apache version. For one, all the header keys start with HTTP_ and they also use underscores instead of dashes. i.e.

HTTP_X_ANET_SIGNATURE instead of X-ANET-SIGNATURE

Hence, the isset() check in isValid() fails.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.