Commit inicial - WordPress Análisis de Precios Unitarios

- WordPress core y plugins
- Tema Twenty Twenty-Four configurado
- Plugin allow-unfiltered-html.php simplificado
- .gitignore configurado para excluir wp-config.php y uploads

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
root
2025-11-03 21:04:30 -06:00
commit a22573bf0b
24068 changed files with 4993111 additions and 0 deletions

View File

@@ -0,0 +1,24 @@
<?php
/**
* Braintree PHP Library
* Creates class_aliases for old class names replaced by PSR-4 Namespaces
*/
require_once(__DIR__ . DIRECTORY_SEPARATOR . 'autoload.php');
if (version_compare(PHP_VERSION, '5.4.0', '<')) {
throw new Braintree_Exception('PHP version >= 5.4.0 required');
}
class Braintree {
public static function requireDependencies() {
$requiredExtensions = ['xmlwriter', 'openssl', 'dom', 'hash', 'curl'];
foreach ($requiredExtensions AS $ext) {
if (!extension_loaded($ext)) {
throw new Braintree_Exception('The Braintree library requires the ' . $ext . ' extension.');
}
}
}
}
Braintree::requireDependencies();

View File

@@ -0,0 +1,43 @@
<?php
namespace Braintree;
/**
* Creates an instance of AccountUpdaterDailyReport
*
*
* @package Braintree
*
* @property-read string $reportUrl
* @property-read date $reportDate
*/
class AccountUpdaterDailyReport extends Base
{
protected $_attributes = [];
protected function _initialize($disputeAttribs)
{
$this->_attributes = $disputeAttribs;
}
public static function factory($attributes)
{
$instance = new self();
$instance->_initialize($attributes);
return $instance;
}
public function __toString()
{
$display = [
'reportDate', 'reportUrl'
];
$displayAttributes = [];
foreach ($display AS $attrib) {
$displayAttributes[$attrib] = $this->$attrib;
}
return __CLASS__ . '[' .
Util::attributesToString($displayAttributes) .']';
}
}
class_alias('Braintree\AccountUpdaterDailyReport', 'Braintree_AccountUpdaterDailyReport');

View File

@@ -0,0 +1,55 @@
<?php
namespace Braintree;
/**
* Braintree AchMandate module
* PHP Version 5
*
* @package Braintree
*
* @property-read string $text
* @property-read string $acceptedAt
*/
class AchMandate extends Base
{
/**
* create a printable representation of the object as:
* ClassName[property=value, property=value]
* @ignore
* @return string
*/
public function __toString()
{
return __CLASS__ . '[' .
Util::attributesToString($this->_attributes) . ']';
}
/**
* sets instance properties from an array of values
*
* @ignore
* @access protected
* @param array $achAttribs array of achMandate data
* @return void
*/
protected function _initialize($achAttribs)
{
// set the attributes
$this->_attributes = $achAttribs;
}
/**
* factory method: returns an instance of AchMandate
* to the requesting method, with populated properties
* @ignore
* @return AchMandate
*/
public static function factory($attributes)
{
$instance = new self();
$instance->_initialize($attributes);
return $instance;
}
}
class_alias('Braintree\AchMandate', 'Braintree_Mandate');

View File

@@ -0,0 +1,43 @@
<?php
namespace Braintree;
/**
* @property-read string $amount
* @property-read \DateTime $createdAt
* @property-read int|null $currentBillingCycle
* @property-read string $description
* @property-read string $id
* @property-read string|null $kind
* @property-read string $merchantId
* @property-read string $name
* @property-read boolean $neverExpires
* @property-read int|null $numberOfBillingCycles
* @property-read int|null $quantity
* @property-read \DateTime $updatedAt
*/
class AddOn extends Modification
{
/**
*
* @param array $attributes
* @return AddOn
*/
public static function factory($attributes)
{
$instance = new self();
$instance->_initialize($attributes);
return $instance;
}
/**
* static methods redirecting to gateway
*
* @return AddOn[]
*/
public static function all()
{
return Configuration::gateway()->addOn()->all();
}
}
class_alias('Braintree\AddOn', 'Braintree_AddOn');

View File

@@ -0,0 +1,53 @@
<?php
namespace Braintree;
class AddOnGateway
{
/**
*
* @var Gateway
*/
private $_gateway;
/**
*
* @var Configuration
*/
private $_config;
/**
*
* @var Http
*/
private $_http;
/**
*
* @param Gateway $gateway
*/
public function __construct($gateway)
{
$this->_gateway = $gateway;
$this->_config = $gateway->config;
$this->_config->assertHasAccessTokenOrKeys();
$this->_http = new Http($gateway->config);
}
/**
*
* @return AddOn[]
*/
public function all()
{
$path = $this->_config->merchantPath() . '/add_ons';
$response = $this->_http->get($path);
$addOns = ["addOn" => $response['addOns']];
return Util::extractAttributeAsArray(
$addOns,
'addOn'
);
}
}
class_alias('Braintree\AddOnGateway', 'Braintree_AddOnGateway');

View File

@@ -0,0 +1,150 @@
<?php
namespace Braintree;
/**
* Braintree Address module
* PHP Version 5
* Creates and manages Braintree Addresses
*
* An Address belongs to a Customer. It can be associated to a
* CreditCard as the billing address. It can also be used
* as the shipping address when creating a Transaction.
*
* @package Braintree
*
* @property-read string $company
* @property-read string $countryName
* @property-read \DateTime $createdAt
* @property-read string $customerId
* @property-read string $extendedAddress
* @property-read string $firstName
* @property-read string $id
* @property-read string $lastName
* @property-read string $locality
* @property-read string $postalCode
* @property-read string $region
* @property-read string $streetAddress
* @property-read \DateTime $updatedAt
*/
class Address extends Base
{
/**
* returns false if comparing object is not a Address,
* or is a Address with a different id
*
* @param object $other address to compare against
* @return boolean
*/
public function isEqual($other)
{
return !($other instanceof self) ?
false :
($this->id === $other->id && $this->customerId === $other->customerId);
}
/**
* create a printable representation of the object as:
* ClassName[property=value, property=value]
* @ignore
* @return string
*/
public function __toString()
{
return __CLASS__ . '[' .
Util::attributesToString($this->_attributes) . ']';
}
/**
* sets instance properties from an array of values
*
* @ignore
* @access protected
* @param array $addressAttribs array of address data
* @return void
*/
protected function _initialize($addressAttribs)
{
// set the attributes
$this->_attributes = $addressAttribs;
}
/**
* factory method: returns an instance of Address
* to the requesting method, with populated properties
* @ignore
* @return Address
*/
public static function factory($attributes)
{
$instance = new self();
$instance->_initialize($attributes);
return $instance;
}
// static methods redirecting to gateway
/**
*
* @param array $attribs
* @return Address
*/
public static function create($attribs)
{
return Configuration::gateway()->address()->create($attribs);
}
/**
*
* @param array $attribs
* @return Address
*/
public static function createNoValidate($attribs)
{
return Configuration::gateway()->address()->createNoValidate($attribs);
}
/**
*
* @param Customer|int $customerOrId
* @param int $addressId
* @throws InvalidArgumentException
* @return Result\Successful
*/
public static function delete($customerOrId = null, $addressId = null)
{
return Configuration::gateway()->address()->delete($customerOrId, $addressId);
}
/**
*
* @param Customer|int $customerOrId
* @param int $addressId
* @throws Exception\NotFound
* @return Address
*/
public static function find($customerOrId, $addressId)
{
return Configuration::gateway()->address()->find($customerOrId, $addressId);
}
/**
*
* @param Customer|int $customerOrId
* @param int $addressId
* @param array $attributes
* @throws Exception\Unexpected
* @return Result\Successful|Result\Error
*/
public static function update($customerOrId, $addressId, $attributes)
{
return Configuration::gateway()->address()->update($customerOrId, $addressId, $attributes);
}
public static function updateNoValidate($customerOrId, $addressId, $attributes)
{
return Configuration::gateway()->address()->updateNoValidate($customerOrId, $addressId, $attributes);
}
}
class_alias('Braintree\Address', 'Braintree_Address');

View File

@@ -0,0 +1,314 @@
<?php
namespace Braintree;
use InvalidArgumentException;
/**
* Braintree AddressGateway module
* PHP Version 5
* Creates and manages Braintree Addresses
*
* An Address belongs to a Customer. It can be associated to a
* CreditCard as the billing address. It can also be used
* as the shipping address when creating a Transaction.
*
* @package Braintree
*/
class AddressGateway
{
/**
*
* @var Gateway
*/
private $_gateway;
/**
*
* @var Configuration
*/
private $_config;
/**
*
* @var Http
*/
private $_http;
/**
*
* @param Gateway $gateway
*/
public function __construct($gateway)
{
$this->_gateway = $gateway;
$this->_config = $gateway->config;
$this->_config->assertHasAccessTokenOrKeys();
$this->_http = new Http($gateway->config);
}
/* public class methods */
/**
*
* @access public
* @param array $attribs
* @return Result\Successful|Result\Error
*/
public function create($attribs)
{
Util::verifyKeys(self::createSignature(), $attribs);
$customerId = isset($attribs['customerId']) ?
$attribs['customerId'] :
null;
$this->_validateCustomerId($customerId);
unset($attribs['customerId']);
try {
return $this->_doCreate(
'/customers/' . $customerId . '/addresses',
['address' => $attribs]
);
} catch (Exception\NotFound $e) {
throw new Exception\NotFound(
'Customer ' . $customerId . ' not found.'
);
}
}
/**
* attempts the create operation assuming all data will validate
* returns a Address object instead of a Result
*
* @access public
* @param array $attribs
* @return self
* @throws Exception\ValidationError
*/
public function createNoValidate($attribs)
{
$result = $this->create($attribs);
return Util::returnObjectOrThrowException(__CLASS__, $result);
}
/**
* delete an address by id
*
* @param mixed $customerOrId
* @param string $addressId
*/
public function delete($customerOrId = null, $addressId = null)
{
$this->_validateId($addressId);
$customerId = $this->_determineCustomerId($customerOrId);
$path = $this->_config->merchantPath() . '/customers/' . $customerId . '/addresses/' . $addressId;
$this->_http->delete($path);
return new Result\Successful();
}
/**
* find an address by id
*
* Finds the address with the given <b>addressId</b> that is associated
* to the given <b>customerOrId</b>.
* If the address cannot be found, a NotFound exception will be thrown.
*
*
* @access public
* @param mixed $customerOrId
* @param string $addressId
* @return Address
* @throws Exception\NotFound
*/
public function find($customerOrId, $addressId)
{
$customerId = $this->_determineCustomerId($customerOrId);
$this->_validateId($addressId);
try {
$path = $this->_config->merchantPath() . '/customers/' . $customerId . '/addresses/' . $addressId;
$response = $this->_http->get($path);
return Address::factory($response['address']);
} catch (Exception\NotFound $e) {
throw new Exception\NotFound(
'address for customer ' . $customerId .
' with id ' . $addressId . ' not found.'
);
}
}
/**
* updates the address record
*
* if calling this method in context,
* customerOrId is the 2nd attribute, addressId 3rd.
* customerOrId & addressId are not sent in object context.
*
*
* @access public
* @param array $attributes
* @param mixed $customerOrId (only used in call)
* @param string $addressId (only used in call)
* @return Result\Successful|Result\Error
*/
public function update($customerOrId, $addressId, $attributes)
{
$this->_validateId($addressId);
$customerId = $this->_determineCustomerId($customerOrId);
Util::verifyKeys(self::updateSignature(), $attributes);
$path = $this->_config->merchantPath() . '/customers/' . $customerId . '/addresses/' . $addressId;
$response = $this->_http->put($path, ['address' => $attributes]);
return $this->_verifyGatewayResponse($response);
}
/**
* update an address record, assuming validations will pass
*
* if calling this method in context,
* customerOrId is the 2nd attribute, addressId 3rd.
* customerOrId & addressId are not sent in object context.
*
* @access public
* @param array $transactionAttribs
* @param string $customerId
* @return Transaction
* @throws Exception\ValidationsFailed
* @see Address::update()
*/
public function updateNoValidate($customerOrId, $addressId, $attributes)
{
$result = $this->update($customerOrId, $addressId, $attributes);
return Util::returnObjectOrThrowException(__CLASS__, $result);
}
/**
* creates a full array signature of a valid create request
* @return array gateway create request format
*/
public static function createSignature()
{
return [
'company', 'countryCodeAlpha2', 'countryCodeAlpha3', 'countryCodeNumeric',
'countryName', 'customerId', 'extendedAddress', 'firstName',
'lastName', 'locality', 'postalCode', 'region', 'streetAddress'
];
}
/**
* creates a full array signature of a valid update request
* @return array gateway update request format
*/
public static function updateSignature()
{
// TODO: remove customerId from update signature
return self::createSignature();
}
/**
* verifies that a valid address id is being used
* @ignore
* @param string $id address id
* @throws InvalidArgumentException
*/
private function _validateId($id = null)
{
if (empty($id) || trim($id) == "") {
throw new InvalidArgumentException(
'expected address id to be set'
);
}
if (!preg_match('/^[0-9A-Za-z_-]+$/', $id)) {
throw new InvalidArgumentException(
$id . ' is an invalid address id.'
);
}
}
/**
* verifies that a valid customer id is being used
* @ignore
* @param string $id customer id
* @throws InvalidArgumentException
*/
private function _validateCustomerId($id = null)
{
if (empty($id) || trim($id) == "") {
throw new InvalidArgumentException(
'expected customer id to be set'
);
}
if (!preg_match('/^[0-9A-Za-z_-]+$/', $id)) {
throw new InvalidArgumentException(
$id . ' is an invalid customer id.'
);
}
}
/**
* determines if a string id or Customer object was passed
* @ignore
* @param mixed $customerOrId
* @return string customerId
*/
private function _determineCustomerId($customerOrId)
{
$customerId = ($customerOrId instanceof Customer) ? $customerOrId->id : $customerOrId;
$this->_validateCustomerId($customerId);
return $customerId;
}
/* private class methods */
/**
* sends the create request to the gateway
* @ignore
* @param string $subPath
* @param array $params
* @return Result\Successful|Result\Error
*/
private function _doCreate($subPath, $params)
{
$fullPath = $this->_config->merchantPath() . $subPath;
$response = $this->_http->post($fullPath, $params);
return $this->_verifyGatewayResponse($response);
}
/**
* generic method for validating incoming gateway responses
*
* creates a new Address object and encapsulates
* it inside a Result\Successful object, or
* encapsulates an Errors object inside a Result\Error
* alternatively, throws an Unexpected exception if the response is invalid
*
* @ignore
* @param array $response gateway response values
* @return Result\Successful|Result\Error
* @throws Exception\Unexpected
*/
private function _verifyGatewayResponse($response)
{
if (isset($response['address'])) {
// return a populated instance of Address
return new Result\Successful(
Address::factory($response['address'])
);
} else if (isset($response['apiErrorResponse'])) {
return new Result\Error($response['apiErrorResponse']);
} else {
throw new Exception\Unexpected(
"Expected address or apiErrorResponse"
);
}
}
}
class_alias('Braintree\AddressGateway', 'Braintree_AddressGateway');

View File

@@ -0,0 +1,80 @@
<?php
namespace Braintree;
/**
* Braintree AmexExpressCheckoutCard module
* Creates and manages Braintree Amex Express Checkout cards
*
* <b>== More information ==</b>
*
* See {@link https://developers.braintreepayments.com/javascript+php}<br />
*
* @package Braintree
* @category Resources
*
* @property-read string $bin
* @property-read string $cardMemberExpiryDate
* @property-read string $cardMemberNumber
* @property-read string $cardType
* @property-read \DateTime $createdAt
* @property-read string $customerId
* @property-read boolean $default
* @property-read string $expirationMonth
* @property-read string $expirationYear
* @property-read string $imageUrl
* @property-read string $token
* @property-read string $sourceDescription
* @property-read \Braintree\Subscription[] $subscriptions
* @property-read \DateTime $updatedAt
*/
class AmexExpressCheckoutCard extends Base
{
/* instance methods */
/**
* returns false if default is null or false
*
* @return boolean
*/
public function isDefault()
{
return $this->default;
}
/**
* factory method: returns an instance of AmexExpressCheckoutCard
* to the requesting method, with populated properties
*
* @ignore
* @return AmexExpressCheckoutCard
*/
public static function factory($attributes)
{
$instance = new self();
$instance->_initialize($attributes);
return $instance;
}
/**
* sets instance properties from an array of values
*
* @access protected
* @param array $amexExpressCheckoutCardAttribs array of Amex Express Checkout card properties
* @return void
*/
protected function _initialize($amexExpressCheckoutCardAttribs)
{
// set the attributes
$this->_attributes = $amexExpressCheckoutCardAttribs;
$subscriptionArray = [];
if (isset($amexExpressCheckoutCardAttribs['subscriptions'])) {
foreach ($amexExpressCheckoutCardAttribs['subscriptions'] AS $subscription) {
$subscriptionArray[] = Subscription::factory($subscription);
}
}
$this->_set('subscriptions', $subscriptionArray);
}
}
class_alias('Braintree\AmexExpressCheckoutCard', 'Braintree_AmexExpressCheckoutCard');

View File

@@ -0,0 +1,90 @@
<?php
namespace Braintree;
/**
* Braintree AndroidPayCard module
* Creates and manages Braintree Android Pay cards
*
* <b>== More information ==</b>
*
* See {@link https://developers.braintreepayments.com/javascript+php}<br />
*
* @package Braintree
* @category Resources
*
* @property-read string $bin
* @property-read string $cardType
* @property-read \DateTime $createdAt
* @property-read string $customerId
* @property-read boolean $default
* @property-read string $expirationMonth
* @property-read string $expirationYear
* @property-read string $googleTransactionId
* @property-read string $imageUrl
* @property-read string $last4
* @property-read string $sourceCardLast4
* @property-read string $sourceCardType
* @property-read string $sourceDescription
* @property-read \Braintree\Subscription[] $subscriptions
* @property-read string $token
* @property-read \DateTime $updatedAt
* @property-read string $virtualCardLast4
* @property-read string $virtualCardType
*/
class AndroidPayCard extends Base
{
/* instance methods */
/**
* returns false if default is null or false
*
* @return boolean
*/
public function isDefault()
{
return $this->default;
}
/**
* factory method: returns an instance of AndroidPayCard
* to the requesting method, with populated properties
*
* @ignore
* @return AndroidPayCard
*/
public static function factory($attributes)
{
$defaultAttributes = [
'expirationMonth' => '',
'expirationYear' => '',
'last4' => $attributes['virtualCardLast4'],
'cardType' => $attributes['virtualCardType'],
];
$instance = new self();
$instance->_initialize(array_merge($defaultAttributes, $attributes));
return $instance;
}
/**
* sets instance properties from an array of values
*
* @access protected
* @param array $androidPayCardAttribs array of Android Pay card properties
* @return void
*/
protected function _initialize($androidPayCardAttribs)
{
// set the attributes
$this->_attributes = $androidPayCardAttribs;
$subscriptionArray = [];
if (isset($androidPayCardAttribs['subscriptions'])) {
foreach ($androidPayCardAttribs['subscriptions'] AS $subscription) {
$subscriptionArray[] = Subscription::factory($subscription);
}
}
$this->_set('subscriptions', $subscriptionArray);
}
}
class_alias('Braintree\AndroidPayCard', 'Braintree_AndroidPayCard');

View File

@@ -0,0 +1,103 @@
<?php
namespace Braintree;
/**
* Braintree ApplePayCard module
* Creates and manages Braintree Apple Pay cards
*
* <b>== More information ==</b>
*
* See {@link https://developers.braintreepayments.com/javascript+php}<br />
*
* @package Braintree
* @category Resources
*
* @property-read string $bin
* @property-read string $cardType
* @property-read \DateTime $createdAt
* @property-read string $customerId
* @property-read boolean $default
* @property-read string $expirationDate
* @property-read string $expirationMonth
* @property-read string $expirationYear
* @property-read boolean $expired
* @property-read string $imageUrl
* @property-read string $last4
* @property-read string $token
* @property-read string $paymentInstrumentName
* @property-read string $sourceDescription
* @property-read \Braintree\Subscription[] $subscriptions
* @property-read \DateTime $updatedAt
*/
class ApplePayCard extends Base
{
// Card Type
const AMEX = 'Apple Pay - American Express';
const MASTER_CARD = 'Apple Pay - MasterCard';
const VISA = 'Apple Pay - Visa';
/* instance methods */
/**
* returns false if default is null or false
*
* @return boolean
*/
public function isDefault()
{
return $this->default;
}
/**
* checks whether the card is expired based on the current date
*
* @return boolean
*/
public function isExpired()
{
return $this->expired;
}
/**
* factory method: returns an instance of ApplePayCard
* to the requesting method, with populated properties
*
* @ignore
* @return ApplePayCard
*/
public static function factory($attributes)
{
$defaultAttributes = [
'expirationMonth' => '',
'expirationYear' => '',
'last4' => '',
];
$instance = new self();
$instance->_initialize(array_merge($defaultAttributes, $attributes));
return $instance;
}
/**
* sets instance properties from an array of values
*
* @access protected
* @param array $applePayCardAttribs array of Apple Pay card properties
* @return void
*/
protected function _initialize($applePayCardAttribs)
{
// set the attributes
$this->_attributes = $applePayCardAttribs;
$subscriptionArray = [];
if (isset($applePayCardAttribs['subscriptions'])) {
foreach ($applePayCardAttribs['subscriptions'] AS $subscription) {
$subscriptionArray[] = Subscription::factory($subscription);
}
}
$this->_set('subscriptions', $subscriptionArray);
$this->_set('expirationDate', $this->expirationMonth . '/' . $this->expirationYear);
}
}
class_alias('Braintree\ApplePayCard', 'Braintree_ApplePayCard');

View File

@@ -0,0 +1,65 @@
<?php
namespace Braintree;
/**
* Braintree ApplePayGateway module
* Manages Apple Pay for Web
*
* @package Braintree
* @category Resources
*/
class ApplePayGateway
{
private $_gateway;
private $_config;
private $_http;
public function __construct($gateway)
{
$this->_gateway = $gateway;
$this->_config = $gateway->config;
$this->_config->assertHasAccessTokenOrKeys();
$this->_http = new Http($gateway->config);
}
public function registerDomain($domain)
{
$path = $this->_config->merchantPath() . '/processing/apple_pay/validate_domains';
$response = $this->_http->post($path, ['url' => $domain]);
if (array_key_exists('response', $response) && $response['response']['success'])
{
return new Result\Successful;
}
else if (array_key_exists('apiErrorResponse', $response))
{
return new Result\Error($response['apiErrorResponse']);
}
}
public function unregisterDomain($domain)
{
$path = $this->_config->merchantPath() . '/processing/apple_pay/unregister_domain';
$this->_http->delete($path, ['url' => $domain]);
return new Result\Successful;
}
public function registeredDomains()
{
$path = $this->_config->merchantPath() . '/processing/apple_pay/registered_domains';
$response = $this->_http->get($path);
if (array_key_exists('response', $response) && array_key_exists('domains', $response['response']))
{
$options = ApplePayOptions::factory($response['response']);
return new Result\Successful($options, 'applePayOptions');
}
else if (array_key_exists('apiErrorResponse', $response))
{
return new Result\Error($response['apiErrorResponse']);
}
else
{
throw new Exception\Unexpected('expected response or apiErrorResponse');
}
}
}
class_alias('Braintree\ApplePayGateway', 'Braintree_ApplePayGateway');

View File

@@ -0,0 +1,28 @@
<?php
namespace Braintree;
/**
* Braintree ApplePayOptions module
* Manages configuration and options for Apple Pay
*
* @package Braintree
* @category Resources
*
* @property-read array $domains
*/
class ApplePayOptions extends Base
{
public static function factory($attributes)
{
$instance = new self();
$instance->_initialize($attributes);
return $instance;
}
protected function _initialize($attributes)
{
$this->_attributes = $attributes;
}
}
class_alias('Braintree\ApplePayOptions', 'Braintree_ApplePayOptions');

View File

@@ -0,0 +1,35 @@
<?php
namespace Braintree;
/**
* Creates an instance of AuthorizationAdjustment as returned from a transaction
*
* @package Braintree
*
* @property-read string $amount
* @property-read boolean $success
* @property-read \DateTime $timestamp
*
*/
class AuthorizationAdjustment extends Base
{
public static function factory($attributes)
{
$instance = new self();
$instance->_initialize($attributes);
return $instance;
}
protected function _initialize($authorizationAdjustmentAttribs)
{
$this->_attributes = $authorizationAdjustmentAttribs;
}
public function __toString()
{
return __CLASS__ . '[' . Util::attributesToString($this->_attributes) . ']';
}
}
class_alias('Braintree\AuthorizationAdjustment', 'Braintree_Authorization_Adjustment');

View File

@@ -0,0 +1,88 @@
<?php
namespace Braintree;
use JsonSerializable;
/**
* Braintree PHP Library.
*
* Braintree base class and initialization
* Provides methods to child classes. This class cannot be instantiated.
*
* PHP version 5
*/
abstract class Base implements JsonSerializable
{
protected $_attributes = [];
/**
* @ignore
* don't permit an explicit call of the constructor!
* (like $t = new Transaction())
*/
protected function __construct()
{
}
/**
* Disable cloning of objects
*
* @ignore
*/
protected function __clone()
{
}
/**
* Accessor for instance properties stored in the private $_attributes property
*
* @ignore
* @param string $name
* @return mixed
*/
public function __get($name)
{
if (array_key_exists($name, $this->_attributes)) {
return $this->_attributes[$name];
}
else {
trigger_error('Undefined property on ' . get_class($this) . ': ' . $name, E_USER_NOTICE);
return null;
}
}
/**
* Checks for the existance of a property stored in the private $_attributes property
*
* @ignore
* @param string $name
* @return boolean
*/
public function __isset($name)
{
return array_key_exists($name, $this->_attributes);
}
/**
* Mutator for instance properties stored in the private $_attributes property
*
* @ignore
* @param string $key
* @param mixed $value
*/
public function _set($key, $value)
{
$this->_attributes[$key] = $value;
}
/**
* Implementation of JsonSerializable
*
* @ignore
* @return array
*/
public function jsonSerialize()
{
return $this->_attributes;
}
}

View File

@@ -0,0 +1,41 @@
<?php
namespace Braintree;
/**
* @property-read string $commercial
* @property-read string $countryOfIssuance
* @property-read string $debit
* @property-read string $durbinRegulated
* @property-read string $healthcare
* @property-read string $issuingBank
* @property-read string $payroll
* @property-read string $prepaid
* @property-read string $productId
*/
class BinData extends Base
{
public static function factory($attributes)
{
$instance = new self();
$instance->_initialize($attributes);
return $instance;
}
protected function _initialize($attributes)
{
$this->_attributes = $attributes;
}
/**
* returns a string representation of the bin data
* @return string
*/
public function __toString()
{
return __CLASS__ . '[' .
Util::attributesToString($this->_attributes) .']';
}
}
class_alias('Braintree\BinData', 'Braintree_BinData');

View File

@@ -0,0 +1,49 @@
<?php
namespace Braintree;
class ClientToken
{
const DEFAULT_VERSION = 2;
// static methods redirecting to gateway
/**
*
* @param array $params
* @return string
*/
public static function generate($params=[])
{
return Configuration::gateway()->clientToken()->generate($params);
}
/**
*
* @param type $params
* @throws InvalidArgumentException
*/
public static function conditionallyVerifyKeys($params)
{
return Configuration::gateway()->clientToken()->conditionallyVerifyKeys($params);
}
/**
*
* @return string client token retrieved from server
*/
public static function generateWithCustomerIdSignature()
{
return Configuration::gateway()->clientToken()->generateWithCustomerIdSignature();
}
/**
*
* @return string client token retrieved from server
*/
public static function generateWithoutCustomerIdSignature()
{
return Configuration::gateway()->clientToken()->generateWithoutCustomerIdSignature();
}
}
class_alias('Braintree\ClientToken', 'Braintree_ClientToken');

View File

@@ -0,0 +1,129 @@
<?php
namespace Braintree;
use InvalidArgumentException;
class ClientTokenGateway
{
/**
*
* @var Gateway
*/
private $_gateway;
/**
*
* @var Configuration
*/
private $_config;
/**
*
* @var Http
*/
private $_http;
/**
*
* @param Gateway $gateway
*/
public function __construct($gateway)
{
$this->_gateway = $gateway;
$this->_config = $gateway->config;
$this->_config->assertHasAccessTokenOrKeys();
$this->_http = new Http($gateway->config);
}
public function generate($params=[])
{
if (!array_key_exists("version", $params)) {
$params["version"] = ClientToken::DEFAULT_VERSION;
}
$this->conditionallyVerifyKeys($params);
$generateParams = ["client_token" => $params];
return $this->_doGenerate('/client_token', $generateParams);
}
/**
* sends the generate request to the gateway
*
* @ignore
* @param var $url
* @param array $params
* @return string
*/
public function _doGenerate($subPath, $params)
{
$fullPath = $this->_config->merchantPath() . $subPath;
$response = $this->_http->post($fullPath, $params);
return $this->_verifyGatewayResponse($response);
}
/**
*
* @param array $params
* @throws InvalidArgumentException
*/
public function conditionallyVerifyKeys($params)
{
if (array_key_exists("customerId", $params)) {
Util::verifyKeys($this->generateWithCustomerIdSignature(), $params);
} else {
Util::verifyKeys($this->generateWithoutCustomerIdSignature(), $params);
}
}
/**
*
* @return mixed[]
*/
public function generateWithCustomerIdSignature()
{
return [
"version", "customerId", "proxyMerchantId",
["options" => ["makeDefault", "verifyCard", "failOnDuplicatePaymentMethod"]],
"merchantAccountId"];
}
/**
*
* @return string[]
*/
public function generateWithoutCustomerIdSignature()
{
return ["version", "proxyMerchantId", "merchantAccountId"];
}
/**
* generic method for validating incoming gateway responses
*
* If the request is successful, returns a client token string.
* Otherwise, throws an InvalidArgumentException with the error
* response from the Gateway or an HTTP status code exception.
*
* @ignore
* @param array $response gateway response values
* @return string client token
* @throws InvalidArgumentException | HTTP status code exception
*/
private function _verifyGatewayResponse($response)
{
if (isset($response['clientToken'])) {
return $response['clientToken']['value'];
} elseif (isset($response['apiErrorResponse'])) {
throw new InvalidArgumentException(
$response['apiErrorResponse']['message']
);
} else {
throw new Exception\Unexpected(
"Expected clientToken or apiErrorResponse"
);
}
}
}
class_alias('Braintree\ClientTokenGateway', 'Braintree_ClientTokenGateway');

View File

@@ -0,0 +1,110 @@
<?php
namespace Braintree;
/**
* Braintree CoinbaseAccount module
*
* @package Braintree
* @category Resources
*/
/**
* Manages Braintree CoinbaseAccounts
*
* <b>== More information ==</b>
*
*
* @package Braintree
* @category Resources
*
* @property-read string $customerId
* @property-read string $token
* @property-read string $userId
* @property-read string $userName
* @property-read string $userEmail
*/
class CoinbaseAccount extends Base
{
/**
* factory method: returns an instance of CoinbaseAccount
* to the requesting method, with populated properties
*
* @ignore
* @return CoinbaseAccount
*/
public static function factory($attributes)
{
$instance = new self();
$instance->_initialize($attributes);
return $instance;
}
/* instance methods */
/**
* returns false if default is null or false
*
* @return boolean
*/
public function isDefault()
{
return $this->default;
}
/**
* sets instance properties from an array of values
*
* @access protected
* @param array $coinbaseAccountAttribs array of coinbaseAccount data
* @return void
*/
protected function _initialize($coinbaseAccountAttribs)
{
// set the attributes
$this->_attributes = $coinbaseAccountAttribs;
$subscriptionArray = [];
if (isset($coinbaseAccountAttribs['subscriptions'])) {
foreach ($coinbaseAccountAttribs['subscriptions'] AS $subscription) {
$subscriptionArray[] = Subscription::factory($subscription);
}
}
$this->_set('subscriptions', $subscriptionArray);
}
/**
* create a printable representation of the object as:
* ClassName[property=value, property=value]
* @return string
*/
public function __toString()
{
return __CLASS__ . '[' .
Util::attributesToString($this->_attributes) .']';
}
// static methods redirecting to gateway
public static function find($token)
{
return Configuration::gateway()->coinbaseAccount()->find($token);
}
public static function update($token, $attributes)
{
return Configuration::gateway()->coinbaseAccount()->update($token, $attributes);
}
public static function delete($token)
{
return Configuration::gateway()->coinbaseAccount()->delete($token);
}
public static function sale($token, $transactionAttribs)
{
return Configuration::gateway()->coinbaseAccount()->sale($token, $transactionAttribs);
}
}
class_alias('Braintree\CoinbaseAccount', 'Braintree_CoinbaseAccount');

View File

@@ -0,0 +1,161 @@
<?php
namespace Braintree;
use Countable;
use IteratorAggregate;
use ArrayAccess;
use OutOfRangeException;
use ArrayIterator;
/**
* Braintree Generic collection
*
* PHP Version 5
*
* Based on Generic Collection class from:
* {@link http://codeutopia.net/code/library/CU/Collection.php}
*
* @package Braintree
* @subpackage Utility
*/
class Collection implements Countable, IteratorAggregate, ArrayAccess
{
/**
*
* @var array collection storage
*/
protected $_collection = [];
/**
* Add a value into the collection
* @param string $value
*/
public function add($value)
{
$this->_collection[] = $value;
}
/**
* Set index's value
* @param integer $index
* @param mixed $value
* @throws OutOfRangeException
*/
public function set($index, $value)
{
if($index >= $this->count())
throw new OutOfRangeException('Index out of range');
$this->_collection[$index] = $value;
}
/**
* Remove a value from the collection
* @param integer $index index to remove
* @throws OutOfRangeException if index is out of range
*/
public function remove($index)
{
if($index >= $this->count())
throw new OutOfRangeException('Index out of range');
array_splice($this->_collection, $index, 1);
}
/**
* Return value at index
* @param integer $index
* @return mixed
* @throws OutOfRangeException
*/
public function get($index)
{
if($index >= $this->count())
throw new OutOfRangeException('Index out of range');
return $this->_collection[$index];
}
/**
* Determine if index exists
* @param integer $index
* @return boolean
*/
public function exists($index)
{
if($index >= $this->count())
return false;
return true;
}
/**
* Return count of items in collection
* Implements countable
* @return integer
*/
public function count()
{
return count($this->_collection);
}
/**
* Return an iterator
* Implements IteratorAggregate
* @return ArrayIterator
*/
public function getIterator()
{
return new ArrayIterator($this->_collection);
}
/**
* Set offset to value
* Implements ArrayAccess
* @see set
* @param integer $offset
* @param mixed $value
*/
public function offsetSet($offset, $value)
{
$this->set($offset, $value);
}
/**
* Unset offset
* Implements ArrayAccess
* @see remove
* @param integer $offset
*/
public function offsetUnset($offset)
{
$this->remove($offset);
}
/**
* get an offset's value
* Implements ArrayAccess
* @see get
* @param integer $offset
* @return mixed
*/
public function offsetGet($offset)
{
return $this->get($offset);
}
/**
* Determine if offset exists
* Implements ArrayAccess
* @see exists
* @param integer $offset
* @return boolean
*/
public function offsetExists($offset)
{
return $this->exists($offset);
}
}
class_alias('Braintree\Collection', 'Braintree_Collection');

View File

@@ -0,0 +1,665 @@
<?php
namespace Braintree;
/**
*
* Configuration registry
*
* @package Braintree
* @subpackage Utility
*/
class Configuration
{
public static $global;
private $_environment = null;
private $_merchantId = null;
private $_publicKey = null;
private $_privateKey = null;
private $_clientId = null;
private $_clientSecret = null;
private $_accessToken = null;
private $_proxyHost = null;
private $_proxyPort = null;
private $_proxyType = null;
private $_proxyUser = null;
private $_proxyPassword = null;
private $_timeout = 60;
private $_sslVersion = null;
private $_acceptGzipEncoding = true;
/**
* Braintree API version to use
* @access public
*/
const API_VERSION = 5;
const GRAPHQL_API_VERSION = '2018-09-10';
public function __construct($attribs = [])
{
foreach ($attribs as $kind => $value) {
if ($kind == 'environment') {
CredentialsParser::assertValidEnvironment($value);
$this->_environment = $value;
}
if ($kind == 'merchantId') {
$this->_merchantId = $value;
}
if ($kind == 'publicKey') {
$this->_publicKey = $value;
}
if ($kind == 'privateKey') {
$this->_privateKey = $value;
}
if ($kind == 'timeout') {
$this->_timeout = $value;
}
if ($kind == 'acceptGzipEncoding') {
$this->_acceptGzipEncoding = $value;
}
}
if (isset($attribs['clientId']) || isset($attribs['accessToken'])) {
if (isset($attribs['environment']) || isset($attribs['merchantId']) || isset($attribs['publicKey']) || isset($attribs['privateKey'])) {
throw new Exception\Configuration('Cannot mix OAuth credentials (clientId, clientSecret, accessToken) with key credentials (publicKey, privateKey, environment, merchantId).');
}
$parsedCredentials = new CredentialsParser($attribs);
$this->_environment = $parsedCredentials->getEnvironment();
$this->_merchantId = $parsedCredentials->getMerchantId();
$this->_clientId = $parsedCredentials->getClientId();
$this->_clientSecret = $parsedCredentials->getClientSecret();
$this->_accessToken = $parsedCredentials->getAccessToken();
}
}
/**
* resets configuration to default
* @access public
*/
public static function reset()
{
self::$global = new Configuration();
}
public static function gateway()
{
return new Gateway(self::$global);
}
public static function environment($value=null)
{
if (empty($value)) {
return self::$global->getEnvironment();
}
CredentialsParser::assertValidEnvironment($value);
self::$global->setEnvironment($value);
}
public static function merchantId($value=null)
{
if (empty($value)) {
return self::$global->getMerchantId();
}
self::$global->setMerchantId($value);
}
public static function publicKey($value=null)
{
if (empty($value)) {
return self::$global->getPublicKey();
}
self::$global->setPublicKey($value);
}
public static function privateKey($value=null)
{
if (empty($value)) {
return self::$global->getPrivateKey();
}
self::$global->setPrivateKey($value);
}
/**
* Sets or gets the read timeout to use for making requests.
*
* @param integer $value If provided, sets the read timeout
* @return integer The read timeout used for connecting to Braintree
*/
public static function timeout($value=null)
{
if (empty($value)) {
return self::$global->getTimeout();
}
self::$global->setTimeout($value);
}
/**
* Sets or gets the SSL version to use for making requests. See
* https://php.net/manual/en/function.curl-setopt.php for possible
* CURLOPT_SSLVERSION values.
*
* @param integer $value If provided, sets the SSL version
* @return integer The SSL version used for connecting to Braintree
*/
public static function sslVersion($value=null)
{
if (empty($value)) {
return self::$global->getSslVersion();
}
self::$global->setSslVersion($value);
}
/**
* Sets or gets the proxy host to use for connecting to Braintree
*
* @param string $value If provided, sets the proxy host
* @return string The proxy host used for connecting to Braintree
*/
public static function proxyHost($value = null)
{
if (empty($value)) {
return self::$global->getProxyHost();
}
self::$global->setProxyHost($value);
}
/**
* Sets or gets the port of the proxy to use for connecting to Braintree
*
* @param string $value If provided, sets the port of the proxy
* @return string The port of the proxy used for connecting to Braintree
*/
public static function proxyPort($value = null)
{
if (empty($value)) {
return self::$global->getProxyPort();
}
self::$global->setProxyPort($value);
}
/**
* Sets or gets the proxy type to use for connecting to Braintree. This value
* can be any of the CURLOPT_PROXYTYPE options in PHP cURL.
*
* @param string $value If provided, sets the proxy type
* @return string The proxy type used for connecting to Braintree
*/
public static function proxyType($value = null)
{
if (empty($value)) {
return self::$global->getProxyType();
}
self::$global->setProxyType($value);
}
/**
* Specifies whether or not a proxy is properly configured
*
* @return bool true if a proxy is configured properly, false if not
*/
public static function isUsingProxy()
{
$proxyHost = self::$global->getProxyHost();
$proxyPort = self::$global->getProxyPort();
return !empty($proxyHost) && !empty($proxyPort);
}
public static function proxyUser($value = null)
{
if (empty($value)) {
return self::$global->getProxyUser();
}
self::$global->setProxyUser($value);
}
public static function proxyPassword($value = null)
{
if (empty($value)) {
return self::$global->getProxyPassword();
}
self::$global->setProxyPassword($value);
}
/**
* Specified whether or not a username and password have been provided for
* use with an authenticated proxy
*
* @return bool true if both proxyUser and proxyPassword are present
*/
public static function isAuthenticatedProxy()
{
$proxyUser = self::$global->getProxyUser();
$proxyPwd = self::$global->getProxyPassword();
return !empty($proxyUser) && !empty($proxyPwd);
}
/**
* Specify if the HTTP client is able to decode gzipped responses.
*
* @param bool $value If true, will send an Accept-Encoding header with a gzip value. If false, will not send an Accept-Encoding header with a gzip value.
* @return bool true if an Accept-Encoding header with a gzip value will be sent, false if not
*/
public static function acceptGzipEncoding($value = null)
{
if (is_null($value)) {
return self::$global->getAcceptGzipEncoding();
}
self::$global->setAcceptGzipEncoding($value);
}
public static function assertGlobalHasAccessTokenOrKeys()
{
self::$global->assertHasAccessTokenOrKeys();
}
public function assertHasAccessTokenOrKeys()
{
if (empty($this->_accessToken)) {
if (empty($this->_merchantId)) {
throw new Exception\Configuration('Braintree\\Configuration::merchantId needs to be set (or accessToken needs to be passed to Braintree\\Gateway).');
} else if (empty($this->_environment)) {
throw new Exception\Configuration('Braintree\\Configuration::environment needs to be set.');
} else if (empty($this->_publicKey)) {
throw new Exception\Configuration('Braintree\\Configuration::publicKey needs to be set.');
} else if (empty($this->_privateKey)) {
throw new Exception\Configuration('Braintree\\Configuration::privateKey needs to be set.');
}
}
}
public function assertHasClientCredentials()
{
$this->assertHasClientId();
$this->assertHasClientSecret();
}
public function assertHasClientId()
{
if (empty($this->_clientId)) {
throw new Exception\Configuration('clientId needs to be passed to Braintree\\Gateway.');
}
}
public function assertHasClientSecret()
{
if (empty($this->_clientSecret)) {
throw new Exception\Configuration('clientSecret needs to be passed to Braintree\\Gateway.');
}
}
public function getEnvironment()
{
return $this->_environment;
}
/**
* Do not use this method directly. Pass in the environment to the constructor.
*/
public function setEnvironment($value)
{
$this->_environment = $value;
}
public function getMerchantId()
{
return $this->_merchantId;
}
/**
* Do not use this method directly. Pass in the merchantId to the constructor.
*/
public function setMerchantId($value)
{
$this->_merchantId = $value;
}
public function getPublicKey()
{
return $this->_publicKey;
}
public function getClientId()
{
return $this->_clientId;
}
/**
* Do not use this method directly. Pass in the publicKey to the constructor.
*/
public function setPublicKey($value)
{
$this->_publicKey = $value;
}
public function getPrivateKey()
{
return $this->_privateKey;
}
public function getClientSecret()
{
return $this->_clientSecret;
}
/**
* Do not use this method directly. Pass in the privateKey to the constructor.
*/
public function setPrivateKey($value)
{
$this->_privateKey = $value;
}
private function setProxyHost($value)
{
$this->_proxyHost = $value;
}
public function getProxyHost()
{
return $this->_proxyHost;
}
private function setProxyPort($value)
{
$this->_proxyPort = $value;
}
public function getProxyPort()
{
return $this->_proxyPort;
}
private function setProxyType($value)
{
$this->_proxyType = $value;
}
public function getProxyType()
{
return $this->_proxyType;
}
private function setProxyUser($value)
{
$this->_proxyUser = $value;
}
public function getProxyUser()
{
return $this->_proxyUser;
}
private function setProxyPassword($value)
{
$this->_proxyPassword = $value;
}
public function getProxyPassword()
{
return $this->_proxyPassword;
}
private function setTimeout($value)
{
$this->_timeout = $value;
}
public function getTimeout()
{
return $this->_timeout;
}
private function setSslVersion($value)
{
$this->_sslVersion = $value;
}
private function getSslVersion()
{
return $this->_sslVersion;
}
public function getAcceptGzipEncoding()
{
return $this->_acceptGzipEncoding;
}
private function setAcceptGzipEncoding($value)
{
$this->_acceptGzipEncoding = $value;
}
public function getAccessToken()
{
return $this->_accessToken;
}
public function isAccessToken()
{
return !empty($this->_accessToken);
}
public function isClientCredentials()
{
return !empty($this->_clientId);
}
/**
* returns the base braintree gateway URL based on config values
*
* @access public
* @param none
* @return string braintree gateway URL
*/
public function baseUrl()
{
return sprintf('%s://%s:%d', $this->protocol(), $this->serverName(), $this->portNumber());
}
/**
* returns the base URL for Braintree's GraphQL endpoint based on config values
*
* @access public
* @param none
* @return string Braintree GraphQL URL
*/
public function graphQLBaseUrl()
{
return sprintf('%s://%s:%d/graphql', $this->protocol(), $this->graphQLServerName(), $this->graphQLPortNumber());
}
/**
* sets the merchant path based on merchant ID
*
* @access protected
* @param none
* @return string merchant path uri
*/
public function merchantPath()
{
return '/merchants/' . $this->_merchantId;
}
/**
* sets the physical path for the location of the CA certs
*
* @access public
* @param none
* @return string filepath
*/
public function caFile($sslPath = NULL)
{
$sslPath = $sslPath ? $sslPath : DIRECTORY_SEPARATOR . '..' . DIRECTORY_SEPARATOR .
'ssl' . DIRECTORY_SEPARATOR;
$caPath = __DIR__ . $sslPath . 'api_braintreegateway_com.ca.crt';
if (!file_exists($caPath))
{
throw new Exception\SSLCaFileNotFound();
}
return $caPath;
}
/**
* returns the port number depending on environment
*
* @access public
* @param none
* @return int portnumber
*/
public function portNumber()
{
if ($this->sslOn()) {
return 443;
}
return getenv("GATEWAY_PORT") ? getenv("GATEWAY_PORT") : 3000;
}
/**
* returns the graphql port number depending on environment
*
* @access public
* @param none
* @return int graphql portnumber
*/
public function graphQLPortNumber()
{
if ($this->sslOn()) {
return 443;
}
return getenv("GRAPHQL_PORT") ?: 8080;
}
/**
* returns http protocol depending on environment
*
* @access public
* @param none
* @return string http || https
*/
public function protocol()
{
return $this->sslOn() ? 'https' : 'http';
}
/**
* returns gateway server name depending on environment
*
* @access public
* @param none
* @return string server domain name
*/
public function serverName()
{
switch($this->_environment) {
case 'production':
$serverName = 'api.braintreegateway.com';
break;
case 'qa':
$serverName = 'gateway.qa.braintreepayments.com';
break;
case 'sandbox':
$serverName = 'api.sandbox.braintreegateway.com';
break;
case 'development':
case 'integration':
default:
$serverName = 'localhost';
break;
}
return $serverName;
}
/**
* returns Braintree GraphQL server name depending on environment
*
* @access public
* @param none
* @return string graphql domain name
*/
public function graphQLServerName()
{
switch($this->_environment) {
case 'production':
$graphQLServerName = 'payments.braintree-api.com';
break;
case 'qa':
$graphQLServerName = 'payments-qa.dev.braintree-api.com';
break;
case 'sandbox':
$graphQLServerName = 'payments.sandbox.braintree-api.com';
break;
case 'development':
case 'integration':
default:
$graphQLServerName = 'graphql.bt.local';
break;
}
return $graphQLServerName;
}
public function authUrl()
{
switch($this->_environment) {
case 'production':
$serverName = 'https://auth.venmo.com';
break;
case 'qa':
$serverName = 'https://auth.qa.venmo.com';
break;
case 'sandbox':
$serverName = 'https://auth.sandbox.venmo.com';
break;
case 'development':
case 'integration':
default:
$serverName = 'http://auth.venmo.dev:9292';
break;
}
return $serverName;
}
/**
* returns boolean indicating SSL is on or off for this session,
* depending on environment
*
* @access public
* @param none
* @return boolean
*/
public function sslOn()
{
switch($this->_environment) {
case 'integration':
case 'development':
$ssl = false;
break;
case 'production':
case 'qa':
case 'sandbox':
default:
$ssl = true;
break;
}
return $ssl;
}
/**
* log message to default logger
*
* @param string $message
*
*/
public function logMessage($message)
{
error_log('[Braintree] ' . $message);
}
}
Configuration::reset();
class_alias('Braintree\Configuration', 'Braintree_Configuration');

View File

@@ -0,0 +1,37 @@
<?php
namespace Braintree;
/**
* Connected Merchant PayPal Status Changed Payload
*
* @package Braintree
*
* @property-read string $merchantPublicId
* @property-read string $action
* @property-read string $oauthApplicationClientId
*/
class ConnectedMerchantPayPalStatusChanged extends Base
{
protected $_attributes = [];
/**
* @ignore
*/
public static function factory($attributes)
{
$instance = new self();
$instance->_initialize($attributes);
$instance->_attributes['merchantId'] = $instance->_attributes['merchantPublicId'];
return $instance;
}
/**
* @ignore
*/
protected function _initialize($attributes)
{
$this->_attributes = $attributes;
}
}
class_alias('Braintree\ConnectedMerchantPayPalStatusChanged', 'Braintree_ConnectedMerchantPayPalStatusChanged');

View File

@@ -0,0 +1,37 @@
<?php
namespace Braintree;
/**
* Connected Merchant Status Transitioned Payload
*
* @package Braintree
*
* @property-read string $merchantPublicId
* @property-read string $status
* @property-read string $oauthApplicationClientId
*/
class ConnectedMerchantStatusTransitioned extends Base
{
protected $_attributes = [];
/**
* @ignore
*/
public static function factory($attributes)
{
$instance = new self();
$instance->_initialize($attributes);
$instance->_attributes['merchantId'] = $instance->_attributes['merchantPublicId'];
return $instance;
}
/**
* @ignore
*/
protected function _initialize($attributes)
{
$this->_attributes = $attributes;
}
}
class_alias('Braintree\ConnectedMerchantStatusTransitioned', 'Braintree_ConnectedMerchantStatusTransitioned');

View File

@@ -0,0 +1,147 @@
<?php
namespace Braintree;
/**
*
* CredentialsParser registry
*
* @package Braintree
* @subpackage Utility
*/
class CredentialsParser
{
private $_clientId;
private $_clientSecret;
private $_accessToken;
private $_environment;
private $_merchantId;
public function __construct($attribs)
{
foreach ($attribs as $kind => $value) {
if ($kind == 'clientId') {
$this->_clientId = $value;
}
if ($kind == 'clientSecret') {
$this->_clientSecret = $value;
}
if ($kind == 'accessToken') {
$this->_accessToken = $value;
}
}
$this->parse();
}
/**
*
* @access protected
* @static
* @var array valid environments, used for validation
*/
private static $_validEnvironments = [
'development',
'integration',
'sandbox',
'production',
'qa',
];
public function parse()
{
$environments = [];
if (!empty($this->_clientId)) {
$environments[] = ['clientId', $this->_parseClientCredential('clientId', $this->_clientId, 'client_id')];
}
if (!empty($this->_clientSecret)) {
$environments[] = ['clientSecret', $this->_parseClientCredential('clientSecret', $this->_clientSecret, 'client_secret')];
}
if (!empty($this->_accessToken)) {
$environments[] = ['accessToken', $this->_parseAccessToken()];
}
$checkEnv = $environments[0];
foreach ($environments as $env) {
if ($env[1] !== $checkEnv[1]) {
throw new Exception\Configuration(
'Mismatched credential environments: ' . $checkEnv[0] . ' environment is ' . $checkEnv[1] .
' and ' . $env[0] . ' environment is ' . $env[1]);
}
}
self::assertValidEnvironment($checkEnv[1]);
$this->_environment = $checkEnv[1];
}
public static function assertValidEnvironment($environment) {
if (!in_array($environment, self::$_validEnvironments)) {
throw new Exception\Configuration('"' .
$environment . '" is not a valid environment.');
}
}
private function _parseClientCredential($credentialType, $value, $expectedValuePrefix)
{
$explodedCredential = explode('$', $value);
if (sizeof($explodedCredential) != 3) {
throw new Exception\Configuration('Incorrect ' . $credentialType . ' format. Expected: type$environment$token');
}
$gotValuePrefix = $explodedCredential[0];
$environment = $explodedCredential[1];
$token = $explodedCredential[2];
if ($gotValuePrefix != $expectedValuePrefix) {
throw new Exception\Configuration('Value passed for ' . $credentialType . ' is not a ' . $credentialType);
}
return $environment;
}
private function _parseAccessToken()
{
$accessTokenExploded = explode('$', $this->_accessToken);
if (sizeof($accessTokenExploded) != 4) {
throw new Exception\Configuration('Incorrect accessToken syntax. Expected: type$environment$merchant_id$token');
}
$gotValuePrefix = $accessTokenExploded[0];
$environment = $accessTokenExploded[1];
$merchantId = $accessTokenExploded[2];
$token = $accessTokenExploded[3];
if ($gotValuePrefix != 'access_token') {
throw new Exception\Configuration('Value passed for accessToken is not an accessToken');
}
$this->_merchantId = $merchantId;
return $environment;
}
public function getClientId()
{
return $this->_clientId;
}
public function getClientSecret()
{
return $this->_clientSecret;
}
public function getAccessToken()
{
return $this->_accessToken;
}
public function getEnvironment()
{
return $this->_environment;
}
public function getMerchantId()
{
return $this->_merchantId;
}
}
class_alias('Braintree\CredentialsParser', 'Braintree_CredentialsParser');

View File

@@ -0,0 +1,332 @@
<?php
namespace Braintree;
/**
* Braintree CreditCard module
* Creates and manages Braintree CreditCards
*
* <b>== More information ==</b>
*
* For more detailed information on CreditCards, see {@link https://developers.braintreepayments.com/reference/response/credit-card/php https://developers.braintreepayments.com/reference/response/credit-card/php}<br />
* For more detailed information on CreditCard verifications, see {@link https://developers.braintreepayments.com/reference/response/credit-card-verification/php https://developers.braintreepayments.com/reference/response/credit-card-verification/php}
*
* @package Braintree
* @category Resources
*
* @property-read \Braintree\Address $billingAddress
* @property-read string $bin
* @property-read string $cardType
* @property-read string $cardholderName
* @property-read string $commercial
* @property-read \DateTime $createdAt
* @property-read string $customerId
* @property-read string $customerLocation
* @property-read string $debit
* @property-read boolean $default
* @property-read string $durbinRegulated
* @property-read string $expirationDate
* @property-read string $expirationMonth
* @property-read string $expirationYear
* @property-read boolean $expired
* @property-read boolean $healthcare
* @property-read string $imageUrl
* @property-read string $issuingBank
* @property-read string $last4
* @property-read string $maskedNumber
* @property-read string $payroll
* @property-read string $prepaid
* @property-read string $productId
* @property-read \Braintree\Subscription[] $subscriptions
* @property-read string $token
* @property-read string $uniqueNumberIdentifier
* @property-read \DateTime $updatedAt
* @property-read \Braintree\CreditCardVerification|null $verification
*/
class CreditCard extends Base
{
// Card Type
const AMEX = 'American Express';
const CARTE_BLANCHE = 'Carte Blanche';
const CHINA_UNION_PAY = 'China UnionPay';
const DINERS_CLUB_INTERNATIONAL = 'Diners Club';
const DISCOVER = 'Discover';
const ELO = 'Elo';
const JCB = 'JCB';
const LASER = 'Laser';
const MAESTRO = 'Maestro';
const UK_MAESTRO = 'UK Maestro';
const MASTER_CARD = 'MasterCard';
const SOLO = 'Solo';
const SWITCH_TYPE = 'Switch';
const VISA = 'Visa';
const UNKNOWN = 'Unknown';
// Credit card origination location
const INTERNATIONAL = "international";
const US = "us";
const PREPAID_YES = 'Yes';
const PREPAID_NO = 'No';
const PREPAID_UNKNOWN = 'Unknown';
const PAYROLL_YES = 'Yes';
const PAYROLL_NO = 'No';
const PAYROLL_UNKNOWN = 'Unknown';
const HEALTHCARE_YES = 'Yes';
const HEALTHCARE_NO = 'No';
const HEALTHCARE_UNKNOWN = 'Unknown';
const DURBIN_REGULATED_YES = 'Yes';
const DURBIN_REGULATED_NO = 'No';
const DURBIN_REGULATED_UNKNOWN = 'Unknown';
const DEBIT_YES = 'Yes';
const DEBIT_NO = 'No';
const DEBIT_UNKNOWN = 'Unknown';
const COMMERCIAL_YES = 'Yes';
const COMMERCIAL_NO = 'No';
const COMMERCIAL_UNKNOWN = 'Unknown';
const COUNTRY_OF_ISSUANCE_UNKNOWN = "Unknown";
const ISSUING_BANK_UNKNOWN = "Unknown";
const PRODUCT_ID_UNKNOWN = "Unknown";
/* instance methods */
/**
* returns false if default is null or false
*
* @return boolean
*/
public function isDefault()
{
return $this->default;
}
/**
* checks whether the card is expired based on the current date
*
* @return boolean
*/
public function isExpired()
{
return $this->expired;
}
/**
* checks whether the card is associated with venmo sdk
*
* @return boolean
*/
public function isVenmoSdk()
{
return $this->venmoSdk;
}
/**
* sets instance properties from an array of values
*
* @access protected
* @param array $creditCardAttribs array of creditcard data
* @return void
*/
protected function _initialize($creditCardAttribs)
{
// set the attributes
$this->_attributes = $creditCardAttribs;
// map each address into its own object
$billingAddress = isset($creditCardAttribs['billingAddress']) ?
Address::factory($creditCardAttribs['billingAddress']) :
null;
$subscriptionArray = [];
if (isset($creditCardAttribs['subscriptions'])) {
foreach ($creditCardAttribs['subscriptions'] AS $subscription) {
$subscriptionArray[] = Subscription::factory($subscription);
}
}
$this->_set('subscriptions', $subscriptionArray);
$this->_set('billingAddress', $billingAddress);
$this->_set('expirationDate', $this->expirationMonth . '/' . $this->expirationYear);
$this->_set('maskedNumber', $this->bin . '******' . $this->last4);
if(isset($creditCardAttribs['verifications']) && count($creditCardAttribs['verifications']) > 0) {
$verifications = $creditCardAttribs['verifications'];
usort($verifications, [$this, '_compareCreatedAtOnVerifications']);
$this->_set('verification', CreditCardVerification::factory($verifications[0]));
}
}
private function _compareCreatedAtOnVerifications($verificationAttrib1, $verificationAttrib2)
{
return ($verificationAttrib2['createdAt'] < $verificationAttrib1['createdAt']) ? -1 : 1;
}
/**
* returns false if comparing object is not a CreditCard,
* or is a CreditCard with a different id
*
* @param object $otherCreditCard customer to compare against
* @return boolean
*/
public function isEqual($otherCreditCard)
{
return !($otherCreditCard instanceof self) ? false : $this->token === $otherCreditCard->token;
}
/**
* create a printable representation of the object as:
* ClassName[property=value, property=value]
* @return string
*/
public function __toString()
{
return __CLASS__ . '[' .
Util::attributesToString($this->_attributes) .']';
}
/**
* factory method: returns an instance of CreditCard
* to the requesting method, with populated properties
*
* @ignore
* @return CreditCard
*/
public static function factory($attributes)
{
$defaultAttributes = [
'bin' => '',
'expirationMonth' => '',
'expirationYear' => '',
'last4' => '',
];
$instance = new self();
$instance->_initialize(array_merge($defaultAttributes, $attributes));
return $instance;
}
// static methods redirecting to gateway
public static function create($attribs)
{
return Configuration::gateway()->creditCard()->create($attribs);
}
public static function createNoValidate($attribs)
{
return Configuration::gateway()->creditCard()->createNoValidate($attribs);
}
public static function createFromTransparentRedirect($queryString)
{
return Configuration::gateway()->creditCard()->createFromTransparentRedirect($queryString);
}
public static function createCreditCardUrl()
{
return Configuration::gateway()->creditCard()->createCreditCardUrl();
}
public static function expired()
{
return Configuration::gateway()->creditCard()->expired();
}
public static function fetchExpired($ids)
{
return Configuration::gateway()->creditCard()->fetchExpired($ids);
}
public static function expiringBetween($startDate, $endDate)
{
return Configuration::gateway()->creditCard()->expiringBetween($startDate, $endDate);
}
public static function fetchExpiring($startDate, $endDate, $ids)
{
return Configuration::gateway()->creditCard()->fetchExpiring($startDate, $endDate, $ids);
}
public static function find($token)
{
return Configuration::gateway()->creditCard()->find($token);
}
public static function fromNonce($nonce)
{
return Configuration::gateway()->creditCard()->fromNonce($nonce);
}
public static function credit($token, $transactionAttribs)
{
return Configuration::gateway()->creditCard()->credit($token, $transactionAttribs);
}
public static function creditNoValidate($token, $transactionAttribs)
{
return Configuration::gateway()->creditCard()->creditNoValidate($token, $transactionAttribs);
}
public static function sale($token, $transactionAttribs)
{
return Configuration::gateway()->creditCard()->sale($token, $transactionAttribs);
}
public static function saleNoValidate($token, $transactionAttribs)
{
return Configuration::gateway()->creditCard()->saleNoValidate($token, $transactionAttribs);
}
public static function update($token, $attributes)
{
return Configuration::gateway()->creditCard()->update($token, $attributes);
}
public static function updateNoValidate($token, $attributes)
{
return Configuration::gateway()->creditCard()->updateNoValidate($token, $attributes);
}
public static function updateCreditCardUrl()
{
return Configuration::gateway()->creditCard()->updateCreditCardUrl();
}
public static function updateFromTransparentRedirect($queryString)
{
return Configuration::gateway()->creditCard()->updateFromTransparentRedirect($queryString);
}
public static function delete($token)
{
return Configuration::gateway()->creditCard()->delete($token);
}
/** @return array */
public static function allCardTypes()
{
return [
CreditCard::AMEX,
CreditCard::CARTE_BLANCHE,
CreditCard::CHINA_UNION_PAY,
CreditCard::DINERS_CLUB_INTERNATIONAL,
CreditCard::DISCOVER,
CreditCard::ELO,
CreditCard::JCB,
CreditCard::LASER,
CreditCard::MAESTRO,
CreditCard::MASTER_CARD,
CreditCard::SOLO,
CreditCard::SWITCH_TYPE,
CreditCard::VISA,
CreditCard::UNKNOWN
];
}
}
class_alias('Braintree\CreditCard', 'Braintree_CreditCard');

View File

@@ -0,0 +1,486 @@
<?php
namespace Braintree;
use InvalidArgumentException;
/**
* Braintree CreditCardGateway module
* Creates and manages Braintree CreditCards
*
* <b>== More information ==</b>
*
* For more detailed information on CreditCards, see {@link https://developers.braintreepayments.com/reference/response/credit-card/php https://developers.braintreepayments.com/reference/response/credit-card/php}<br />
* For more detailed information on CreditCard verifications, see {@link https://developers.braintreepayments.com/reference/response/credit-card-verification/php https://developers.braintreepayments.com/reference/response/credit-card-verification/php}
*
* @package Braintree
* @category Resources
*/
class CreditCardGateway
{
private $_gateway;
private $_config;
private $_http;
public function __construct($gateway)
{
$this->_gateway = $gateway;
$this->_config = $gateway->config;
$this->_config->assertHasAccessTokenOrKeys();
$this->_http = new Http($gateway->config);
}
public function create($attribs)
{
Util::verifyKeys(self::createSignature(), $attribs);
return $this->_doCreate('/payment_methods', ['credit_card' => $attribs]);
}
/**
* attempts the create operation assuming all data will validate
* returns a CreditCard object instead of a Result
*
* @access public
* @param array $attribs
* @return CreditCard
* @throws Exception\ValidationError
*/
public function createNoValidate($attribs)
{
$result = $this->create($attribs);
return Util::returnObjectOrThrowException(__CLASS__, $result);
}
/**
* create a customer from a TransparentRedirect operation
*
* @deprecated since version 2.3.0
* @access public
* @param array $attribs
* @return Result\Successful|Result\Error
*/
public function createFromTransparentRedirect($queryString)
{
trigger_error("DEPRECATED: Please use TransparentRedirectRequest::confirm", E_USER_NOTICE);
$params = TransparentRedirect::parseAndValidateQueryString(
$queryString
);
return $this->_doCreate(
'/payment_methods/all/confirm_transparent_redirect_request',
['id' => $params['id']]
);
}
/**
*
* @deprecated since version 2.3.0
* @access public
* @param none
* @return string
*/
public function createCreditCardUrl()
{
trigger_error("DEPRECATED: Please use TransparentRedirectRequest::url", E_USER_NOTICE);
return $this->_config->baseUrl() . $this->_config->merchantPath().
'/payment_methods/all/create_via_transparent_redirect_request';
}
/**
* returns a ResourceCollection of expired credit cards
* @return ResourceCollection
*/
public function expired()
{
$path = $this->_config->merchantPath() . '/payment_methods/all/expired_ids';
$response = $this->_http->post($path);
$pager = [
'object' => $this,
'method' => 'fetchExpired',
'methodArgs' => []
];
return new ResourceCollection($response, $pager);
}
public function fetchExpired($ids)
{
$path = $this->_config->merchantPath() . "/payment_methods/all/expired";
$response = $this->_http->post($path, ['search' => ['ids' => $ids]]);
return Util::extractattributeasarray(
$response['paymentMethods'],
'creditCard'
);
}
/**
* returns a ResourceCollection of credit cards expiring between start/end
*
* @return ResourceCollection
*/
public function expiringBetween($startDate, $endDate)
{
$queryPath = $this->_config->merchantPath() . '/payment_methods/all/expiring_ids?start=' . date('mY', $startDate) . '&end=' . date('mY', $endDate);
$response = $this->_http->post($queryPath);
$pager = [
'object' => $this,
'method' => 'fetchExpiring',
'methodArgs' => [$startDate, $endDate]
];
return new ResourceCollection($response, $pager);
}
public function fetchExpiring($startDate, $endDate, $ids)
{
$queryPath = $this->_config->merchantPath() . '/payment_methods/all/expiring?start=' . date('mY', $startDate) . '&end=' . date('mY', $endDate);
$response = $this->_http->post($queryPath, ['search' => ['ids' => $ids]]);
return Util::extractAttributeAsArray(
$response['paymentMethods'],
'creditCard'
);
}
/**
* find a creditcard by token
*
* @access public
* @param string $token credit card unique id
* @return CreditCard
* @throws Exception\NotFound
*/
public function find($token)
{
$this->_validateId($token);
try {
$path = $this->_config->merchantPath() . '/payment_methods/credit_card/' . $token;
$response = $this->_http->get($path);
return CreditCard::factory($response['creditCard']);
} catch (Exception\NotFound $e) {
throw new Exception\NotFound(
'credit card with token ' . $token . ' not found'
);
}
}
/**
* Convert a payment method nonce to a credit card
*
* @access public
* @param string $nonce payment method nonce
* @return CreditCard
* @throws Exception\NotFound
*/
public function fromNonce($nonce)
{
$this->_validateId($nonce, "nonce");
try {
$path = $this->_config->merchantPath() . '/payment_methods/from_nonce/' . $nonce;
$response = $this->_http->get($path);
return CreditCard::factory($response['creditCard']);
} catch (Exception\NotFound $e) {
throw new Exception\NotFound(
'credit card with nonce ' . $nonce . ' locked, consumed or not found'
);
}
}
/**
* create a credit on the card for the passed transaction
*
* @access public
* @param array $attribs
* @return Result\Successful|Result\Error
*/
public function credit($token, $transactionAttribs)
{
$this->_validateId($token);
return Transaction::credit(
array_merge(
$transactionAttribs,
['paymentMethodToken' => $token]
)
);
}
/**
* create a credit on this card, assuming validations will pass
*
* returns a Transaction object on success
*
* @access public
* @param array $attribs
* @return Transaction
* @throws Exception\ValidationError
*/
public function creditNoValidate($token, $transactionAttribs)
{
$result = $this->credit($token, $transactionAttribs);
return Util::returnObjectOrThrowException('Braintree\Transaction', $result);
}
/**
* create a new sale for the current card
*
* @param string $token
* @param array $transactionAttribs
* @return Result\Successful|Result\Error
* @see Transaction::sale()
*/
public function sale($token, $transactionAttribs)
{
$this->_validateId($token);
return Transaction::sale(
array_merge(
$transactionAttribs,
['paymentMethodToken' => $token]
)
);
}
/**
* create a new sale using this card, assuming validations will pass
*
* returns a Transaction object on success
*
* @access public
* @param array $transactionAttribs
* @param string $token
* @return Transaction
* @throws Exception\ValidationsFailed
* @see Transaction::sale()
*/
public function saleNoValidate($token, $transactionAttribs)
{
$result = $this->sale($token, $transactionAttribs);
return Util::returnObjectOrThrowException('Braintree\Transaction', $result);
}
/**
* updates the creditcard record
*
* if calling this method in context, $token
* is the 2nd attribute. $token is not sent in object context.
*
* @access public
* @param array $attributes
* @param string $token (optional)
* @return Result\Successful|Result\Error
*/
public function update($token, $attributes)
{
Util::verifyKeys(self::updateSignature(), $attributes);
$this->_validateId($token);
return $this->_doUpdate('put', '/payment_methods/credit_card/' . $token, ['creditCard' => $attributes]);
}
/**
* update a creditcard record, assuming validations will pass
*
* if calling this method in context, $token
* is the 2nd attribute. $token is not sent in object context.
* returns a CreditCard object on success
*
* @access public
* @param array $attributes
* @param string $token
* @return CreditCard
* @throws Exception\ValidationsFailed
*/
public function updateNoValidate($token, $attributes)
{
$result = $this->update($token, $attributes);
return Util::returnObjectOrThrowException(__CLASS__, $result);
}
/**
*
* @access public
* @param none
* @return string
*/
public function updateCreditCardUrl()
{
trigger_error("DEPRECATED: Please use TransparentRedirectRequest::url", E_USER_NOTICE);
return $this->_config->baseUrl() . $this->_config->merchantPath() .
'/payment_methods/all/update_via_transparent_redirect_request';
}
/**
* update a customer from a TransparentRedirect operation
*
* @deprecated since version 2.3.0
* @access public
* @param array $attribs
* @return object
*/
public function updateFromTransparentRedirect($queryString)
{
trigger_error("DEPRECATED: Please use TransparentRedirectRequest::confirm", E_USER_NOTICE);
$params = TransparentRedirect::parseAndValidateQueryString(
$queryString
);
return $this->_doUpdate(
'post',
'/payment_methods/all/confirm_transparent_redirect_request',
['id' => $params['id']]
);
}
public function delete($token)
{
$this->_validateId($token);
$path = $this->_config->merchantPath() . '/payment_methods/credit_card/' . $token;
$this->_http->delete($path);
return new Result\Successful();
}
private static function baseOptions()
{
return ['makeDefault', 'verificationMerchantAccountId', 'verifyCard', 'verificationAmount', 'venmoSdkSession'];
}
private static function baseSignature($options)
{
return [
'billingAddressId', 'cardholderName', 'cvv', 'number', 'deviceSessionId',
'expirationDate', 'expirationMonth', 'expirationYear', 'token', 'venmoSdkPaymentMethodCode',
'deviceData', 'fraudMerchantId', 'paymentMethodNonce',
['options' => $options],
[
'billingAddress' => self::billingAddressSignature()
],
];
}
public static function billingAddressSignature()
{
return [
'firstName',
'lastName',
'company',
'countryCodeAlpha2',
'countryCodeAlpha3',
'countryCodeNumeric',
'countryName',
'extendedAddress',
'locality',
'region',
'postalCode',
'streetAddress'
];
}
public static function createSignature()
{
$options = self::baseOptions();
$options[] = "failOnDuplicatePaymentMethod";
$signature = self::baseSignature($options);
$signature[] = 'customerId';
return $signature;
}
public static function updateSignature()
{
$options = self::baseOptions();
$options[] = "failOnDuplicatePaymentMethod";
$signature = self::baseSignature($options);
$updateExistingBillingSignature = [
[
'options' => [
'updateExisting'
]
]
];
foreach($signature AS $key => $value) {
if(is_array($value) and array_key_exists('billingAddress', $value)) {
$signature[$key]['billingAddress'] = array_merge_recursive($value['billingAddress'], $updateExistingBillingSignature);
}
}
return $signature;
}
/**
* sends the create request to the gateway
*
* @ignore
* @param string $subPath
* @param array $params
* @return mixed
*/
public function _doCreate($subPath, $params)
{
$fullPath = $this->_config->merchantPath() . $subPath;
$response = $this->_http->post($fullPath, $params);
return $this->_verifyGatewayResponse($response);
}
/**
* verifies that a valid credit card identifier is being used
* @ignore
* @param string $identifier
* @param Optional $string $identifierType type of identifier supplied, default "token"
* @throws InvalidArgumentException
*/
private function _validateId($identifier = null, $identifierType = "token")
{
if (empty($identifier)) {
throw new InvalidArgumentException(
'expected credit card id to be set'
);
}
if (!preg_match('/^[0-9A-Za-z_-]+$/', $identifier)) {
throw new InvalidArgumentException(
$identifier . ' is an invalid credit card ' . $identifierType . '.'
);
}
}
/**
* sends the update request to the gateway
*
* @ignore
* @param string $url
* @param array $params
* @return mixed
*/
private function _doUpdate($httpVerb, $subPath, $params)
{
$fullPath = $this->_config->merchantPath() . $subPath;
$response = $this->_http->$httpVerb($fullPath, $params);
return $this->_verifyGatewayResponse($response);
}
/**
* generic method for validating incoming gateway responses
*
* creates a new CreditCard object and encapsulates
* it inside a Result\Successful object, or
* encapsulates a Errors object inside a Result\Error
* alternatively, throws an Unexpected exception if the response is invalid
*
* @ignore
* @param array $response gateway response values
* @return Result\Successful|Result\Error
* @throws Exception\Unexpected
*/
private function _verifyGatewayResponse($response)
{
if (isset($response['creditCard'])) {
// return a populated instance of Address
return new Result\Successful(
CreditCard::factory($response['creditCard'])
);
} elseif (isset($response['apiErrorResponse'])) {
return new Result\Error($response['apiErrorResponse']);
} else {
throw new Exception\Unexpected(
"Expected address or apiErrorResponse"
);
}
}
}
class_alias('Braintree\CreditCardGateway', 'Braintree_CreditCardGateway');

View File

@@ -0,0 +1,67 @@
<?php
namespace Braintree;
/**
* {@inheritdoc}
*
* @property-read string $amount
* @property-read mixed $billing
* @property-read string $company
* @property-read string $countryName
* @property-read string $extendedAddress
* @property-read string $firstName
* @property-read string $lastName
* @property-read string $locality
* @property-read string $postalCode
* @property-read string $region
* @property-read string $streetAddress
* @property-read \DateTime $createdAt
* @property-read \Braintree\CreditCard $creditCard
* @property-read string|null $gatewayRejectionReason
* @property-read string $id
* @property-read string $merchantAccountId
* @property-read string $processorResponseCode
* @property-read string $processorResponseText
* @property-read string $processorResponseType
* @property-read \Braintree\RiskData|null $riskData
*/
class CreditCardVerification extends Result\CreditCardVerification
{
public static function factory($attributes)
{
$instance = new self($attributes);
return $instance;
}
// static methods redirecting to gateway
//
public static function create($attributes)
{
Util::verifyKeys(self::createSignature(), $attributes);
return Configuration::gateway()->creditCardVerification()->create($attributes);
}
public static function fetch($query, $ids)
{
return Configuration::gateway()->creditCardVerification()->fetch($query, $ids);
}
public static function search($query)
{
return Configuration::gateway()->creditCardVerification()->search($query);
}
public static function createSignature()
{
return [
['options' => ['amount', 'merchantAccountId']],
['creditCard' =>
[
'cardholderName', 'cvv', 'number',
'expirationDate', 'expirationMonth', 'expirationYear',
['billingAddress' => CreditCardGateway::billingAddressSignature()]
]
]];
}
}
class_alias('Braintree\CreditCardVerification', 'Braintree_CreditCardVerification');

View File

@@ -0,0 +1,74 @@
<?php
namespace Braintree;
class CreditCardVerificationGateway
{
private $_gateway;
private $_config;
private $_http;
public function __construct($gateway)
{
$this->_gateway = $gateway;
$this->_config = $gateway->config;
$this->_config->assertHasAccessTokenOrKeys();
$this->_http = new Http($gateway->config);
}
public function create($attributes)
{
$response = $this->_http->post($this->_config->merchantPath() . "/verifications", ['verification' => $attributes]);
return $this->_verifyGatewayResponse($response);
}
private function _verifyGatewayResponse($response)
{
if(isset($response['verification'])){
return new Result\Successful(
CreditCardVerification::factory($response['verification'])
);
} else if (isset($response['apiErrorResponse'])) {
return new Result\Error($response['apiErrorResponse']);
} else {
throw new Exception\Unexpected(
"Expected transaction or apiErrorResponse"
);
}
}
public function fetch($query, $ids)
{
$criteria = [];
foreach ($query as $term) {
$criteria[$term->name] = $term->toparam();
}
$criteria["ids"] = CreditCardVerificationSearch::ids()->in($ids)->toparam();
$path = $this->_config->merchantPath() . '/verifications/advanced_search';
$response = $this->_http->post($path, ['search' => $criteria]);
return Util::extractattributeasarray(
$response['creditCardVerifications'],
'verification'
);
}
public function search($query)
{
$criteria = [];
foreach ($query as $term) {
$criteria[$term->name] = $term->toparam();
}
$path = $this->_config->merchantPath() . '/verifications/advanced_search_ids';
$response = $this->_http->post($path, ['search' => $criteria]);
$pager = [
'object' => $this,
'method' => 'fetch',
'methodArgs' => [$query]
];
return new ResourceCollection($response, $pager);
}
}
class_alias('Braintree\CreditCardVerificationGateway', 'Braintree_CreditCardVerificationGateway');

View File

@@ -0,0 +1,56 @@
<?php
namespace Braintree;
class CreditCardVerificationSearch
{
public static function id() {
return new TextNode('id');
}
public static function creditCardCardholderName() {
return new TextNode('credit_card_cardholder_name');
}
public static function billingAddressDetailsPostalCode() {
return new TextNode('billing_address_details_postal_code');
}
public static function customerEmail() {
return new TextNode('customer_email');
}
public static function customerId() {
return new TextNode('customer_id');
}
public static function paymentMethodToken(){
return new TextNode('payment_method_token');
}
public static function creditCardExpirationDate() {
return new EqualityNode('credit_card_expiration_date');
}
public static function creditCardNumber() {
return new PartialMatchNode('credit_card_number');
}
public static function ids() {
return new MultipleValueNode('ids');
}
public static function createdAt() {
return new RangeNode("created_at");
}
public static function creditCardCardType()
{
return new MultipleValueNode("credit_card_card_type", CreditCard::allCardTypes());
}
public static function status()
{
return new MultipleValueNode("status", Result\CreditCardVerification::allStatuses());
}
}
class_alias('Braintree\CreditCardVerificationSearch', 'Braintree_CreditCardVerificationSearch');

View File

@@ -0,0 +1,435 @@
<?php
namespace Braintree;
/**
* Braintree Customer module
* Creates and manages Customers
*
* <b>== More information ==</b>
*
* For more detailed information on Customers, see {@link https://developers.braintreepayments.com/reference/response/customer/php https://developers.braintreepayments.com/reference/response/customer/php}
*
* @package Braintree
* @category Resources
*
* @property-read \Braintree\Address[] $addresses
* @property-read \Braintree\AndroidPayCard[] $androidPayCards
* @property-read \Braintree\AmexExpressCheckoutCard[] $amexExpressCheckoutCards
* @property-read \Braintree\ApplePayCard[] $applePayCards
* @property-read \Braintree\CoinbaseAccount[] $coinbaseAccounts
* @property-read string $company
* @property-read \DateTime $createdAt
* @property-read \Braintree\CreditCard[] $creditCards
* @property-read array $customFields custom fields passed with the request
* @property-read string $email
* @property-read string $fax
* @property-read string $firstName
* @property-read string $id
* @property-read string $lastName
* @property-read \Braintree\MasterpassCard[] $masterpassCards
* @property-read \Braintree\PaymentMethod[] $paymentMethods
* @property-read \Braintree\PayPalAccount[] $paypalAccounts
* @property-read string $phone
* @property-read \Braintree\SamsungPayCard[] $samsungPayCards
* @property-read \DateTime $updatedAt
* @property-read \Braintree\UsBankAccount[] $usBankAccounts
* @property-read \Braintree\VenmoAccount[] $venmoAccounts
* @property-read \Braintree\VisaCheckoutCard[] $visaCheckoutCards
* @property-read string $website
*/
class Customer extends Base
{
/**
*
* @return Customer[]
*/
public static function all()
{
return Configuration::gateway()->customer()->all();
}
/**
*
* @param string $query
* @param int[] $ids
* @return Customer|Customer[]
*/
public static function fetch($query, $ids)
{
return Configuration::gateway()->customer()->fetch($query, $ids);
}
/**
*
* @param array $attribs
* @return Result\Successful|Result\Error
*/
public static function create($attribs = [])
{
return Configuration::gateway()->customer()->create($attribs);
}
/**
*
* @param array $attribs
* @return Customer
*/
public static function createNoValidate($attribs = [])
{
return Configuration::gateway()->customer()->createNoValidate($attribs);
}
/**
* @deprecated since version 2.3.0
* @param string $queryString
* @return Result\Successful
*/
public static function createFromTransparentRedirect($queryString)
{
return Configuration::gateway()->customer()->createFromTransparentRedirect($queryString);
}
/**
* @deprecated since version 2.3.0
* @return string
*/
public static function createCustomerUrl()
{
return Configuration::gateway()->customer()->createCustomerUrl();
}
/**
*
* @throws Exception\NotFound
* @param string $id customer id
* @return Customer
*/
public static function find($id, $associationFilterId = null)
{
return Configuration::gateway()->customer()->find($id, $associationFilterId);
}
/**
*
* @param int $customerId
* @param array $transactionAttribs
* @return Result\Successful|Result\Error
*/
public static function credit($customerId, $transactionAttribs)
{
return Configuration::gateway()->customer()->credit($customerId, $transactionAttribs);
}
/**
*
* @throws Exception\ValidationError
* @param type $customerId
* @param type $transactionAttribs
* @return Transaction
*/
public static function creditNoValidate($customerId, $transactionAttribs)
{
return Configuration::gateway()->customer()->creditNoValidate($customerId, $transactionAttribs);
}
/**
*
* @throws Exception on invalid id or non-200 http response code
* @param int $customerId
* @return Result\Successful
*/
public static function delete($customerId)
{
return Configuration::gateway()->customer()->delete($customerId);
}
/**
*
* @param int $customerId
* @param array $transactionAttribs
* @return Transaction
*/
public static function sale($customerId, $transactionAttribs)
{
return Configuration::gateway()->customer()->sale($customerId, $transactionAttribs);
}
/**
*
* @param int $customerId
* @param array $transactionAttribs
* @return Transaction
*/
public static function saleNoValidate($customerId, $transactionAttribs)
{
return Configuration::gateway()->customer()->saleNoValidate($customerId, $transactionAttribs);
}
/**
*
* @throws InvalidArgumentException
* @param string $query
* @return ResourceCollection
*/
public static function search($query)
{
return Configuration::gateway()->customer()->search($query);
}
/**
*
* @throws Exception\Unexpected
* @param int $customerId
* @param array $attributes
* @return Result\Successful|Result\Error
*/
public static function update($customerId, $attributes)
{
return Configuration::gateway()->customer()->update($customerId, $attributes);
}
/**
*
* @throws Exception\Unexpected
* @param int $customerId
* @param array $attributes
* @return CustomerGateway
*/
public static function updateNoValidate($customerId, $attributes)
{
return Configuration::gateway()->customer()->updateNoValidate($customerId, $attributes);
}
/**
*
* @deprecated since version 2.3.0
* @return string
*/
public static function updateCustomerUrl()
{
return Configuration::gateway()->customer()->updateCustomerUrl();
}
/**
*
* @deprecated since version 2.3.0
* @param string $queryString
* @return Result\Successful|Result\Error
*/
public static function updateFromTransparentRedirect($queryString)
{
return Configuration::gateway()->customer()->updateFromTransparentRedirect($queryString);
}
/* instance methods */
/**
* sets instance properties from an array of values
*
* @ignore
* @access protected
* @param array $customerAttribs array of customer data
*/
protected function _initialize($customerAttribs)
{
$this->_attributes = $customerAttribs;
$addressArray = [];
if (isset($customerAttribs['addresses'])) {
foreach ($customerAttribs['addresses'] AS $address) {
$addressArray[] = Address::factory($address);
}
}
$this->_set('addresses', $addressArray);
$creditCardArray = [];
if (isset($customerAttribs['creditCards'])) {
foreach ($customerAttribs['creditCards'] AS $creditCard) {
$creditCardArray[] = CreditCard::factory($creditCard);
}
}
$this->_set('creditCards', $creditCardArray);
$coinbaseAccountArray = [];
if (isset($customerAttribs['coinbaseAccounts'])) {
foreach ($customerAttribs['coinbaseAccounts'] AS $coinbaseAccount) {
$coinbaseAccountArray[] = CoinbaseAccount::factory($coinbaseAccount);
}
}
$this->_set('coinbaseAccounts', $coinbaseAccountArray);
$paypalAccountArray = [];
if (isset($customerAttribs['paypalAccounts'])) {
foreach ($customerAttribs['paypalAccounts'] AS $paypalAccount) {
$paypalAccountArray[] = PayPalAccount::factory($paypalAccount);
}
}
$this->_set('paypalAccounts', $paypalAccountArray);
$applePayCardArray = [];
if (isset($customerAttribs['applePayCards'])) {
foreach ($customerAttribs['applePayCards'] AS $applePayCard) {
$applePayCardArray[] = ApplePayCard::factory($applePayCard);
}
}
$this->_set('applePayCards', $applePayCardArray);
$androidPayCardArray = [];
if (isset($customerAttribs['androidPayCards'])) {
foreach ($customerAttribs['androidPayCards'] AS $androidPayCard) {
$androidPayCardArray[] = AndroidPayCard::factory($androidPayCard);
}
}
$this->_set('androidPayCards', $androidPayCardArray);
$amexExpressCheckoutCardArray = [];
if (isset($customerAttribs['amexExpressCheckoutCards'])) {
foreach ($customerAttribs['amexExpressCheckoutCards'] AS $amexExpressCheckoutCard) {
$amexExpressCheckoutCardArray[] = AmexExpressCheckoutCard::factory($amexExpressCheckoutCard);
}
}
$this->_set('amexExpressCheckoutCards', $amexExpressCheckoutCardArray);
$venmoAccountArray = array();
if (isset($customerAttribs['venmoAccounts'])) {
foreach ($customerAttribs['venmoAccounts'] AS $venmoAccount) {
$venmoAccountArray[] = VenmoAccount::factory($venmoAccount);
}
}
$this->_set('venmoAccounts', $venmoAccountArray);
$visaCheckoutCardArray = [];
if (isset($customerAttribs['visaCheckoutCards'])) {
foreach ($customerAttribs['visaCheckoutCards'] AS $visaCheckoutCard) {
$visaCheckoutCardArray[] = VisaCheckoutCard::factory($visaCheckoutCard);
}
}
$this->_set('visaCheckoutCards', $visaCheckoutCardArray);
$masterpassCardArray = [];
if (isset($customerAttribs['masterpassCards'])) {
foreach ($customerAttribs['masterpassCards'] AS $masterpassCard) {
$masterpassCardArray[] = MasterpassCard::factory($masterpassCard);
}
}
$this->_set('masterpassCards', $masterpassCardArray);
$samsungPayCardArray = [];
if (isset($customerAttribs['samsungPayCards'])) {
foreach ($customerAttribs['samsungPayCards'] AS $samsungPayCard) {
$samsungPayCardArray[] = SamsungPayCard::factory($samsungPayCard);
}
}
$this->_set('samsungPayCards', $samsungPayCardArray);
$usBankAccountArray = array();
if (isset($customerAttribs['usBankAccounts'])) {
foreach ($customerAttribs['usBankAccounts'] AS $usBankAccount) {
$usBankAccountArray[] = UsBankAccount::factory($usBankAccount);
}
}
$this->_set('usBankAccounts', $usBankAccountArray);
$this->_set('paymentMethods', array_merge(
$this->creditCards,
$this->paypalAccounts,
$this->applePayCards,
$this->coinbaseAccounts,
$this->androidPayCards,
$this->amexExpressCheckoutCards,
$this->venmoAccounts,
$this->visaCheckoutCards,
$this->masterpassCards,
$this->samsungPayCards,
$this->usBankAccounts
));
}
/**
* returns a string representation of the customer
* @return string
*/
public function __toString()
{
return __CLASS__ . '[' .
Util::attributesToString($this->_attributes) .']';
}
/**
* returns false if comparing object is not a Customer,
* or is a Customer with a different id
*
* @param object $otherCust customer to compare against
* @return boolean
*/
public function isEqual($otherCust)
{
return !($otherCust instanceof Customer) ? false : $this->id === $otherCust->id;
}
/**
* returns an array containt all of the customer's payment methods
*
* @deprecated since version 3.1.0 - use the paymentMethods property directly
*
* @return array
*/
public function paymentMethods()
{
return $this->paymentMethods;
}
/**
* returns the customer's default payment method
*
* @return CreditCard|PayPalAccount
*/
public function defaultPaymentMethod()
{
$defaultPaymentMethods = array_filter($this->paymentMethods, 'Braintree\Customer::_defaultPaymentMethodFilter');
return current($defaultPaymentMethods);
}
public static function _defaultPaymentMethodFilter($paymentMethod)
{
return $paymentMethod->isDefault();
}
/* private class properties */
/**
* @access protected
* @var array registry of customer data
*/
protected $_attributes = [
'addresses' => '',
'company' => '',
'creditCards' => '',
'email' => '',
'fax' => '',
'firstName' => '',
'id' => '',
'lastName' => '',
'phone' => '',
'createdAt' => '',
'updatedAt' => '',
'website' => '',
];
/**
* factory method: returns an instance of Customer
* to the requesting method, with populated properties
*
* @ignore
* @param array $attributes
* @return Customer
*/
public static function factory($attributes)
{
$instance = new Customer();
$instance->_initialize($attributes);
return $instance;
}
}
class_alias('Braintree\Customer', 'Braintree_Customer');

View File

@@ -0,0 +1,668 @@
<?php
namespace Braintree;
use InvalidArgumentException;
/**
* Braintree CustomerGateway module
* Creates and manages Customers
*
* <b>== More information ==</b>
*
* For more detailed information on Customers, see {@link https://developers.braintreepayments.com/reference/response/customer/php https://developers.braintreepayments.com/reference/response/customer/php}
*
* @package Braintree
* @category Resources
*/
class CustomerGateway
{
private $_gateway;
private $_config;
private $_http;
public function __construct($gateway)
{
$this->_gateway = $gateway;
$this->_config = $gateway->config;
$this->_config->assertHasAccessTokenOrKeys();
$this->_http = new Http($gateway->config);
}
public function all()
{
$path = $this->_config->merchantPath() . '/customers/advanced_search_ids';
$response = $this->_http->post($path);
$pager = [
'object' => $this,
'method' => 'fetch',
'methodArgs' => [[]]
];
return new ResourceCollection($response, $pager);
}
public function fetch($query, $ids)
{
$criteria = [];
foreach ($query as $term) {
$criteria[$term->name] = $term->toparam();
}
$criteria["ids"] = CustomerSearch::ids()->in($ids)->toparam();
$path = $this->_config->merchantPath() . '/customers/advanced_search';
$response = $this->_http->post($path, ['search' => $criteria]);
return Util::extractattributeasarray(
$response['customers'],
'customer'
);
}
/**
* Creates a customer using the given +attributes+. If <tt>:id</tt> is not passed,
* the gateway will generate it.
*
* <code>
* $result = Customer::create(array(
* 'first_name' => 'John',
* 'last_name' => 'Smith',
* 'company' => 'Smith Co.',
* 'email' => 'john@smith.com',
* 'website' => 'www.smithco.com',
* 'fax' => '419-555-1234',
* 'phone' => '614-555-1234'
* ));
* if($result->success) {
* echo 'Created customer ' . $result->customer->id;
* } else {
* echo 'Could not create customer, see result->errors';
* }
* </code>
*
* @access public
* @param array $attribs
* @return Result\Successful|Result\Error
*/
public function create($attribs = [])
{
Util::verifyKeys(self::createSignature(), $attribs);
return $this->_doCreate('/customers', ['customer' => $attribs]);
}
/**
* attempts the create operation assuming all data will validate
* returns a Customer object instead of a Result
*
* @access public
* @param array $attribs
* @return Customer
* @throws Exception\ValidationError
*/
public function createNoValidate($attribs = [])
{
$result = $this->create($attribs);
return Util::returnObjectOrThrowException(__CLASS__, $result);
}
/**
* create a customer from a TransparentRedirect operation
*
* @deprecated since version 2.3.0
* @access public
* @param array $attribs
* @return Customer
*/
public function createFromTransparentRedirect($queryString)
{
trigger_error("DEPRECATED: Please use TransparentRedirectRequest::confirm", E_USER_NOTICE);
$params = TransparentRedirect::parseAndValidateQueryString(
$queryString
);
return $this->_doCreate(
'/customers/all/confirm_transparent_redirect_request',
['id' => $params['id']]
);
}
/**
*
* @deprecated since version 2.3.0
* @access public
* @param none
* @return string
*/
public function createCustomerUrl()
{
trigger_error("DEPRECATED: Please use TransparentRedirectRequest::url", E_USER_NOTICE);
return $this->_config->baseUrl() . $this->_config->merchantPath() .
'/customers/all/create_via_transparent_redirect_request';
}
/**
* creates a full array signature of a valid create request
* @return array gateway create request format
*/
public static function createSignature()
{
$creditCardSignature = CreditCardGateway::createSignature();
unset($creditCardSignature[array_search('customerId', $creditCardSignature)]);
$signature = [
'id', 'company', 'email', 'fax', 'firstName',
'lastName', 'phone', 'website', 'deviceData',
'deviceSessionId', 'fraudMerchantId', 'paymentMethodNonce',
['riskData' =>
['customerBrowser', 'customerIp', 'customer_browser', 'customer_ip']
],
['creditCard' => $creditCardSignature],
['customFields' => ['_anyKey_']],
['options' => [
['paypal' => [
'payee_email',
'payeeEmail',
'order_id',
'orderId',
'custom_field',
'customField',
'description',
'amount',
['shipping' =>
[
'firstName', 'lastName', 'company', 'countryName',
'countryCodeAlpha2', 'countryCodeAlpha3', 'countryCodeNumeric',
'extendedAddress', 'locality', 'postalCode', 'region',
'streetAddress'],
],
]]
]],
];
return $signature;
}
/**
* creates a full array signature of a valid update request
* @return array update request format
*/
public static function updateSignature()
{
$creditCardSignature = CreditCardGateway::updateSignature();
foreach($creditCardSignature AS $key => $value) {
if(is_array($value) and array_key_exists('options', $value)) {
array_push($creditCardSignature[$key]['options'], 'updateExistingToken');
}
}
$signature = [
'id', 'company', 'email', 'fax', 'firstName',
'lastName', 'phone', 'website', 'deviceData',
'deviceSessionId', 'fraudMerchantId', 'paymentMethodNonce', 'defaultPaymentMethodToken',
['creditCard' => $creditCardSignature],
['customFields' => ['_anyKey_']],
['options' => [
['paypal' => [
'payee_email',
'payeeEmail',
'order_id',
'orderId',
'custom_field',
'customField',
'description',
'amount',
['shipping' =>
[
'firstName', 'lastName', 'company', 'countryName',
'countryCodeAlpha2', 'countryCodeAlpha3', 'countryCodeNumeric',
'extendedAddress', 'locality', 'postalCode', 'region',
'streetAddress'],
],
]],
]],
];
return $signature;
}
/**
* find a customer by id
*
* @access public
* @param string id customer Id
* @param string associationFilterId association filter Id
* @return Customer|boolean The customer object or false if the request fails.
* @throws Exception\NotFound
*/
public function find($id, $associationFilterId = null)
{
$this->_validateId($id);
try {
$queryParams = '';
if ($associationFilterId) {
$queryParams = '?association_filter_id=' . $associationFilterId;
}
$path = $this->_config->merchantPath() . '/customers/' . $id . $queryParams;
$response = $this->_http->get($path);
return Customer::factory($response['customer']);
} catch (Exception\NotFound $e) {
throw new Exception\NotFound(
'customer with id ' . $id . ' not found'
);
}
}
/**
* credit a customer for the passed transaction
*
* @access public
* @param int $customerId
* @param array $transactionAttribs
* @return Result\Successful|Result\Error
*/
public function credit($customerId, $transactionAttribs)
{
$this->_validateId($customerId);
return Transaction::credit(
array_merge($transactionAttribs,
['customerId' => $customerId]
)
);
}
/**
* credit a customer, assuming validations will pass
*
* returns a Transaction object on success
*
* @access public
* @param int $customerId
* @param array $transactionAttribs
* @return Transaction
* @throws Exception\ValidationError
*/
public function creditNoValidate($customerId, $transactionAttribs)
{
$result = $this->credit($customerId, $transactionAttribs);
return Util::returnObjectOrThrowException('Braintree\Transaction', $result);
}
/**
* delete a customer by id
*
* @param string $customerId
*/
public function delete($customerId)
{
$this->_validateId($customerId);
$path = $this->_config->merchantPath() . '/customers/' . $customerId;
$this->_http->delete($path);
return new Result\Successful();
}
/**
* create a new sale for a customer
*
* @param string $customerId
* @param array $transactionAttribs
* @return Result\Successful|Result\Error
* @see Transaction::sale()
*/
public function sale($customerId, $transactionAttribs)
{
$this->_validateId($customerId);
return Transaction::sale(
array_merge($transactionAttribs,
['customerId' => $customerId]
)
);
}
/**
* create a new sale for a customer, assuming validations will pass
*
* returns a Transaction object on success
* @access public
* @param string $customerId
* @param array $transactionAttribs
* @return Transaction
* @throws Exception\ValidationsFailed
* @see Transaction::sale()
*/
public function saleNoValidate($customerId, $transactionAttribs)
{
$result = $this->sale($customerId, $transactionAttribs);
return Util::returnObjectOrThrowException('Braintree\Transaction', $result);
}
/**
* Returns a ResourceCollection of customers matching the search query.
*
* If <b>query</b> is a string, the search will be a basic search.
* If <b>query</b> is a hash, the search will be an advanced search.
* For more detailed information and examples, see {@link https://developers.braintreepayments.com/reference/request/customer/search/php https://developers.braintreepayments.com/reference/request/customer/search/php}
*
* @param mixed $query search query
* @return ResourceCollection
* @throws InvalidArgumentException
*/
public function search($query)
{
$criteria = [];
foreach ($query as $term) {
$result = $term->toparam();
if(is_null($result) || empty($result)) {
throw new InvalidArgumentException('Operator must be provided');
}
$criteria[$term->name] = $term->toparam();
}
$path = $this->_config->merchantPath() . '/customers/advanced_search_ids';
$response = $this->_http->post($path, ['search' => $criteria]);
$pager = [
'object' => $this,
'method' => 'fetch',
'methodArgs' => [$query]
];
return new ResourceCollection($response, $pager);
}
/**
* updates the customer record
*
* if calling this method in static context, customerId
* is the 2nd attribute. customerId is not sent in object context.
*
* @access public
* @param string $customerId (optional)
* @param array $attributes
* @return Result\Successful|Result\Error
*/
public function update($customerId, $attributes)
{
Util::verifyKeys(self::updateSignature(), $attributes);
$this->_validateId($customerId);
return $this->_doUpdate(
'put',
'/customers/' . $customerId,
['customer' => $attributes]
);
}
/**
* update a customer record, assuming validations will pass
*
* if calling this method in static context, customerId
* is the 2nd attribute. customerId is not sent in object context.
* returns a Customer object on success
*
* @access public
* @param string $customerId
* @param array $attributes
* @return Customer
* @throws Exception\ValidationsFailed
*/
public function updateNoValidate($customerId, $attributes)
{
$result = $this->update($customerId, $attributes);
return Util::returnObjectOrThrowException(__CLASS__, $result);
}
/**
*
* @deprecated since version 2.3.0
* @access public
* @return string
*/
public function updateCustomerUrl()
{
trigger_error("DEPRECATED: Please use TransparentRedirectRequest::url", E_USER_NOTICE);
return $this->_config->baseUrl() . $this->_config->merchantPath() .
'/customers/all/update_via_transparent_redirect_request';
}
/**
* update a customer from a TransparentRedirect operation
*
* @deprecated since version 2.3.0
* @access public
* @param string $queryString
* @return object
*/
public function updateFromTransparentRedirect($queryString)
{
trigger_error("DEPRECATED: Please use TransparentRedirectRequest::confirm", E_USER_NOTICE);
$params = TransparentRedirect::parseAndValidateQueryString(
$queryString
);
return $this->_doUpdate(
'post',
'/customers/all/confirm_transparent_redirect_request',
['id' => $params['id']]
);
}
/* instance methods */
/**
* sets instance properties from an array of values
*
* @ignore
* @access protected
* @param array $customerAttribs array of customer data
* @return void
*/
protected function _initialize($customerAttribs)
{
// set the attributes
$this->_attributes = $customerAttribs;
// map each address into its own object
$addressArray = [];
if (isset($customerAttribs['addresses'])) {
foreach ($customerAttribs['addresses'] AS $address) {
$addressArray[] = Address::factory($address);
}
}
$this->_set('addresses', $addressArray);
// map each creditCard into its own object
$creditCardArray = [];
if (isset($customerAttribs['creditCards'])) {
foreach ($customerAttribs['creditCards'] AS $creditCard) {
$creditCardArray[] = CreditCard::factory($creditCard);
}
}
$this->_set('creditCards', $creditCardArray);
// map each coinbaseAccount into its own object
$coinbaseAccountArray = [];
if (isset($customerAttribs['coinbaseAccounts'])) {
foreach ($customerAttribs['coinbaseAccounts'] AS $coinbaseAccount) {
$coinbaseAccountArray[] = CoinbaseAccount::factory($coinbaseAccount);
}
}
$this->_set('coinbaseAccounts', $coinbaseAccountArray);
// map each paypalAccount into its own object
$paypalAccountArray = [];
if (isset($customerAttribs['paypalAccounts'])) {
foreach ($customerAttribs['paypalAccounts'] AS $paypalAccount) {
$paypalAccountArray[] = PayPalAccount::factory($paypalAccount);
}
}
$this->_set('paypalAccounts', $paypalAccountArray);
// map each applePayCard into its own object
$applePayCardArray = [];
if (isset($customerAttribs['applePayCards'])) {
foreach ($customerAttribs['applePayCards'] AS $applePayCard) {
$applePayCardArray[] = ApplePayCard::factory($applePayCard);
}
}
$this->_set('applePayCards', $applePayCardArray);
// map each androidPayCard into its own object
$androidPayCardArray = [];
if (isset($customerAttribs['androidPayCards'])) {
foreach ($customerAttribs['androidPayCards'] AS $androidPayCard) {
$androidPayCardArray[] = AndroidPayCard::factory($androidPayCard);
}
}
$this->_set('androidPayCards', $androidPayCardArray);
$this->_set('paymentMethods', array_merge($this->creditCards, $this->paypalAccounts, $this->applePayCards, $this->coinbaseAccounts, $this->androidPayCards));
}
/**
* returns a string representation of the customer
* @return string
*/
public function __toString()
{
return __CLASS__ . '[' .
Util::attributesToString($this->_attributes) .']';
}
/**
* returns false if comparing object is not a Customer,
* or is a Customer with a different id
*
* @param object $otherCust customer to compare against
* @return boolean
*/
public function isEqual($otherCust)
{
return !($otherCust instanceof Customer) ? false : $this->id === $otherCust->id;
}
/**
* returns an array containt all of the customer's payment methods
*
* @return array
*/
public function paymentMethods()
{
return $this->paymentMethods;
}
/**
* returns the customer's default payment method
*
* @return CreditCard|PayPalAccount|ApplePayCard|AndroidPayCard
*/
public function defaultPaymentMethod()
{
$defaultPaymentMethods = array_filter($this->paymentMethods, 'Braintree\\Customer::_defaultPaymentMethodFilter');
return current($defaultPaymentMethods);
}
public static function _defaultPaymentMethodFilter($paymentMethod)
{
return $paymentMethod->isDefault();
}
/* private class properties */
/**
* @access protected
* @var array registry of customer data
*/
protected $_attributes = [
'addresses' => '',
'company' => '',
'creditCards' => '',
'email' => '',
'fax' => '',
'firstName' => '',
'id' => '',
'lastName' => '',
'phone' => '',
'createdAt' => '',
'updatedAt' => '',
'website' => '',
];
/**
* sends the create request to the gateway
*
* @ignore
* @param string $subPath
* @param array $params
* @return mixed
*/
public function _doCreate($subPath, $params)
{
$fullPath = $this->_config->merchantPath() . $subPath;
$response = $this->_http->post($fullPath, $params);
return $this->_verifyGatewayResponse($response);
}
/**
* verifies that a valid customer id is being used
* @ignore
* @param string customer id
* @throws InvalidArgumentException
*/
private function _validateId($id = null) {
if (is_null($id)) {
throw new InvalidArgumentException(
'expected customer id to be set'
);
}
if (!preg_match('/^[0-9A-Za-z_-]+$/', $id)) {
throw new InvalidArgumentException(
$id . ' is an invalid customer id.'
);
}
}
/* private class methods */
/**
* sends the update request to the gateway
*
* @ignore
* @param string $subPath
* @param array $params
* @return mixed
*/
private function _doUpdate($httpVerb, $subPath, $params)
{
$fullPath = $this->_config->merchantPath() . $subPath;
$response = $this->_http->$httpVerb($fullPath, $params);
return $this->_verifyGatewayResponse($response);
}
/**
* generic method for validating incoming gateway responses
*
* creates a new Customer object and encapsulates
* it inside a Result\Successful object, or
* encapsulates a Errors object inside a Result\Error
* alternatively, throws an Unexpected exception if the response is invalid.
*
* @ignore
* @param array $response gateway response values
* @return Result\Successful|Result\Error
* @throws Exception\Unexpected
*/
private function _verifyGatewayResponse($response)
{
if (isset($response['customer'])) {
// return a populated instance of Customer
return new Result\Successful(
Customer::factory($response['customer'])
);
} else if (isset($response['apiErrorResponse'])) {
return new Result\Error($response['apiErrorResponse']);
} else {
throw new Exception\Unexpected(
"Expected customer or apiErrorResponse"
);
}
}
}
class_alias('Braintree\CustomerGateway', 'Braintree_CustomerGateway');

View File

@@ -0,0 +1,34 @@
<?php
namespace Braintree;
class CustomerSearch
{
public static function addressCountryName() { return new TextNode('address_country_name'); }
public static function addressExtendedAddress() { return new TextNode('address_extended_address'); }
public static function addressFirstName() { return new TextNode('address_first_name'); }
public static function addressLastName() { return new TextNode('address_last_name'); }
public static function addressLocality() { return new TextNode('address_locality'); }
public static function addressPostalCode() { return new TextNode('address_postal_code'); }
public static function addressRegion() { return new TextNode('address_region'); }
public static function addressStreetAddress() { return new TextNode('address_street_address'); }
public static function cardholderName() { return new TextNode('cardholder_name'); }
public static function company() { return new TextNode('company'); }
public static function email() { return new TextNode('email'); }
public static function fax() { return new TextNode('fax'); }
public static function firstName() { return new TextNode('first_name'); }
public static function id() { return new TextNode('id'); }
public static function lastName() { return new TextNode('last_name'); }
public static function paymentMethodToken() { return new TextNode('payment_method_token'); }
public static function paymentMethodTokenWithDuplicates() { return new IsNode('payment_method_token_with_duplicates'); }
public static function paypalAccountEmail() { return new IsNode('paypal_account_email'); }
public static function phone() { return new TextNode('phone'); }
public static function website() { return new TextNode('website'); }
public static function creditCardExpirationDate() { return new EqualityNode('credit_card_expiration_date'); }
public static function creditCardNumber() { return new PartialMatchNode('credit_card_number'); }
public static function ids() { return new MultipleValueNode('ids'); }
public static function createdAt() { return new RangeNode("created_at"); }
}
class_alias('Braintree\CustomerSearch', 'Braintree_CustomerSearch');

View File

@@ -0,0 +1,12 @@
<?php
namespace Braintree;
/**
* @property-read string $name
* @property-read string $phone
* @property-read string $url
*/
class Descriptor extends Instance
{
}
class_alias('Braintree\Descriptor', 'Braintree_Descriptor');

View File

@@ -0,0 +1,60 @@
<?php
namespace Braintree;
/**
* Digest encryption module
* Digest creates an HMAC-SHA1 hash for encrypting messages
*/
class Digest
{
public static function hexDigestSha1($key, $string)
{
if(function_exists('hash_hmac')) {
return self::_builtInHmacSha1($string, $key);
} else {
return self::_hmacSha1($string, $key);
}
}
public static function hexDigestSha256($key, $string)
{
return hash_hmac('sha256', $string, hash('sha256', $key, true));
}
public static function secureCompare($left, $right)
{
if (strlen($left) != strlen($right)) {
return false;
}
$leftBytes = unpack("C*", $left);
$rightBytes = unpack("C*", $right);
$result = 0;
for ($i = 1; $i <= count($leftBytes); $i++) {
$result = $result | ($leftBytes[$i] ^ $rightBytes[$i]);
}
return $result == 0;
}
public static function _builtInHmacSha1($message, $key)
{
return hash_hmac('sha1', $message, sha1($key, true));
}
public static function _hmacSha1($message, $key)
{
$pack = 'H40';
$keyDigest = sha1($key,true);
$innerPad = str_repeat(chr(0x36), 64);
$outerPad = str_repeat(chr(0x5C), 64);
for ($i = 0; $i < 20; $i++) {
$innerPad{$i} = $keyDigest{$i} ^ $innerPad{$i};
$outerPad{$i} = $keyDigest{$i} ^ $outerPad{$i};
}
return sha1($outerPad.pack($pack, sha1($innerPad.$message)));
}
}
class_alias('Braintree\Digest', 'Braintree_Digest');

View File

@@ -0,0 +1,66 @@
<?php
namespace Braintree;
class Disbursement extends Base
{
const TYPE_CREDIT = "credit";
const TYPE_DEBIT = "debit";
private $_merchantAccount;
protected function _initialize($disbursementAttribs)
{
$this->_attributes = $disbursementAttribs;
$this->merchantAccountDetails = $disbursementAttribs['merchantAccount'];
if (isset($disbursementAttribs['merchantAccount'])) {
$this->_set('merchantAccount',
MerchantAccount::factory($disbursementAttribs['merchantAccount'])
);
}
}
public function transactions()
{
$collection = Transaction::search([
TransactionSearch::ids()->in($this->transactionIds),
]);
return $collection;
}
public static function factory($attributes)
{
$instance = new self();
$instance->_initialize($attributes);
return $instance;
}
public function __toString()
{
$display = [
'id', 'merchantAccountDetails', 'exceptionMessage', 'amount',
'disbursementDate', 'followUpAction', 'retry', 'success',
'transactionIds', 'disbursementType'
];
$displayAttributes = [];
foreach ($display AS $attrib) {
$displayAttributes[$attrib] = $this->$attrib;
}
return __CLASS__ . '[' .
Util::attributesToString($displayAttributes) .']';
}
public function isDebit()
{
return $this->disbursementType == Disbursement::TYPE_DEBIT;
}
public function isCredit()
{
return $this->disbursementType == Disbursement::TYPE_CREDIT;
}
}
class_alias('Braintree\Disbursement', 'Braintree_Disbursement');

View File

@@ -0,0 +1,24 @@
<?php
namespace Braintree;
/**
* Disbursement details from a transaction
* Creates an instance of DisbursementDetails as returned from a transaction
*
*
* @package Braintree
*
* @property-read string $disbursementDate
* @property-read boolean $fundsHeld
* @property-read string $settlementAmount
* @property-read string $settlementCurrencyExchangeRate
* @property-read string $settlementCurrencyIsoCode
* @property-read string $success
*/
class DisbursementDetails extends Instance
{
public function isValid() {
return !is_null($this->disbursementDate);
}
}
class_alias('Braintree\DisbursementDetails', 'Braintree_DisbursementDetails');

View File

@@ -0,0 +1,35 @@
<?php
namespace Braintree;
/**
* @property-read string $amount
* @property-read \DateTime $createdAt
* @property-read int|null $currentBillingCycle
* @property-read string $description
* @property-read string $id
* @property-read string|null $kind
* @property-read string $merchantId
* @property-read string $name
* @property-read boolean $neverExpires
* @property-read int|null $numberOfBillingCycles
* @property-read int|null $quantity
* @property-read \DateTime $updatedAt
*/
class Discount extends Modification
{
public static function factory($attributes)
{
$instance = new self();
$instance->_initialize($attributes);
return $instance;
}
// static methods redirecting to gateway
public static function all()
{
return Configuration::gateway()->discount()->all();
}
}
class_alias('Braintree\Discount', 'Braintree_Discount');

View File

@@ -0,0 +1,31 @@
<?php
namespace Braintree;
class DiscountGateway
{
private $_gateway;
private $_config;
private $_http;
public function __construct($gateway)
{
$this->_gateway = $gateway;
$this->_config = $gateway->config;
$this->_config->assertHasAccessTokenOrKeys();
$this->_http = new Http($gateway->config);
}
public function all()
{
$path = $this->_config->merchantPath() . '/discounts';
$response = $this->_http->get($path);
$discounts = ["discount" => $response['discounts']];
return Util::extractAttributeAsArray(
$discounts,
'discount'
);
}
}
class_alias('Braintree\DiscountGateway', 'Braintree_DiscountGateway');

View File

@@ -0,0 +1,191 @@
<?php
namespace Braintree;
/**
* Creates an instance of Dispute as returned from a transaction
*
*
* @package Braintree
*
* @property-read string $amount
* @property-read \DateTime $createdAt
* @property-read string $currencyIsoCode
* @property-read string $disbursementDate
* @property-read \Braintree\Dispute\EvidenceDetails $evidence
* @property-read string $id
* @property-read string $kind
* @property-read string $merchantAccountId
* @property-read string $originalDisputeId
* @property-read string $processorComments
* @property-read string $reason
* @property-read string $reasonCode
* @property-read string $reasonDescription
* @property-read \DateTime $receivedDate
* @property-read string $referenceNumber
* @property-read \DateTime $replyByDate
* @property-read string $status
* @property-read \Braintree\Dispute\StatusHistoryDetails[] $statusHistory
* @property-read \Braintree\Dispute\TransactionDetails $transaction
* @property-read \Braintree\Dispute\TransactionDetails $transactionDetails
* @property-read \DateTime $updatedAt
*/
class Dispute extends Base
{
protected $_attributes = [];
/* Dispute Status */
const ACCEPTED = 'accepted';
const DISPUTED = 'disputed';
const EXPIRED = 'expired';
const OPEN = 'open';
const WON = 'won';
const LOST = 'lost';
/* deprecated; for backwards compatibilty */
const Open = 'open';
/* Dispute Reason */
const CANCELLED_RECURRING_TRANSACTION = "cancelled_recurring_transaction";
const CREDIT_NOT_PROCESSED = "credit_not_processed";
const DUPLICATE = "duplicate";
const FRAUD = "fraud";
const GENERAL = "general";
const INVALID_ACCOUNT = "invalid_account";
const NOT_RECOGNIZED = "not_recognized";
const PRODUCT_NOT_RECEIVED = "product_not_received";
const PRODUCT_UNSATISFACTORY = "product_unsatisfactory";
const TRANSACTION_AMOUNT_DIFFERS = "transaction_amount_differs";
const RETRIEVAL = "retrieval";
/* Dispute Kind */
const CHARGEBACK = 'chargeback';
const PRE_ARBITRATION = 'pre_arbitration';
// RETRIEVAL for kind already defined under Dispute Reason
protected function _initialize($disputeAttribs)
{
$this->_attributes = $disputeAttribs;
if (isset($disputeAttribs['transaction'])) {
$transactionDetails = new Dispute\TransactionDetails($disputeAttribs['transaction']);
$this->_set('transactionDetails', $transactionDetails);
$this->_set('transaction', $transactionDetails);
}
if (isset($disputeAttribs['evidence'])) {
$evidenceArray = array_map(function($evidence) {
return new Dispute\EvidenceDetails($evidence);
}, $disputeAttribs['evidence']);
$this->_set('evidence', $evidenceArray);
}
if (isset($disputeAttribs['statusHistory'])) {
$statusHistoryArray = array_map(function($statusHistory) {
return new Dispute\StatusHistoryDetails($statusHistory);
}, $disputeAttribs['statusHistory']);
$this->_set('statusHistory', $statusHistoryArray);
}
if (isset($disputeAttribs['transaction'])) {
$this->_set('transaction',
new Dispute\TransactionDetails($disputeAttribs['transaction'])
);
}
}
public static function factory($attributes)
{
$instance = new self();
$instance->_initialize($attributes);
return $instance;
}
public function __toString()
{
$display = [
'amount', 'reason', 'status',
'replyByDate', 'receivedDate', 'currencyIsoCode'
];
$displayAttributes = [];
foreach ($display AS $attrib) {
$displayAttributes[$attrib] = $this->$attrib;
}
return __CLASS__ . '[' .
Util::attributesToString($displayAttributes) .']';
}
/**
* Accepts a dispute, given a dispute ID
*
* @param string $id
*/
public static function accept($id)
{
return Configuration::gateway()->dispute()->accept($id);
}
/**
* Adds file evidence to a dispute, given a dispute ID and a document ID
*
* @param string $disputeId
* @param string $documentIdOrRequest
*/
public static function addFileEvidence($disputeId, $documentIdOrRequest)
{
return Configuration::gateway()->dispute()->addFileEvidence($disputeId, $documentIdOrRequest);
}
/**
* Adds text evidence to a dispute, given a dispute ID and content
*
* @param string $id
* @param string $contentOrRequest
*/
public static function addTextEvidence($id, $contentOrRequest)
{
return Configuration::gateway()->dispute()->addTextEvidence($id, $contentOrRequest);
}
/**
* Finalize a dispute, given a dispute ID
*
* @param string $id
*/
public static function finalize($id)
{
return Configuration::gateway()->dispute()->finalize($id);
}
/**
* Find a dispute, given a dispute ID
*
* @param string $id
*/
public static function find($id)
{
return Configuration::gateway()->dispute()->find($id);
}
/**
* Remove evidence from a dispute, given a dispute ID and evidence ID
*
* @param string $disputeId
* @param string $evidenceId
*/
public static function removeEvidence($disputeId, $evidenceId)
{
return Configuration::gateway()->dispute()->removeEvidence($disputeId, $evidenceId);
}
/**
* Search for Disputes, given a DisputeSearch query
*
* @param DisputeSearch $query
*/
public static function search($query)
{
return Configuration::gateway()->dispute()->search($query);
}
}
class_alias('Braintree\Dispute', 'Braintree_Dispute');

View File

@@ -0,0 +1,31 @@
<?php
namespace Braintree\Dispute;
use Braintree\Instance;
/**
* Evidence details for a dispute
*
* @package Braintree
*
* @property-read string $category
* @property-read string $comment
* @property-read \DateTime $createdAt
* @property-read string $id
* @property-read \DateTime $sentToProcessorAt
* @property-read string $sequenceNumber
* @property-read string $tag
* @property-read string $url
*/
class EvidenceDetails extends Instance
{
public function __construct($attributes)
{
if (array_key_exists('category', $attributes)) {
$attributes['tag'] = $attributes['category'];
}
parent::__construct($attributes);
}
}
class_alias('Braintree\Dispute\EvidenceDetails', 'Braintree_Dispute_EvidenceDetails');

View File

@@ -0,0 +1,20 @@
<?php
namespace Braintree\Dispute;
use Braintree\Instance;
/**
* Status History for a dispute
*
* @package Braintree
*
* @property-read \DateTime $disbursementDate
* @property-read \DateTime $effectiveDate
* @property-read string $status
* @property-read \DateTime $timestamp
*/
class StatusHistoryDetails extends Instance
{
}
class_alias('Braintree\Dispute\StatusHistoryDetails', 'Braintree_Dispute_StatusHistoryDetails');

View File

@@ -0,0 +1,25 @@
<?php
namespace Braintree\Dispute;
use Braintree\Instance;
/**
* Transaction details for a dispute
*
* @package Braintree
*/
/**
* Creates an instance of DisbursementDetails as returned from a transaction
*
*
* @package Braintree
*
* @property-read string $amount
* @property-read string $id
*/
class TransactionDetails extends Instance
{
}
class_alias('Braintree\Dispute\TransactionDetails', 'Braintree_Dispute_TransactionDetails');

View File

@@ -0,0 +1,274 @@
<?php
namespace Braintree;
use InvalidArgumentException;
/**
* Braintree DisputeGateway module
* PHP Version 5
* Creates and manages Braintree Disputes
*
* @package Braintree
*/
class DisputeGateway
{
/**
* @var Gateway
*/
private $_gateway;
/**
* @var Configuration
*/
private $_config;
/**
* @var Http
*/
private $_http;
/**
* @param Gateway $gateway
*/
public function __construct($gateway)
{
$this->_gateway = $gateway;
$this->_config = $gateway->config;
$this->_config->assertHasAccessTokenOrKeys();
$this->_http = new Http($gateway->config);
}
/* public class methods */
/**
* Accepts a dispute, given a dispute ID
*
* @param string $id
*/
public function accept($id)
{
try {
if (trim($id) == "") {
throw new Exception\NotFound();
}
$path = $this->_config->merchantPath() . '/disputes/' . $id . '/accept';
$response = $this->_http->put($path);
if (isset($response['apiErrorResponse'])) {
return new Result\Error($response['apiErrorResponse']);
}
return new Result\Successful();
} catch (Exception\NotFound $e) {
throw new Exception\NotFound('dispute with id "' . $id . '" not found');
}
}
/**
* Adds file evidence to a dispute, given a dispute ID and a document ID
*
* @param string $disputeId
* @param string $documentIdOrRequest
*/
public function addFileEvidence($disputeId, $documentIdOrRequest)
{
$request = is_array($documentIdOrRequest) ? $documentIdOrRequest : ['documentId' => $documentIdOrRequest];
if (trim($disputeId) == "") {
throw new Exception\NotFound('dispute with id "' . $disputeId . '" not found');
}
if (trim($request['documentId']) == "") {
throw new Exception\NotFound('document with id "' . $request['documentId'] . '" not found');
}
try {
if (array_key_exists('category', $request)) {
if (trim($request['category']) == "") {
throw new InvalidArgumentException('category cannot be blank');
}
}
$request['document_upload_id'] = $request['documentId'];
unset($request['documentId']);
$path = $this->_config->merchantPath() . '/disputes/' . $disputeId . '/evidence';
$response = $this->_http->post($path, ['evidence' => $request]);
if (isset($response['apiErrorResponse'])) {
return new Result\Error($response['apiErrorResponse']);
}
if (isset($response['evidence'])) {
$evidence = new Dispute\EvidenceDetails($response['evidence']);
return new Result\Successful($evidence);
}
} catch (Exception\NotFound $e) {
throw new Exception\NotFound('dispute with id "' . $disputeId . '" not found');
}
}
/**
* Adds text evidence to a dispute, given a dispute ID and content
*
* @param string $id
* @param string $content
*/
public function addTextEvidence($id, $contentOrRequest)
{
$request = is_array($contentOrRequest) ? $contentOrRequest : ['content' => $contentOrRequest];
if (trim($request['content']) == "") {
throw new InvalidArgumentException('content cannot be blank');
}
try {
$evidence = [
'comments' => $request['content'],
];
if (trim($id) == "") {
throw new Exception\NotFound();
}
if (array_key_exists('tag', $request)) {
$evidence['category'] = $request['tag'];
}
if (array_key_exists('category', $request)) {
if (trim($request['category']) == "") {
throw new InvalidArgumentException('category cannot be blank');
}
$evidence['category'] = $request['category'];
}
if (array_key_exists('sequenceNumber', $request)) {
if (trim($request['sequenceNumber']) == "") {
throw new InvalidArgumentException('sequenceNumber cannot be blank');
} else if ((string)(int)($request['sequenceNumber']) != $request['sequenceNumber']) {
throw new InvalidArgumentException('sequenceNumber must be an integer');
}
$evidence['sequenceNumber'] = (int)$request['sequenceNumber'];
}
$path = $this->_config->merchantPath() . '/disputes/' . $id . '/evidence';
$response = $this->_http->post($path, [
'evidence' => $evidence
]);
if (isset($response['apiErrorResponse'])) {
return new Result\Error($response['apiErrorResponse']);
}
if (isset($response['evidence'])) {
$evidence = new Dispute\EvidenceDetails($response['evidence']);
return new Result\Successful($evidence);
}
} catch (Exception\NotFound $e) {
throw new Exception\NotFound('dispute with id "' . $id . '" not found');
}
}
/**
* Finalize a dispute, given a dispute ID
*
* @param string $id
*/
public function finalize($id)
{
try {
if (trim($id) == "") {
throw new Exception\NotFound();
}
$path = $this->_config->merchantPath() . '/disputes/' . $id . '/finalize';
$response = $this->_http->put($path);
if (isset($response['apiErrorResponse'])) {
return new Result\Error($response['apiErrorResponse']);
}
return new Result\Successful();
} catch (Exception\NotFound $e) {
throw new Exception\NotFound('dispute with id "' . $id . '" not found');
}
}
/**
* Find a dispute, given a dispute ID
*
* @param string $id
*/
public function find($id)
{
if (trim($id) == "") {
throw new Exception\NotFound('dispute with id "' . $id . '" not found');
}
try {
$path = $this->_config->merchantPath() . '/disputes/' . $id;
$response = $this->_http->get($path);
return Dispute::factory($response['dispute']);
} catch (Exception\NotFound $e) {
throw new Exception\NotFound('dispute with id "' . $id . '" not found');
}
}
/**
* Remove evidence from a dispute, given a dispute ID and evidence ID
*
* @param string $disputeId
* @param string $evidenceId
*/
public function removeEvidence($disputeId, $evidenceId)
{
try {
if (trim($disputeId) == "" || trim($evidenceId) == "") {
throw new Exception\NotFound();
}
$path = $this->_config->merchantPath() . '/disputes/' . $disputeId . '/evidence/' . $evidenceId;
$response = $this->_http->delete($path);
if (isset($response['apiErrorResponse'])) {
return new Result\Error($response['apiErrorResponse']);
}
return new Result\Successful();
} catch (Exception\NotFound $e) {
throw new Exception\NotFound('evidence with id "' . $evidenceId . '" for dispute with id "' . $disputeId . '" not found');
}
}
/**
* Search for Disputes, given a DisputeSearch query
*
* @param DisputeSearch $query
*/
public function search($query)
{
$criteria = [];
foreach ($query as $term) {
$criteria[$term->name] = $term->toparam();
}
$pager = [
'object' => $this,
'method' => 'fetchDisputes',
'query' => $criteria
];
return new PaginatedCollection($pager);
}
public function fetchDisputes($query, $page)
{
$response = $this->_http->post($this->_config->merchantPath() . '/disputes/advanced_search?page=' . $page, [
'search' => $query
]);
$body = $response['disputes'];
$disputes = Util::extractattributeasarray($body, 'dispute');
$totalItems = $body['totalItems'][0];
$pageSize = $body['pageSize'][0];
return new PaginatedResult($totalItems, $pageSize, $disputes);
}
}
class_alias('Braintree\DisputeGateway', 'Braintree_DisputeGateway');

View File

@@ -0,0 +1,90 @@
<?php
namespace Braintree;
class DisputeSearch
{
public static function amountDisputed() {
return new RangeNode("amount_disputed");
}
public static function amountWon()
{
return new RangeNode("amount_won");
}
public static function caseNumber()
{
return new TextNode("case_number");
}
public static function id()
{
return new TextNode("id");
}
public static function customerId()
{
return new TextNode("customer_id");
}
public static function kind()
{
return new MultipleValueNode("kind");
}
public static function merchantAccountId()
{
return new MultipleValueNode("merchant_account_id");
}
public static function reason()
{
return new MultipleValueNode("reason");
}
public static function reasonCode()
{
return new MultipleValueNode("reason_code");
}
public static function receivedDate()
{
return new RangeNode("received_date");
}
public static function disbursementDate()
{
return new RangeNode("disbursement_date");
}
public static function effectiveDate()
{
return new RangeNode("effective_date");
}
public static function referenceNumber()
{
return new TextNode("reference_number");
}
public static function replyByDate()
{
return new RangeNode("reply_by_date");
}
public static function status()
{
return new MultipleValueNode("status");
}
public static function transactionId()
{
return new TextNode("transaction_id");
}
public static function transactionSource()
{
return new MultipleValueNode("transaction_source");
}
}
class_alias('Braintree\DisputeSearch', 'Braintree_DisputeSearch');

View File

@@ -0,0 +1,52 @@
<?php
namespace Braintree;
use InvalidArgumentException;
/**
* Upload documents to Braintree in exchange for a DocumentUpload object.
*
* An example of creating a document upload with all available fields:
* $result = Braintree\DocumentUpload::create([
* "kind" => Braintree\DocumentUpload::EVIDENCE_DOCUMENT,
* "file" => $pngFile
* ]);
*
* For more information on DocumentUploads, see https://developers.braintreepayments.com/reference/request/document_upload/create
*
* @property-read string $contentType
* @property-read \DateTime $expiresAt
* @property-read string $id
* @property-read string $kind
* @property-read string $name
* @property-read int $size
*/
class DocumentUpload extends Base
{
/* DocumentUpload Kind */
const EVIDENCE_DOCUMENT = "evidence_document";
protected function _initialize($documentUploadAttribs)
{
$this->_attributes = $documentUploadAttribs;
}
/**
* Creates a DocumentUpload object
* @param kind The kind of document
* @param file The open file to upload
* @throws InvalidArgumentException if the params are not expected
*/
public static function create($params)
{
return Configuration::gateway()->documentUpload()->create($params);
}
public static function factory($attributes)
{
$instance = new self();
$instance->_initialize($attributes);
return $instance;
}
}
class_alias('Braintree\DocumentUpload', 'Braintree_DocumentUpload');

View File

@@ -0,0 +1,81 @@
<?php
namespace Braintree;
use InvalidArgumentException;
/**
* Braintree DisputeGateway module
* PHP Version 5
* Creates and manages Braintree Disputes
*
* @package Braintree
*/
class DocumentUploadGateway
{
/**
* @var Gateway
*/
private $_gateway;
/**
* @var Configuration
*/
private $_config;
/**
* @var Http
*/
private $_http;
/**
* @param Gateway $gateway
*/
public function __construct($gateway)
{
$this->_gateway = $gateway;
$this->_config = $gateway->config;
$this->_config->assertHasAccessTokenOrKeys();
$this->_http = new Http($gateway->config);
}
/* public class methods */
/**
* Accepts a dispute, given a dispute ID
*
* @param string $id
*/
public function create($params)
{
Util::verifyKeys(self::createSignature(), $params);
$file = $params['file'];
if (!is_resource($file)) {
throw new InvalidArgumentException('file must be a stream resource');
}
$payload = [
'document_upload[kind]' => $params['kind']
];
$path = $this->_config->merchantPath() . '/document_uploads/';
$response = $this->_http->postMultipart($path, $payload, $file);
if (isset($response['apiErrorResponse'])) {
return new Result\Error($response['apiErrorResponse']);
}
if (isset($response['documentUpload'])) {
$documentUpload = DocumentUpload::factory($response['documentUpload']);
return new Result\Successful($documentUpload);
}
}
public static function createSignature()
{
return [
'file', 'kind'
];
}
}
class_alias('Braintree\DocumentUploadGateway', 'Braintree_DocumentUploadGateway');

View File

@@ -0,0 +1,23 @@
<?php
namespace Braintree;
class EndsWithNode
{
public function __construct($name)
{
$this->name = $name;
$this->searchTerms = [];
}
public function endsWith($value)
{
$this->searchTerms["ends_with"] = strval($value);
return $this;
}
public function toParam()
{
return $this->searchTerms;
}
}
class_alias('Braintree\EndsWithNode', 'Braintree_EndsWithNode');

View File

@@ -0,0 +1,12 @@
<?php
namespace Braintree;
class EqualityNode extends IsNode
{
function isNot($value)
{
$this->searchTerms['is_not'] = strval($value);
return $this;
}
}
class_alias('Braintree\EqualityNode', 'Braintree_EqualityNode');

View File

@@ -0,0 +1,671 @@
<?php
namespace Braintree\Error;
/**
*
* Validation Error codes and messages
*
* ErrorCodes class provides constants for validation errors.
* The constants should be used to check for a specific validation
* error in a ValidationErrorCollection.
* The error messages returned from the server may change;
* but the codes will remain the same.
*
* @package Braintree
* @subpackage Errors
* @category Validation
*/
class Codes
{
const ADDRESS_CANNOT_BE_BLANK = '81801';
const ADDRESS_COMPANY_IS_INVALID = '91821';
const ADDRESS_COMPANY_IS_TOO_LONG = '81802';
const ADDRESS_COUNTRY_CODE_ALPHA2_IS_NOT_ACCEPTED = '91814';
const ADDRESS_COUNTRY_CODE_ALPHA3_IS_NOT_ACCEPTED = '91816';
const ADDRESS_COUNTRY_CODE_NUMERIC_IS_NOT_ACCEPTED = '91817';
const ADDRESS_COUNTRY_NAME_IS_NOT_ACCEPTED = '91803';
const ADDRESS_EXTENDED_ADDRESS_IS_INVALID = '91823';
const ADDRESS_EXTENDED_ADDRESS_IS_TOO_LONG = '81804';
const ADDRESS_FIRST_NAME_IS_INVALID = '91819';
const ADDRESS_FIRST_NAME_IS_TOO_LONG = '81805';
const ADDRESS_INCONSISTENT_COUNTRY = '91815';
const ADDRESS_LAST_NAME_IS_INVALID = '91820';
const ADDRESS_LAST_NAME_IS_TOO_LONG = '81806';
const ADDRESS_LOCALITY_IS_INVALID = '91824';
const ADDRESS_LOCALITY_IS_TOO_LONG = '81807';
const ADDRESS_POSTAL_CODE_INVALID_CHARACTERS = '81813';
const ADDRESS_POSTAL_CODE_IS_INVALID = '91826';
const ADDRESS_POSTAL_CODE_IS_REQUIRED = '81808';
const ADDRESS_POSTAL_CODE_IS_TOO_LONG = '81809';
const ADDRESS_REGION_IS_INVALID = '91825';
const ADDRESS_REGION_IS_TOO_LONG = '81810';
const ADDRESS_STATE_IS_INVALID_FOR_SELLER_PROTECTION = '81827';
const ADDRESS_STREET_ADDRESS_IS_INVALID = '91822';
const ADDRESS_STREET_ADDRESS_IS_REQUIRED = '81811';
const ADDRESS_STREET_ADDRESS_IS_TOO_LONG = '81812';
const ADDRESS_TOO_MANY_ADDRESSES_PER_CUSTOMER = '91818';
const APPLE_PAY_CARDS_ARE_NOT_ACCEPTED = '83501';
const APPLE_PAY_CUSTOMER_ID_IS_REQUIRED_FOR_VAULTING = '83502';
const APPLE_PAY_TOKEN_IS_IN_USE = '93503';
const APPLE_PAY_PAYMENT_METHOD_NONCE_CONSUMED = '93504';
const APPLE_PAY_PAYMENT_METHOD_NONCE_UNKNOWN = '93505';
const APPLE_PAY_PAYMENT_METHOD_NONCE_UNLOCKED = '93506';
const APPLE_PAY_PAYMENT_METHOD_NONCE_CARD_TYPE_IS_NOT_ACCEPTED = '83518';
const APPLE_PAY_CANNOT_UPDATE_APPLE_PAY_CARD_USING_PAYMENT_METHOD_NONCE = '93507';
const APPLE_PAY_NUMBER_IS_REQUIRED = '93508';
const APPLE_PAY_EXPIRATION_MONTH_IS_REQUIRED = '93509';
const APPLE_PAY_EXPIRATION_YEAR_IS_REQUIRED = '93510';
const APPLE_PAY_CRYPTOGRAM_IS_REQUIRED = '93511';
const APPLE_PAY_DECRYPTION_FAILED = '83512';
const APPLE_PAY_DISABLED = '93513';
const APPLE_PAY_MERCHANT_NOT_CONFIGURED = '93514';
const APPLE_PAY_MERCHANT_KEYS_ALREADY_CONFIGURED = '93515';
const APPLE_PAY_MERCHANT_KEYS_NOT_CONFIGURED = '93516';
const APPLE_PAY_CERTIFICATE_INVALID = '93517';
const APPLE_PAY_CERTIFICATE_MISMATCH = '93519';
const APPLE_PAY_INVALID_TOKEN = '83520';
const APPLE_PAY_PRIVATE_KEY_MISMATCH = '93521';
const APPLE_PAY_KEY_MISMATCH_STORING_CERTIFICATE = '93522';
const AUTHORIZATION_FINGERPRINT_INVALID_CREATED_AT = '93204';
const AUTHORIZATION_FINGERPRINT_INVALID_FORMAT = '93202';
const AUTHORIZATION_FINGERPRINT_INVALID_PUBLIC_KEY = '93205';
const AUTHORIZATION_FINGERPRINT_INVALID_SIGNATURE = '93206';
const AUTHORIZATION_FINGERPRINT_MISSING_FINGERPRINT = '93201';
const AUTHORIZATION_FINGERPRINT_OPTIONS_NOT_ALLOWED_WITHOUT_CUSTOMER = '93207';
const AUTHORIZATION_FINGERPRINT_SIGNATURE_REVOKED = '93203';
const CLIENT_TOKEN_CUSTOMER_DOES_NOT_EXIST = '92804';
const CLIENT_TOKEN_FAIL_ON_DUPLICATE_PAYMENT_METHOD_REQUIRES_CUSTOMER_ID = '92803';
const CLIENT_TOKEN_MAKE_DEFAULT_REQUIRES_CUSTOMER_ID = '92801';
const CLIENT_TOKEN_PROXY_MERCHANT_DOES_NOT_EXIST = '92805';
const CLIENT_TOKEN_UNSUPPORTED_VERSION = '92806';
const CLIENT_TOKEN_VERIFY_CARD_REQUIRES_CUSTOMER_ID = '92802';
const CLIENT_TOKEN_MERCHANT_ACCOUNT_DOES_NOT_EXIST = '92807';
const CREDIT_CARD_BILLING_ADDRESS_CONFLICT = '91701';
const CREDIT_CARD_BILLING_ADDRESS_FORMAT_IS_INVALID = '91744';
const CREDIT_CARD_BILLING_ADDRESS_ID_IS_INVALID = '91702';
const CREDIT_CARD_CANNOT_UPDATE_CARD_USING_PAYMENT_METHOD_NONCE = '91735';
const CREDIT_CARD_CARDHOLDER_NAME_IS_TOO_LONG = '81723';
const CREDIT_CARD_CREDIT_CARD_TYPE_IS_NOT_ACCEPTED = '81703';
const CREDIT_CARD_CREDIT_CARD_TYPE_IS_NOT_ACCEPTED_BY_SUBSCRIPTION_MERCHANT_ACCOUNT = '81718';
const CREDIT_CARD_CUSTOMER_ID_IS_INVALID = '91705';
const CREDIT_CARD_CUSTOMER_ID_IS_REQUIRED = '91704';
const CREDIT_CARD_CVV_IS_INVALID = '81707';
const CREDIT_CARD_CVV_IS_REQUIRED = '81706';
const CREDIT_CARD_CVV_VERIFICATION_FAILED = '81736';
const CREDIT_CARD_DUPLICATE_CARD_EXISTS = '81724';
const CREDIT_CARD_EXPIRATION_DATE_CONFLICT = '91708';
const CREDIT_CARD_EXPIRATION_DATE_IS_INVALID = '81710';
const CREDIT_CARD_EXPIRATION_DATE_IS_REQUIRED = '81709';
const CREDIT_CARD_EXPIRATION_DATE_YEAR_IS_INVALID = '81711';
const CREDIT_CARD_EXPIRATION_MONTH_IS_INVALID = '81712';
const CREDIT_CARD_EXPIRATION_YEAR_IS_INVALID = '81713';
const CREDIT_CARD_INVALID_PARAMS_FOR_CREDIT_CARD_UPDATE = '91745';
const CREDIT_CARD_INVALID_VENMO_SDK_PAYMENT_METHOD_CODE = '91727';
const CREDIT_CARD_NUMBER_INVALID_LENGTH = '81716';
const CREDIT_CARD_NUMBER_IS_INVALID = '81715';
const CREDIT_CARD_NUMBER_IS_PROHIBITED = '81750';
const CREDIT_CARD_NUMBER_IS_REQUIRED = '81714';
const CREDIT_CARD_NUMBER_LENGTH_IS_INVALID = '81716';
const CREDIT_CARD_NUMBER_MUST_BE_TEST_NUMBER = '81717';
const CREDIT_CARD_OPTIONS_UPDATE_EXISTING_TOKEN_IS_INVALID = '91723';
const CREDIT_CARD_OPTIONS_UPDATE_EXISTING_TOKEN_NOT_ALLOWED = '91729';
const CREDIT_CARD_OPTIONS_VERIFICATION_AMOUNT_CANNOT_BE_NEGATIVE = '91739';
const CREDIT_CARD_OPTIONS_VERIFICATION_AMOUNT_FORMAT_IS_INVALID = '91740';
const CREDIT_CARD_OPTIONS_VERIFICATION_AMOUNT_IS_TOO_LARGE = '91752';
const CREDIT_CARD_OPTIONS_VERIFICATION_AMOUNT_NOT_SUPPORTED_BY_PROCESSOR = '91741';
const CREDIT_CARD_OPTIONS_VERIFICATION_MERCHANT_ACCOUNT_ID_IS_INVALID = '91728';
const CREDIT_CARD_OPTIONS_VERIFICATION_MERCHANT_ACCOUNT_IS_FORBIDDEN = '91743';
const CREDIT_CARD_OPTIONS_VERIFICATION_MERCHANT_ACCOUNT_IS_SUSPENDED = '91742';
const CREDIT_CARD_OPTIONS_VERIFICATION_MERCHANT_ACCOUNT_CANNOT_BE_SUB_MERCHANT_ACCOUNT = '91755';
const CREDIT_CARD_PAYMENT_METHOD_CONFLICT = '81725';
const CREDIT_CARD_PAYMENT_METHOD_IS_NOT_A_CREDIT_CARD = '91738';
const CREDIT_CARD_PAYMENT_METHOD_NONCE_CARD_TYPE_IS_NOT_ACCEPTED = '91734';
const CREDIT_CARD_PAYMENT_METHOD_NONCE_CONSUMED = '91731';
const CREDIT_CARD_PAYMENT_METHOD_NONCE_LOCKED = '91733';
const CREDIT_CARD_PAYMENT_METHOD_NONCE_UNKNOWN = '91732';
const CREDIT_CARD_POSTAL_CODE_VERIFICATION_FAILED = '81737';
const CREDIT_CARD_TOKEN_FORMAT_IS_INVALID = '91718';
const CREDIT_CARD_TOKEN_INVALID = '91718';
const CREDIT_CARD_TOKEN_IS_IN_USE = '91719';
const CREDIT_CARD_TOKEN_IS_NOT_ALLOWED = '91721';
const CREDIT_CARD_TOKEN_IS_REQUIRED = '91722';
const CREDIT_CARD_TOKEN_IS_TOO_LONG = '91720';
const CREDIT_CARD_VENMO_SDK_PAYMENT_METHOD_CODE_CARD_TYPE_IS_NOT_ACCEPTED = '91726';
const CREDIT_CARD_VERIFICATION_NOT_SUPPORTED_ON_THIS_MERCHANT_ACCOUNT = '91730';
const CUSTOMER_COMPANY_IS_TOO_LONG = '81601';
const CUSTOMER_CUSTOM_FIELD_IS_INVALID = '91602';
const CUSTOMER_CUSTOM_FIELD_IS_TOO_LONG = '81603';
const CUSTOMER_EMAIL_FORMAT_IS_INVALID = '81604';
const CUSTOMER_EMAIL_IS_INVALID = '81604';
const CUSTOMER_EMAIL_IS_REQUIRED = '81606';
const CUSTOMER_EMAIL_IS_TOO_LONG = '81605';
const CUSTOMER_FAX_IS_TOO_LONG = '81607';
const CUSTOMER_FIRST_NAME_IS_TOO_LONG = '81608';
const CUSTOMER_ID_IS_INVAILD = '91610'; //Deprecated
const CUSTOMER_ID_IS_INVALID = '91610';
const CUSTOMER_ID_IS_IN_USE = '91609';
const CUSTOMER_ID_IS_NOT_ALLOWED = '91611';
const CUSTOMER_ID_IS_REQUIRED = '91613';
const CUSTOMER_ID_IS_TOO_LONG = '91612';
const CUSTOMER_LAST_NAME_IS_TOO_LONG = '81613';
const CUSTOMER_PHONE_IS_TOO_LONG = '81614';
const CUSTOMER_VAULTED_PAYMENT_INSTRUMENT_NONCE_BELONGS_TO_DIFFERENT_CUSTOMER = '91617';
const CUSTOMER_WEBSITE_FORMAT_IS_INVALID = '81616';
const CUSTOMER_WEBSITE_IS_INVALID = '81616';
const CUSTOMER_WEBSITE_IS_TOO_LONG = '81615';
const DESCRIPTOR_NAME_FORMAT_IS_INVALID = '92201';
const DESCRIPTOR_PHONE_FORMAT_IS_INVALID = '92202';
const DESCRIPTOR_INTERNATIONAL_NAME_FORMAT_IS_INVALID = '92204';
const DESCRIPTOR_DYNAMIC_DESCRIPTORS_DISABLED = '92203';
const DESCRIPTOR_INTERNATIONAL_PHONE_FORMAT_IS_INVALID = '92205';
const DESCRIPTOR_URL_FORMAT_IS_INVALID = '92206';
const DISPUTE_CAN_ONLY_ADD_EVIDENCE_TO_OPEN_DISPUTE = '95701';
const DISPUTE_CAN_ONLY_REMOVE_EVIDENCE_FROM_OPEN_DISPUTE = '95702';
const DISPUTE_CAN_ONLY_ADD_EVIDENCE_TO_DISPUTE = '95703';
const DISPUTE_CAN_ONLY_ACCEPT_OPEN_DISPUTE = '95704';
const DISPUTE_CAN_ONLY_FINALIZE_OPEN_DISPUTE = '95705';
const DISPUTE_CAN_ONLY_CREATE_EVIDENCE_WITH_VALID_CATEGORY = '95706';
const DISPUTE_EVIDENCE_CONTENT_DATE_INVALID = '95707';
const DISPUTE_EVIDENCE_CONTENT_TOO_LONG = '95708';
const DISPUTE_EVIDENCE_CONTENT_ARN_TOO_LONG = '95709';
const DISPUTE_EVIDENCE_CONTENT_PHONE_TOO_LONG = '95710';
const DISPUTE_EVIDENCE_CATEGORY_TEXT_ONLY = '95711';
const DISPUTE_EVIDENCE_CATEGORY_DOCUMENT_ONLY = '95712';
const DISPUTE_EVIDENCE_CATEGORY_NOT_FOR_REASON_CODE = '95713';
const DISPUTE_EVIDENCE_CATEGORY_DUPLICATE = '95713';
const DISPUTE_EVIDENCE_CATEGORY_EMAIL_INVALID = '95713';
const DISPUTE_DIGITAL_GOODS_MISSING_EVIDENCE = '95720';
const DISPUTE_DIGITAL_GOODS_MISSING_DOWNLOAD_DATE = '95721';
const DISPUTE_PRIOR_NON_DISPUTED_TRANSACTION_MISSING_ARN = '95722';
const DISPUTE_PRIOR_NON_DISPUTED_TRANSACTION_MISSING_DATE = '95723';
const DISPUTE_RECURRING_TRANSACTION_MISSING_DATE = '95724';
const DISPUTE_RECURRING_TRANSACTION_MISSING_ARN = '95725';
const DISPUTE_VALID_EVIDENCE_REQUIRED_TO_FINALIZE = '95726';
const DOCUMENT_UPLOAD_KIND_IS_INVALID = '84901';
const DOCUMENT_UPLOAD_FILE_IS_TOO_LARGE = '84902';
const DOCUMENT_UPLOAD_FILE_TYPE_IS_INVALID = '84903';
const DOCUMENT_UPLOAD_FILE_IS_MALFORMED_OR_ENCRYPTED = '84904';
const DOCUMENT_UPLOAD_FILE_IS_TOO_LONG = '84905';
const FAILED_AUTH_ADJUSTMENT_ALLOW_RETRY = '95603';
const FAILED_AUTH_ADJUSTMENT_HARD_DECLINE = '95602';
const FINAL_AUTH_SUBMIT_FOR_SETTLEMENT_FOR_DIFFERENT_AMOUNT = '95601';
const INDUSTRY_DATA_LEG_TRAVEL_FLIGHT_ARRIVAL_AIRPORT_CODE_IS_TOO_LONG = '96301';
const INDUSTRY_DATA_LEG_TRAVEL_FLIGHT_ARRIVAL_TIME_FORMAT_IS_INVALID = '96302';
const INDUSTRY_DATA_LEG_TRAVEL_FLIGHT_CARRIER_CODE_IS_TOO_LONG = '96303';
const INDUSTRY_DATA_LEG_TRAVEL_FLIGHT_CONJUNCTION_TICKET_IS_TOO_LONG = '96304';
const INDUSTRY_DATA_LEG_TRAVEL_FLIGHT_COUPON_NUMBER_IS_TOO_LONG = '96305';
const INDUSTRY_DATA_LEG_TRAVEL_FLIGHT_DEPARTURE_AIRPORT_CODE_IS_TOO_LONG = '96306';
const INDUSTRY_DATA_LEG_TRAVEL_FLIGHT_DEPARTURE_TIME_FORMAT_IS_INVALID = '96307';
const INDUSTRY_DATA_LEG_TRAVEL_FLIGHT_EXCHANGE_TICKET_IS_TOO_LONG = '96308';
const INDUSTRY_DATA_LEG_TRAVEL_FLIGHT_FARE_AMOUNT_CANNOT_BE_NEGATIVE = '96309';
const INDUSTRY_DATA_LEG_TRAVEL_FLIGHT_FARE_AMOUNT_FORMAT_IS_INVALID = '96310';
const INDUSTRY_DATA_LEG_TRAVEL_FLIGHT_FARE_AMOUNT_IS_TOO_LARGE = '96311';
const INDUSTRY_DATA_LEG_TRAVEL_FLIGHT_FARE_BASIS_CODE_IS_TOO_LONG = '96312';
const INDUSTRY_DATA_LEG_TRAVEL_FLIGHT_FEE_AMOUNT_CANNOT_BE_NEGATIVE = '96313';
const INDUSTRY_DATA_LEG_TRAVEL_FLIGHT_FEE_AMOUNT_FORMAT_IS_INVALID = '96314';
const INDUSTRY_DATA_LEG_TRAVEL_FLIGHT_FEE_AMOUNT_IS_TOO_LARGE = '96315';
const INDUSTRY_DATA_LEG_TRAVEL_FLIGHT_SERVICE_CLASS_IS_TOO_LONG = '96316';
const INDUSTRY_DATA_LEG_TRAVEL_FLIGHT_TAX_AMOUNT_CANNOT_BE_NEGATIVE = '96317';
const INDUSTRY_DATA_LEG_TRAVEL_FLIGHT_TAX_AMOUNT_FORMAT_IS_INVALID = '96318';
const INDUSTRY_DATA_LEG_TRAVEL_FLIGHT_TAX_AMOUNT_IS_TOO_LARGE = '96319';
const INDUSTRY_DATA_LEG_TRAVEL_FLIGHT_TICKET_NUMBER_IS_TOO_LONG = '96320';
const INDUSTRY_DATA_INDUSTRY_TYPE_IS_INVALID = '93401';
const INDUSTRY_DATA_LODGING_EMPTY_DATA = '93402';
const INDUSTRY_DATA_LODGING_FOLIO_NUMBER_IS_INVALID = '93403';
const INDUSTRY_DATA_LODGING_CHECK_IN_DATE_IS_INVALID = '93404';
const INDUSTRY_DATA_LODGING_CHECK_OUT_DATE_IS_INVALID = '93405';
const INDUSTRY_DATA_LODGING_CHECK_OUT_DATE_MUST_FOLLOW_CHECK_IN_DATE = '93406';
const INDUSTRY_DATA_LODGING_UNKNOWN_DATA_FIELD = '93407';
const INDUSTRY_DATA_TRAVEL_CRUISE_EMPTY_DATA = '93408';
const INDUSTRY_DATA_TRAVEL_CRUISE_UNKNOWN_DATA_FIELD = '93409';
const INDUSTRY_DATA_TRAVEL_CRUISE_TRAVEL_PACKAGE_IS_INVALID = '93410';
const INDUSTRY_DATA_TRAVEL_CRUISE_DEPARTURE_DATE_IS_INVALID = '93411';
const INDUSTRY_DATA_TRAVEL_CRUISE_LODGING_CHECK_IN_DATE_IS_INVALID = '93412';
const INDUSTRY_DATA_TRAVEL_CRUISE_LODGING_CHECK_OUT_DATE_IS_INVALID = '93413';
const INDUSTRY_DATA_TRAVEL_FLIGHT_EMPTY_DATA = '93414';
const INDUSTRY_DATA_TRAVEL_FLIGHT_UNKNOWN_DATA_FIELD = '93415';
const INDUSTRY_DATA_TRAVEL_FLIGHT_CUSTOMER_CODE_IS_TOO_LONG = '93416';
const INDUSTRY_DATA_TRAVEL_FLIGHT_FARE_AMOUNT_CANNOT_BE_NEGATIVE = '93417';
const INDUSTRY_DATA_TRAVEL_FLIGHT_FARE_AMOUNT_FORMAT_IS_INVALID = '93418';
const INDUSTRY_DATA_TRAVEL_FLIGHT_FARE_AMOUNT_IS_TOO_LARGE = '93419';
const INDUSTRY_DATA_TRAVEL_FLIGHT_FEE_AMOUNT_CANNOT_BE_NEGATIVE = '93420';
const INDUSTRY_DATA_TRAVEL_FLIGHT_FEE_AMOUNT_FORMAT_IS_INVALID = '93421';
const INDUSTRY_DATA_TRAVEL_FLIGHT_FEE_AMOUNT_IS_TOO_LARGE = '93422';
const INDUSTRY_DATA_TRAVEL_FLIGHT_ISSUED_DATE_FORMAT_IS_INVALID = '93423';
const INDUSTRY_DATA_TRAVEL_FLIGHT_ISSUING_CARRIER_CODE_IS_TOO_LONG = '93424';
const INDUSTRY_DATA_TRAVEL_FLIGHT_PASSENGER_MIDDLE_INITIAL_IS_TOO_LONG = '93425';
const INDUSTRY_DATA_TRAVEL_FLIGHT_RESTRICTED_TICKET_IS_REQUIRED = '93426';
const INDUSTRY_DATA_TRAVEL_FLIGHT_TAX_AMOUNT_CANNOT_BE_NEGATIVE = '93427';
const INDUSTRY_DATA_TRAVEL_FLIGHT_TAX_AMOUNT_FORMAT_IS_INVALID = '93428';
const INDUSTRY_DATA_TRAVEL_FLIGHT_TAX_AMOUNT_IS_TOO_LARGE = '93429';
const INDUSTRY_DATA_TRAVEL_FLIGHT_TICKET_NUMBER_IS_TOO_LONG = '93430';
const INDUSTRY_DATA_TRAVEL_FLIGHT_LEGS_EXPECTED = '93431';
const INDUSTRY_DATA_TRAVEL_FLIGHT_TOO_MANY_LEGS = '93432';
const TRANSACTION_LINE_ITEM_COMMODITY_CODE_IS_TOO_LONG = '95801';
const TRANSACTION_LINE_ITEM_DESCRIPTION_IS_TOO_LONG = '95803';
const TRANSACTION_LINE_ITEM_DISCOUNT_AMOUNT_FORMAT_IS_INVALID = '95804';
const TRANSACTION_LINE_ITEM_DISCOUNT_AMOUNT_IS_TOO_LARGE = '95805';
const TRANSACTION_LINE_ITEM_DISCOUNT_AMOUNT_MUST_BE_GREATER_THAN_ZERO = '95806'; // Deprecated as the amount may be zero. Use TRANSACTION_LINE_ITEM_DISCOUNT_AMOUNT_CANNOT_BE_ZERO.
const TRANSACTION_LINE_ITEM_DISCOUNT_AMOUNT_CANNOT_BE_NEGATIVE = '95806';
const TRANSACTION_LINE_ITEM_KIND_IS_INVALID = '95807';
const TRANSACTION_LINE_ITEM_KIND_IS_REQUIRED = '95808';
const TRANSACTION_LINE_ITEM_NAME_IS_REQUIRED = '95822';
const TRANSACTION_LINE_ITEM_NAME_IS_TOO_LONG = '95823';
const TRANSACTION_LINE_ITEM_PRODUCT_CODE_IS_TOO_LONG = '95809';
const TRANSACTION_LINE_ITEM_QUANTITY_FORMAT_IS_INVALID = '95810';
const TRANSACTION_LINE_ITEM_QUANTITY_IS_REQUIRED = '95811';
const TRANSACTION_LINE_ITEM_QUANTITY_IS_TOO_LARGE = '95812';
const TRANSACTION_LINE_ITEM_TOTAL_AMOUNT_FORMAT_IS_INVALID = '95813';
const TRANSACTION_LINE_ITEM_TOTAL_AMOUNT_IS_REQUIRED = '95814';
const TRANSACTION_LINE_ITEM_TOTAL_AMOUNT_IS_TOO_LARGE = '95815';
const TRANSACTION_LINE_ITEM_TOTAL_AMOUNT_MUST_BE_GREATER_THAN_ZERO = '95816';
const TRANSACTION_LINE_ITEM_UNIT_AMOUNT_FORMAT_IS_INVALID = '95817';
const TRANSACTION_LINE_ITEM_UNIT_AMOUNT_IS_REQUIRED = '95818';
const TRANSACTION_LINE_ITEM_UNIT_AMOUNT_IS_TOO_LARGE = '95819';
const TRANSACTION_LINE_ITEM_UNIT_AMOUNT_MUST_BE_GREATER_THAN_ZERO = '95820';
const TRANSACTION_LINE_ITEM_UNIT_OF_MEASURE_IS_TOO_LONG = '95821';
const TRANSACTION_LINE_ITEM_UNIT_TAX_AMOUNT_FORMAT_IS_INVALID = '95824';
const TRANSACTION_LINE_ITEM_UNIT_TAX_AMOUNT_IS_TOO_LARGE = '95825';
const TRANSACTION_LINE_ITEM_UNIT_TAX_AMOUNT_MUST_BE_GREATER_THAN_ZERO = '95826'; // Deprecated as the amount may be zero. Use TRANSACTION_LINE_ITEM_UNIT_TAX_AMOUNT_CANNOT_BE_ZERO.
const TRANSACTION_LINE_ITEM_UNIT_TAX_AMOUNT_CANNOT_BE_NEGATIVE = '95826';
const TRANSACTION_LINE_ITEM_TAX_AMOUNT_FORMAT_IS_INVALID = '95827';
const TRANSACTION_LINE_ITEM_TAX_AMOUNT_IS_TOO_LARGE = '95828';
const TRANSACTION_LINE_ITEM_TAX_AMOUNT_CANNOT_BE_NEGATIVE = '95829';
const TRANSACTION_EXTERNAL_VAULT_STATUS_IS_INVALID = '915175';
const TRANSACTION_EXTERNAL_VAULT_STATUS_WITH_PREVIOUS_NETWORK_TRANSACTION_ID_IS_INVALID = '915177';
const TRANSACTION_EXTERNAL_VAULT_CARD_TYPE_IS_INVALID = '915178';
const TRANSACTION_EXTERNAL_VAULT_PREVIOUS_NETWORK_TRANSACTION_ID_IS_INVALID = '915179';
const MERCHANT_COUNTRY_CANNOT_BE_BLANK = '83603';
const MERCHANT_COUNTRY_CODE_ALPHA2_IS_INVALID = '93607';
const MERCHANT_COUNTRY_CODE_ALPHA2_IS_NOT_ACCEPTED = '93606';
const MERCHANT_COUNTRY_CODE_ALPHA3_IS_INVALID = '93605';
const MERCHANT_COUNTRY_CODE_ALPHA3_IS_NOT_ACCEPTED = '93604';
const MERCHANT_COUNTRY_CODE_NUMERIC_IS_INVALID = '93609';
const MERCHANT_COUNTRY_CODE_NUMERIC_IS_NOT_ACCEPTED = '93608';
const MERCHANT_COUNTRY_NAME_IS_INVALID = '93611';
const MERCHANT_COUNTRY_NAME_IS_NOT_ACCEPTED = '93610';
const MERCHANT_CURRENCIES_ARE_INVALID = '93614';
const MERCHANT_EMAIL_FORMAT_IS_INVALID = '93602';
const MERCHANT_EMAIL_IS_REQUIRED = '83601';
const MERCHANT_INCONSISTENT_COUNTRY = '93612';
const MERCHANT_ACCOUNT_PAYMENT_METHODS_ARE_INVALID = '93613';
const MERCHANT_PAYMENT_METHODS_ARE_NOT_ALLOWED = '93615';
const MERCHANT_MERCHANT_ACCOUNT_EXISTS_FOR_CURRENCY = '93616';
const MERCHANT_CURRENCY_IS_REQUIRED = '93617';
const MERCHANT_CURRENCY_IS_INVALID = '93618';
const MERCHANT_NO_MERCHANT_ACCOUNTS = '93619';
const MERCHANT_MERCHANT_ACCOUNT_EXISTS_FOR_ID = '93620';
const MERCHANT_MERCHANT_ACCOUNT_NOT_AUTH_ONBOARDED = '93621';
const MERCHANT_ACCOUNT_ID_FORMAT_IS_INVALID = '82603';
const MERCHANT_ACCOUNT_ID_IS_IN_USE = '82604';
const MERCHANT_ACCOUNT_ID_IS_NOT_ALLOWED = '82605';
const MERCHANT_ACCOUNT_ID_IS_TOO_LONG = '82602';
const MERCHANT_ACCOUNT_MASTER_MERCHANT_ACCOUNT_ID_IS_INVALID = '82607';
const MERCHANT_ACCOUNT_MASTER_MERCHANT_ACCOUNT_ID_IS_REQUIRED = '82606';
const MERCHANT_ACCOUNT_MASTER_MERCHANT_ACCOUNT_MUST_BE_ACTIVE = '82608';
const MERCHANT_ACCOUNT_TOS_ACCEPTED_IS_REQUIRED = '82610';
const MERCHANT_ACCOUNT_CANNOT_BE_UPDATED = '82674';
const MERCHANT_ACCOUNT_DECLINED = '82626';
const MERCHANT_ACCOUNT_DECLINED_MASTER_CARD_MATCH = '82622';
const MERCHANT_ACCOUNT_DECLINED_OFAC = '82621';
const MERCHANT_ACCOUNT_DECLINED_FAILED_KYC = '82623';
const MERCHANT_ACCOUNT_DECLINED_SSN_INVALID = '82624';
const MERCHANT_ACCOUNT_DECLINED_SSN_MATCHES_DECEASED = '82625';
const MERCHANT_ACCOUNT_ID_CANNOT_BE_UPDATED = '82675';
const MERCHANT_ACCOUNT_MASTER_MERCHANT_ACCOUNT_ID_CANNOT_BE_UPDATED = '82676';
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_ACCOUNT_NUMBER_IS_REQUIRED = '82614';
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_COMPANY_NAME_IS_INVALID = '82631';
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_COMPANY_NAME_IS_REQUIRED_WITH_TAX_ID = '82633';
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_DATE_OF_BIRTH_IS_REQUIRED = '82612';
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_DECLINED = '82626'; // Keep for backwards compatibility
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_DECLINED_MASTER_CARD_MATCH = '82622'; // Keep for backwards compatibility
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_DECLINED_OFAC = '82621'; // Keep for backwards compatibility
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_DECLINED_FAILED_KYC = '82623'; // Keep for backwards compatibility
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_DECLINED_SSN_INVALID = '82624'; // Keep for backwards compatibility
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_DECLINED_SSN_MATCHES_DECEASED = '82625'; // Keep for backwards compatibility
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_EMAIL_ADDRESS_IS_INVALID = '82616';
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_FIRST_NAME_IS_INVALID = '82627';
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_FIRST_NAME_IS_REQUIRED = '82609';
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_LAST_NAME_IS_INVALID = '82628';
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_LAST_NAME_IS_REQUIRED = '82611';
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_PHONE_IS_INVALID = '82636';
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_ROUTING_NUMBER_IS_INVALID = '82635';
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_ROUTING_NUMBER_IS_REQUIRED = '82613';
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_SSN_IS_INVALID = '82615';
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_TAX_ID_IS_INVALID = '82632';
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_TAX_ID_IS_REQUIRED_WITH_COMPANY_NAME = '82634';
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_DATE_OF_BIRTH_IS_INVALID = '82663';
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_ADDRESS_REGION_IS_INVALID = '82664';
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_EMAIL_ADDRESS_IS_REQUIRED = '82665';
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_ACCOUNT_NUMBER_IS_INVALID = '82670';
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_TAX_ID_MUST_BE_BLANK = '82673';
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_ADDRESS_LOCALITY_IS_REQUIRED = '82618';
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_ADDRESS_POSTAL_CODE_IS_INVALID = '82630';
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_ADDRESS_POSTAL_CODE_IS_REQUIRED = '82619';
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_ADDRESS_REGION_IS_REQUIRED = '82620';
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_ADDRESS_STREET_ADDRESS_IS_INVALID = '82629';
const MERCHANT_ACCOUNT_APPLICANT_DETAILS_ADDRESS_STREET_ADDRESS_IS_REQUIRED = '82617';
const MERCHANT_ACCOUNT_BUSINESS_DBA_NAME_IS_INVALID = '82646';
const MERCHANT_ACCOUNT_BUSINESS_TAX_ID_IS_INVALID = '82647';
const MERCHANT_ACCOUNT_BUSINESS_TAX_ID_IS_REQUIRED_WITH_LEGAL_NAME = '82648';
const MERCHANT_ACCOUNT_BUSINESS_LEGAL_NAME_IS_REQUIRED_WITH_TAX_ID = '82669';
const MERCHANT_ACCOUNT_BUSINESS_TAX_ID_MUST_BE_BLANK = '82672';
const MERCHANT_ACCOUNT_BUSINESS_LEGAL_NAME_IS_INVALID = '82677';
const MERCHANT_ACCOUNT_BUSINESS_ADDRESS_REGION_IS_INVALID = '82684';
const MERCHANT_ACCOUNT_BUSINESS_ADDRESS_STREET_ADDRESS_IS_INVALID = '82685';
const MERCHANT_ACCOUNT_BUSINESS_ADDRESS_POSTAL_CODE_IS_INVALID = '82686';
const MERCHANT_ACCOUNT_INDIVIDUAL_FIRST_NAME_IS_REQUIRED = '82637';
const MERCHANT_ACCOUNT_INDIVIDUAL_LAST_NAME_IS_REQUIRED = '82638';
const MERCHANT_ACCOUNT_INDIVIDUAL_DATE_OF_BIRTH_IS_REQUIRED = '82639';
const MERCHANT_ACCOUNT_INDIVIDUAL_SSN_IS_INVALID = '82642';
const MERCHANT_ACCOUNT_INDIVIDUAL_EMAIL_IS_INVALID = '82643';
const MERCHANT_ACCOUNT_INDIVIDUAL_FIRST_NAME_IS_INVALID = '82644';
const MERCHANT_ACCOUNT_INDIVIDUAL_LAST_NAME_IS_INVALID = '82645';
const MERCHANT_ACCOUNT_INDIVIDUAL_PHONE_IS_INVALID = '82656';
const MERCHANT_ACCOUNT_INDIVIDUAL_DATE_OF_BIRTH_IS_INVALID = '82666';
const MERCHANT_ACCOUNT_INDIVIDUAL_EMAIL_IS_REQUIRED = '82667';
const MERCHANT_ACCOUNT_INDIVIDUAL_ADDRESS_STREET_ADDRESS_IS_REQUIRED = '82657';
const MERCHANT_ACCOUNT_INDIVIDUAL_ADDRESS_LOCALITY_IS_REQUIRED = '82658';
const MERCHANT_ACCOUNT_INDIVIDUAL_ADDRESS_POSTAL_CODE_IS_REQUIRED = '82659';
const MERCHANT_ACCOUNT_INDIVIDUAL_ADDRESS_REGION_IS_REQUIRED = '82660';
const MERCHANT_ACCOUNT_INDIVIDUAL_ADDRESS_STREET_ADDRESS_IS_INVALID = '82661';
const MERCHANT_ACCOUNT_INDIVIDUAL_ADDRESS_POSTAL_CODE_IS_INVALID = '82662';
const MERCHANT_ACCOUNT_INDIVIDUAL_ADDRESS_REGION_IS_INVALID = '82668';
const MERCHANT_ACCOUNT_FUNDING_ROUTING_NUMBER_IS_REQUIRED = '82640';
const MERCHANT_ACCOUNT_FUNDING_ACCOUNT_NUMBER_IS_REQUIRED = '82641';
const MERCHANT_ACCOUNT_FUNDING_ROUTING_NUMBER_IS_INVALID = '82649';
const MERCHANT_ACCOUNT_FUNDING_ACCOUNT_NUMBER_IS_INVALID = '82671';
const MERCHANT_ACCOUNT_FUNDING_DESTINATION_IS_REQUIRED = '82678';
const MERCHANT_ACCOUNT_FUNDING_DESTINATION_IS_INVALID = '82679';
const MERCHANT_ACCOUNT_FUNDING_EMAIL_IS_REQUIRED = '82680';
const MERCHANT_ACCOUNT_FUNDING_EMAIL_IS_INVALID = '82681';
const MERCHANT_ACCOUNT_FUNDING_MOBILE_PHONE_IS_REQUIRED = '82682';
const MERCHANT_ACCOUNT_FUNDING_MOBILE_PHONE_IS_INVALID = '82683';
const OAUTH_INVALID_GRANT = '93801';
const OAUTH_INVALID_CREDENTIALS = '93802';
const OAUTH_INVALID_SCOPE = '93803';
const OAUTH_INVALID_REQUEST = '93804';
const OAUTH_UNSUPPORTED_GRANT_TYPE = '93805';
const PAYMENT_METHOD_CANNOT_FORWARD_PAYMENT_METHOD_TYPE = '93106';
const PAYMENT_METHOD_CUSTOMER_ID_IS_INVALID = '93105';
const PAYMENT_METHOD_CUSTOMER_ID_IS_REQUIRED = '93104';
const PAYMENT_METHOD_NONCE_IS_INVALID = '93102';
const PAYMENT_METHOD_NONCE_IS_REQUIRED = '93103';
const PAYMENT_METHOD_PAYMENT_METHOD_NONCE_CONSUMED = '93107';
const PAYMENT_METHOD_PAYMENT_METHOD_NONCE_UNKNOWN = '93108';
const PAYMENT_METHOD_PAYMENT_METHOD_NONCE_LOCKED = '93109';
const PAYMENT_METHOD_PAYMENT_METHOD_PARAMS_ARE_REQUIRED = '93101';
const PAYMENT_METHOD_NO_LONGER_SUPPORTED = '93117';
const PAYMENT_METHOD_OPTIONS_US_BANK_ACCOUNT_VERIFICATION_METHOD_IS_INVALID = '93121';
const PAYPAL_ACCOUNT_AUTH_EXPIRED = '92911';
const PAYPAL_ACCOUNT_CANNOT_HAVE_BOTH_ACCESS_TOKEN_AND_CONSENT_CODE = '82903';
const PAYPAL_ACCOUNT_CANNOT_HAVE_FUNDING_SOURCE_WITHOUT_ACCESS_TOKEN = '92912';
const PAYPAL_ACCOUNT_CANNOT_UPDATE_PAYPAL_ACCOUNT_USING_PAYMENT_METHOD_NONCE = '92914';
const PAYPAL_ACCOUNT_CANNOT_VAULT_ONE_TIME_USE_PAYPAL_ACCOUNT = '82902';
const PAYPAL_ACCOUNT_CONSENT_CODE_OR_ACCESS_TOKEN_IS_REQUIRED = '82901';
const PAYPAL_ACCOUNT_CUSTOMER_ID_IS_REQUIRED_FOR_VAULTING = '82905';
const PAYPAL_ACCOUNT_INVALID_FUNDING_SOURCE_SELECTION = '92913';
const PAYPAL_ACCOUNT_INVALID_PARAMS_FOR_PAYPAL_ACCOUNT_UPDATE = '92915';
const PAYPAL_ACCOUNT_PAYMENT_METHOD_NONCE_CONSUMED = '92907';
const PAYPAL_ACCOUNT_PAYMENT_METHOD_NONCE_LOCKED = '92909';
const PAYPAL_ACCOUNT_PAYMENT_METHOD_NONCE_UNKNOWN = '92908';
const PAYPAL_ACCOUNT_PAYPAL_ACCOUNTS_ARE_NOT_ACCEPTED = '82904';
const PAYPAL_ACCOUNT_PAYPAL_COMMUNICATION_ERROR = '92910';
const PAYPAL_ACCOUNT_TOKEN_IS_IN_USE = '92906';
const SEPA_BANK_ACCOUNT_ACCOUNT_HOLDER_NAME_IS_REQUIRED = '93003';
const SEPA_BANK_ACCOUNT_BIC_IS_REQUIRED = '93002';
const SEPA_BANK_ACCOUNT_IBAN_IS_REQUIRED = '93001';
const SEPA_MANDATE_ACCOUNT_HOLDER_NAME_IS_REQUIRED = '83301';
const SEPA_MANDATE_BIC_INVALID_CHARACTER = '83306';
const SEPA_MANDATE_BIC_IS_REQUIRED = '83302';
const SEPA_MANDATE_BIC_LENGTH_IS_INVALID = '83307';
const SEPA_MANDATE_BIC_UNSUPPORTED_COUNTRY = '83308';
const SEPA_MANDATE_BILLING_ADDRESS_CONFLICT = '93311';
const SEPA_MANDATE_BILLING_ADDRESS_ID_IS_INVALID = '93312';
const SEPA_MANDATE_IBAN_INVALID_CHARACTER = '83305';
const SEPA_MANDATE_IBAN_INVALID_FORMAT = '83310';
const SEPA_MANDATE_IBAN_IS_REQUIRED = '83303';
const SEPA_MANDATE_IBAN_UNSUPPORTED_COUNTRY = '83309';
const SEPA_MANDATE_TYPE_IS_REQUIRED = '93304';
const SEPA_MANDATE_TYPE_IS_INVALID = '93313';
const SETTLEMENT_BATCH_SUMMARY_SETTLEMENT_DATE_IS_INVALID = '82302';
const SETTLEMENT_BATCH_SUMMARY_SETTLEMENT_DATE_IS_REQUIRED = '82301';
const SETTLEMENT_BATCH_SUMMARY_CUSTOM_FIELD_IS_INVALID = '82303';
const SUBSCRIPTION_BILLING_DAY_OF_MONTH_CANNOT_BE_UPDATED = '91918';
const SUBSCRIPTION_BILLING_DAY_OF_MONTH_IS_INVALID = '91914';
const SUBSCRIPTION_BILLING_DAY_OF_MONTH_MUST_BE_NUMERIC = '91913';
const SUBSCRIPTION_CANNOT_ADD_DUPLICATE_ADDON_OR_DISCOUNT = '91911';
const SUBSCRIPTION_CANNOT_EDIT_CANCELED_SUBSCRIPTION = '81901';
const SUBSCRIPTION_CANNOT_EDIT_EXPIRED_SUBSCRIPTION = '81910';
const SUBSCRIPTION_CANNOT_EDIT_PRICE_CHANGING_FIELDS_ON_PAST_DUE_SUBSCRIPTION = '91920';
const SUBSCRIPTION_FIRST_BILLING_DATE_CANNOT_BE_IN_THE_PAST = '91916';
const SUBSCRIPTION_FIRST_BILLING_DATE_CANNOT_BE_UPDATED = '91919';
const SUBSCRIPTION_FIRST_BILLING_DATE_IS_INVALID = '91915';
const SUBSCRIPTION_ID_IS_IN_USE = '81902';
const SUBSCRIPTION_INCONSISTENT_NUMBER_OF_BILLING_CYCLES = '91908';
const SUBSCRIPTION_INCONSISTENT_START_DATE = '91917';
const SUBSCRIPTION_INVALID_REQUEST_FORMAT = '91921';
const SUBSCRIPTION_MERCHANT_ACCOUNT_ID_IS_INVALID = '91901';
const SUBSCRIPTION_MISMATCH_CURRENCY_ISO_CODE = '91923';
const SUBSCRIPTION_NUMBER_OF_BILLING_CYCLES_CANNOT_BE_BLANK = '91912';
const SUBSCRIPTION_NUMBER_OF_BILLING_CYCLES_IS_TOO_SMALL = '91909';
const SUBSCRIPTION_NUMBER_OF_BILLING_CYCLES_MUST_BE_GREATER_THAN_ZERO = '91907';
const SUBSCRIPTION_NUMBER_OF_BILLING_CYCLES_MUST_BE_NUMERIC = '91906';
const SUBSCRIPTION_PAYMENT_METHOD_NONCE_CARD_TYPE_IS_NOT_ACCEPTED = '91924';
const SUBSCRIPTION_PAYMENT_METHOD_NONCE_IS_INVALID = '91925';
const SUBSCRIPTION_PAYMENT_METHOD_NONCE_NOT_ASSOCIATED_WITH_CUSTOMER = '91926';
const SUBSCRIPTION_PAYMENT_METHOD_NONCE_UNVAULTED_CARD_IS_NOT_ACCEPTED = '91927';
const SUBSCRIPTION_PAYMENT_METHOD_TOKEN_CARD_TYPE_IS_NOT_ACCEPTED = '91902';
const SUBSCRIPTION_PAYMENT_METHOD_TOKEN_IS_INVALID = '91903';
const SUBSCRIPTION_PAYMENT_METHOD_TOKEN_NOT_ASSOCIATED_WITH_CUSTOMER = '91905';
const SUBSCRIPTION_PLAN_BILLING_FREQUENCY_CANNOT_BE_UPDATED = '91922';
const SUBSCRIPTION_PLAN_ID_IS_INVALID = '91904';
const SUBSCRIPTION_PRICE_CANNOT_BE_BLANK = '81903';
const SUBSCRIPTION_PRICE_FORMAT_IS_INVALID = '81904';
const SUBSCRIPTION_PRICE_IS_TOO_LARGE = '81923';
const SUBSCRIPTION_STATUS_IS_CANCELED = '81905';
const SUBSCRIPTION_TOKEN_FORMAT_IS_INVALID = '81906';
const SUBSCRIPTION_TRIAL_DURATION_FORMAT_IS_INVALID = '81907';
const SUBSCRIPTION_TRIAL_DURATION_IS_REQUIRED = '81908';
const SUBSCRIPTION_TRIAL_DURATION_UNIT_IS_INVALID = '81909';
const SUBSCRIPTION_MERCHANT_ACCOUNT_DOES_NOT_SUPPORT_INSTRUMENT_TYPE = '91930';
const SUBSCRIPTION_PAYMENT_METHOD_NONCE_INSTRUMENT_TYPE_DOES_NOT_SUPPORT_SUBSCRIPTIONS = '91929';
const SUBSCRIPTION_PAYMENT_METHOD_TOKEN_INSTRUMENT_TYPE_DOES_NOT_SUPPORT_SUBSCRIPTIONS = '91928';
const SUBSCRIPTION_MODIFICATION_AMOUNT_CANNOT_BE_BLANK = '92003';
const SUBSCRIPTION_MODIFICATION_AMOUNT_IS_INVALID = '92002';
const SUBSCRIPTION_MODIFICATION_AMOUNT_IS_TOO_LARGE = '92023';
const SUBSCRIPTION_MODIFICATION_CANNOT_EDIT_MODIFICATIONS_ON_PAST_DUE_SUBSCRIPTION = '92022';
const SUBSCRIPTION_MODIFICATION_CANNOT_UPDATE_AND_REMOVE = '92015';
const SUBSCRIPTION_MODIFICATION_EXISTING_ID_IS_INCORRECT_KIND = '92020';
const SUBSCRIPTION_MODIFICATION_EXISTING_ID_IS_INVALID = '92011';
const SUBSCRIPTION_MODIFICATION_EXISTING_ID_IS_REQUIRED = '92012';
const SUBSCRIPTION_MODIFICATION_ID_TO_REMOVE_IS_INCORRECT_KIND = '92021';
const SUBSCRIPTION_MODIFICATION_ID_TO_REMOVE_IS_INVALID = '92025';
const SUBSCRIPTION_MODIFICATION_ID_TO_REMOVE_IS_NOT_PRESENT = '92016';
const SUBSCRIPTION_MODIFICATION_INCONSISTENT_NUMBER_OF_BILLING_CYCLES = '92018';
const SUBSCRIPTION_MODIFICATION_INHERITED_FROM_ID_IS_INVALID = '92013';
const SUBSCRIPTION_MODIFICATION_INHERITED_FROM_ID_IS_REQUIRED = '92014';
const SUBSCRIPTION_MODIFICATION_MISSING = '92024';
const SUBSCRIPTION_MODIFICATION_NUMBER_OF_BILLING_CYCLES_CANNOT_BE_BLANK = '92017';
const SUBSCRIPTION_MODIFICATION_NUMBER_OF_BILLING_CYCLES_IS_INVALID = '92005';
const SUBSCRIPTION_MODIFICATION_NUMBER_OF_BILLING_CYCLES_MUST_BE_GREATER_THAN_ZERO = '92019';
const SUBSCRIPTION_MODIFICATION_QUANTITY_CANNOT_BE_BLANK = '92004';
const SUBSCRIPTION_MODIFICATION_QUANTITY_IS_INVALID = '92001';
const SUBSCRIPTION_MODIFICATION_QUANTITY_MUST_BE_GREATER_THAN_ZERO = '92010';
const TRANSACTION_AMOUNT_CANNOT_BE_NEGATIVE = '81501';
const TRANSACTION_AMOUNT_DOES_NOT_MATCH3_D_SECURE_AMOUNT = '91585';
const TRANSACTION_AMOUNT_DOES_NOT_MATCH_IDEAL_PAYMENT_AMOUNT = '915144';
const TRANSACTION_AMOUNT_FORMAT_IS_INVALID = '81503';
const TRANSACTION_AMOUNT_IS_INVALID = '81503';
const TRANSACTION_AMOUNT_IS_REQUIRED = '81502';
const TRANSACTION_AMOUNT_IS_TOO_LARGE = '81528';
const TRANSACTION_AMOUNT_MUST_BE_GREATER_THAN_ZERO = '81531';
const TRANSACTION_BILLING_ADDRESS_CONFLICT = '91530';
const TRANSACTION_CANNOT_BE_VOIDED = '91504';
const TRANSACTION_CANNOT_CANCEL_RELEASE = '91562';
const TRANSACTION_CANNOT_CLONE_CREDIT = '91543';
const TRANSACTION_CANNOT_CLONE_MARKETPLACE_TRANSACTION = '915137';
const TRANSACTION_CANNOT_CLONE_TRANSACTION_WITH_PAYPAL_ACCOUNT = '91573';
const TRANSACTION_CANNOT_CLONE_TRANSACTION_WITH_VAULT_CREDIT_CARD = '91540';
const TRANSACTION_CANNOT_CLONE_UNSUCCESSFUL_TRANSACTION = '91542';
const TRANSACTION_CANNOT_CLONE_VOICE_AUTHORIZATIONS = '91541';
const TRANSACTION_CANNOT_HOLD_IN_ESCROW = '91560';
const TRANSACTION_CANNOT_PARTIALLY_REFUND_ESCROWED_TRANSACTION = '91563';
const TRANSACTION_CANNOT_REFUND_CREDIT = '91505';
const TRANSACTION_CANNOT_REFUND_SETTLING_TRANSACTION = '91574';
const TRANSACTION_CANNOT_REFUND_UNLESS_SETTLED = '91506';
const TRANSACTION_CANNOT_REFUND_WITH_PENDING_MERCHANT_ACCOUNT = '91559';
const TRANSACTION_CANNOT_REFUND_WITH_SUSPENDED_MERCHANT_ACCOUNT = '91538';
const TRANSACTION_CANNOT_RELEASE_FROM_ESCROW = '91561';
const TRANSACTION_CANNOT_SIMULATE_SETTLEMENT = '91575';
const TRANSACTION_CANNOT_SUBMIT_FOR_PARTIAL_SETTLEMENT = '915103';
const TRANSACTION_CANNOT_SUBMIT_FOR_SETTLEMENT = '91507';
const TRANSACTION_CANNOT_UPDATE_DETAILS_NOT_SUBMITTED_FOR_SETTLEMENT = '915129';
const TRANSACTION_CHANNEL_IS_TOO_LONG = '91550';
const TRANSACTION_CREDIT_CARD_IS_REQUIRED = '91508';
const TRANSACTION_CUSTOMER_DEFAULT_PAYMENT_METHOD_CARD_TYPE_IS_NOT_ACCEPTED = '81509';
const TRANSACTION_CUSTOMER_DOES_NOT_HAVE_CREDIT_CARD = '91511';
const TRANSACTION_CUSTOMER_ID_IS_INVALID = '91510';
const TRANSACTION_CUSTOM_FIELD_IS_INVALID = '91526';
const TRANSACTION_CUSTOM_FIELD_IS_TOO_LONG = '81527';
const TRANSACTION_PAYMENT_INSTRUMENT_WITH_EXTERNAL_VAULT_IS_INVALID = '915176';
const TRANSACTION_HAS_ALREADY_BEEN_REFUNDED = '91512';
const TRANSACTION_IDEAL_PAYMENT_NOT_COMPLETE = '815141';
const TRANSACTION_IDEAL_PAYMENTS_CANNOT_BE_VAULTED = '915150';
const TRANSACTION_LINE_ITEMS_EXPECTED = '915158';
const TRANSACTION_TOO_MANY_LINE_ITEMS = '915157';
const TRANSACTION_DISCOUNT_AMOUNT_FORMAT_IS_INVALID = '915159';
const TRANSACTION_DISCOUNT_AMOUNT_CANNOT_BE_NEGATIVE = '915160';
const TRANSACTION_DISCOUNT_AMOUNT_IS_TOO_LARGE = '915161';
const TRANSACTION_SHIPPING_AMOUNT_FORMAT_IS_INVALID = '915162';
const TRANSACTION_SHIPPING_AMOUNT_CANNOT_BE_NEGATIVE = '915163';
const TRANSACTION_SHIPPING_AMOUNT_IS_TOO_LARGE = '915164';
const TRANSACTION_SHIPS_FROM_POSTAL_CODE_IS_TOO_LONG = '915165';
const TRANSACTION_SHIPS_FROM_POSTAL_CODE_IS_INVALID = '915166';
const TRANSACTION_SHIPS_FROM_POSTAL_CODE_INVALID_CHARACTERS = '915167';
const TRANSACTION_MERCHANT_ACCOUNT_DOES_NOT_MATCH3_D_SECURE_MERCHANT_ACCOUNT = '91584';
const TRANSACTION_MERCHANT_ACCOUNT_DOES_NOT_MATCH_IDEAL_PAYMENT_MERCHANT_ACCOUNT = '915143';
const TRANSACTION_MERCHANT_ACCOUNT_DOES_NOT_SUPPORT_MOTO = '91558';
const TRANSACTION_MERCHANT_ACCOUNT_DOES_NOT_SUPPORT_REFUNDS = '91547';
const TRANSACTION_MERCHANT_ACCOUNT_ID_DOES_NOT_MATCH_SUBSCRIPTION = '915180';
const TRANSACTION_MERCHANT_ACCOUNT_ID_IS_INVALID = '91513';
const TRANSACTION_MERCHANT_ACCOUNT_IS_SUSPENDED = '91514';
const TRANSACTION_MERCHANT_ACCOUNT_NAME_IS_INVALID = '91513'; //Deprecated
const TRANSACTION_OPTIONS_PAY_PAL_CUSTOM_FIELD_TOO_LONG = '91580';
const TRANSACTION_OPTIONS_SUBMIT_FOR_SETTLEMENT_IS_REQUIRED_FOR_CLONING = '91544';
const TRANSACTION_OPTIONS_SUBMIT_FOR_SETTLEMENT_IS_REQUIRED_FOR_PAYPAL_UNILATERAL = '91582';
const TRANSACTION_OPTIONS_USE_BILLING_FOR_SHIPPING_DISABLED = '91572';
const TRANSACTION_OPTIONS_VAULT_IS_DISABLED = '91525';
const TRANSACTION_ORDER_ID_DOES_NOT_MATCH_IDEAL_PAYMENT_ORDER_ID = '91503';
const TRANSACTION_ORDER_ID_IS_REQUIRED_WITH_IDEAL_PAYMENT = '91502';
const TRANSACTION_ORDER_ID_IS_TOO_LONG = '91501';
const TRANSACTION_PAYMENT_INSTRUMENT_NOT_SUPPORTED_BY_MERCHANT_ACCOUNT = '91577';
const TRANSACTION_PAYMENT_INSTRUMENT_TYPE_IS_NOT_ACCEPTED = '915101';
const TRANSACTION_PAYMENT_METHOD_CONFLICT = '91515';
const TRANSACTION_PAYMENT_METHOD_CONFLICT_WITH_VENMO_SDK = '91549';
const TRANSACTION_PAYMENT_METHOD_DOES_NOT_BELONG_TO_CUSTOMER = '91516';
const TRANSACTION_PAYMENT_METHOD_DOES_NOT_BELONG_TO_SUBSCRIPTION = '91527';
const TRANSACTION_PAYMENT_METHOD_NONCE_CARD_TYPE_IS_NOT_ACCEPTED = '91567';
const TRANSACTION_PAYMENT_METHOD_NONCE_CONSUMED = '91564';
const TRANSACTION_PAYMENT_METHOD_NONCE_HAS_NO_VALID_PAYMENT_INSTRUMENT_TYPE = '91569';
const TRANSACTION_PAYMENT_METHOD_NONCE_LOCKED = '91566';
const TRANSACTION_PAYMENT_METHOD_NONCE_UNKNOWN = '91565';
const TRANSACTION_PAYMENT_METHOD_TOKEN_CARD_TYPE_IS_NOT_ACCEPTED = '91517';
const TRANSACTION_PAYMENT_METHOD_TOKEN_IS_INVALID = '91518';
const TRANSACTION_PAYPAL_NOT_ENABLED = '91576';
const TRANSACTION_PAY_PAL_AUTH_EXPIRED = '91579';
const TRANSACTION_PAY_PAL_VAULT_RECORD_MISSING_DATA = '91583';
const TRANSACTION_PROCESSOR_AUTHORIZATION_CODE_CANNOT_BE_SET = '91519';
const TRANSACTION_PROCESSOR_AUTHORIZATION_CODE_IS_INVALID = '81520';
const TRANSACTION_PROCESSOR_DOES_NOT_SUPPORT_AUTHS = '915104';
const TRANSACTION_PROCESSOR_DOES_NOT_SUPPORT_CREDITS = '91546';
const TRANSACTION_PROCESSOR_DOES_NOT_SUPPORT_PARTIAL_SETTLEMENT = '915102';
const TRANSACTION_PROCESSOR_DOES_NOT_SUPPORT_UPDATING_ORDER_ID = '915107';
const TRANSACTION_PROCESSOR_DOES_NOT_SUPPORT_UPDATING_DESCRIPTOR = '915108';
const TRANSACTION_PROCESSOR_DOES_NOT_SUPPORT_UPDATING_DETAILS = '915130';
const TRANSACTION_PROCESSOR_DOES_NOT_SUPPORT_VOICE_AUTHORIZATIONS = '91545';
const TRANSACTION_PURCHASE_ORDER_NUMBER_IS_INVALID = '91548';
const TRANSACTION_PURCHASE_ORDER_NUMBER_IS_TOO_LONG = '91537';
const TRANSACTION_REFUND_AMOUNT_IS_TOO_LARGE = '91521';
const TRANSACTION_SERVICE_FEE_AMOUNT_CANNOT_BE_NEGATIVE = '91554';
const TRANSACTION_SERVICE_FEE_AMOUNT_FORMAT_IS_INVALID = '91555';
const TRANSACTION_SERVICE_FEE_AMOUNT_IS_TOO_LARGE = '91556';
const TRANSACTION_SERVICE_FEE_AMOUNT_NOT_ALLOWED_ON_MASTER_MERCHANT_ACCOUNT = '91557';
const TRANSACTION_SERVICE_FEE_IS_NOT_ALLOWED_ON_CREDITS = '91552';
const TRANSACTION_SERVICE_FEE_NOT_ACCEPTED_FOR_PAYPAL = '91578';
const TRANSACTION_SETTLEMENT_AMOUNT_IS_LESS_THAN_SERVICE_FEE_AMOUNT = '91551';
const TRANSACTION_SETTLEMENT_AMOUNT_IS_TOO_LARGE = '91522';
const TRANSACTION_SHIPPING_ADDRESS_DOESNT_MATCH_CUSTOMER = '91581';
const TRANSACTION_SUBSCRIPTION_DOES_NOT_BELONG_TO_CUSTOMER = '91529';
const TRANSACTION_SUBSCRIPTION_ID_IS_INVALID = '91528';
const TRANSACTION_SUBSCRIPTION_STATUS_MUST_BE_PAST_DUE = '91531';
const TRANSACTION_SUB_MERCHANT_ACCOUNT_REQUIRES_SERVICE_FEE_AMOUNT = '91553';
const TRANSACTION_TAX_AMOUNT_CANNOT_BE_NEGATIVE = '81534';
const TRANSACTION_TAX_AMOUNT_FORMAT_IS_INVALID = '81535';
const TRANSACTION_TAX_AMOUNT_IS_TOO_LARGE = '81536';
const TRANSACTION_THREE_D_SECURE_AUTHENTICATION_FAILED = '81571';
const TRANSACTION_THREE_D_SECURE_TOKEN_IS_INVALID = '91568';
const TRANSACTION_THREE_D_SECURE_TRANSACTION_DATA_DOESNT_MATCH_VERIFY = '91570';
const TRANSACTION_THREE_D_SECURE_ECI_FLAG_IS_REQUIRED = '915113';
const TRANSACTION_THREE_D_SECURE_CAVV_IS_REQUIRED = '915116';
const TRANSACTION_THREE_D_SECURE_XID_IS_REQUIRED = '915115';
const TRANSACTION_THREE_D_SECURE_ECI_FLAG_IS_INVALID = '915114';
const TRANSACTION_THREE_D_SECURE_MERCHANT_ACCOUNT_DOES_NOT_SUPPORT_CARD_TYPE = '915131';
const TRANSACTION_TYPE_IS_INVALID = '91523';
const TRANSACTION_TYPE_IS_REQUIRED = '91524';
const TRANSACTION_UNSUPPORTED_VOICE_AUTHORIZATION = '91539';
const TRANSACTION_US_BANK_ACCOUNT_NONCE_MUST_BE_PLAID_VERIFIED = '915171';
const TRANSACTION_US_BANK_ACCOUNT_NOT_VERIFIED = '915172';
const TRANSACTION_TRANSACTION_SOURCE_IS_INVALID = '915133';
const US_BANK_ACCOUNT_VERIFICATION_NOT_CONFIRMABLE = '96101';
const US_BANK_ACCOUNT_VERIFICATION_MUST_BE_MICRO_TRANSFERS_VERIFICATION = '96102';
const US_BANK_ACCOUNT_VERIFICATION_AMOUNTS_DO_NOT_MATCH = '96103';
const US_BANK_ACCOUNT_VERIFICATION_TOO_MANY_CONFIRMATION_ATTEMPTS = '96104';
const US_BANK_ACCOUNT_VERIFICATION_UNABLE_TO_CONFIRM_DEPOSIT_AMOUNTS = '96105';
const US_BANK_ACCOUNT_VERIFICATION_INVALID_DEPOSIT_AMOUNTS = '96106';
const VERIFICATION_OPTIONS_AMOUNT_CANNOT_BE_NEGATIVE = '94201';
const VERIFICATION_OPTIONS_AMOUNT_FORMAT_IS_INVALID = '94202';
const VERIFICATION_OPTIONS_AMOUNT_IS_TOO_LARGE = '94207';
const VERIFICATION_OPTIONS_AMOUNT_NOT_SUPPORTED_BY_PROCESSOR = '94203';
const VERIFICATION_OPTIONS_MERCHANT_ACCOUNT_ID_IS_INVALID = '94204';
const VERIFICATION_OPTIONS_MERCHANT_ACCOUNT_IS_SUSPENDED = '94205';
const VERIFICATION_OPTIONS_MERCHANT_ACCOUNT_IS_FORBIDDEN = '94206';
const VERIFICATION_OPTIONS_MERCHANT_ACCOUNT_CANNOT_BE_SUB_MERCHANT_ACCOUNT = '94208';
}
class_alias('Braintree\Error\Codes', 'Braintree_Error_Codes');

View File

@@ -0,0 +1,123 @@
<?php
namespace Braintree\Error;
use Braintree\Util;
/**
*
* Error handler
* Handles validation errors
*
* Contains a read-only property $error which is a ValidationErrorCollection
*
* @package Braintree
* @subpackage Errors
* @category Errors
*
* @property-read object $errors
*/
class ErrorCollection implements \Countable
{
private $_errors;
public function __construct($errorData)
{
$this->_errors =
new ValidationErrorCollection($errorData);
}
/**
* Return count of items in collection
* Implements countable
*
* @return integer
*/
public function count()
{
return $this->deepSize();
}
/**
* Returns all of the validation errors at all levels of nesting in a single, flat array.
*/
public function deepAll()
{
return $this->_errors->deepAll();
}
/**
* Returns the total number of validation errors at all levels of nesting. For example,
*if creating a customer with a credit card and a billing address, and each of the customer,
* credit card, and billing address has 1 error, this method will return 3.
*
* @return int size
*/
public function deepSize()
{
$size = $this->_errors->deepSize();
return $size;
}
/**
* return errors for the passed key name
*
* @param string $key
* @return mixed
*/
public function forKey($key)
{
return $this->_errors->forKey($key);
}
/**
* return errors for the passed html field.
* For example, $result->errors->onHtmlField("transaction[customer][last_name]")
*
* @param string $field
* @return array
*/
public function onHtmlField($field)
{
$pieces = preg_split("/[\[\]]+/", $field, 0, PREG_SPLIT_NO_EMPTY);
$errors = $this;
foreach(array_slice($pieces, 0, -1) as $key) {
$errors = $errors->forKey(Util::delimiterToCamelCase($key));
if (!isset($errors)) { return []; }
}
$finalKey = Util::delimiterToCamelCase(end($pieces));
return $errors->onAttribute($finalKey);
}
/**
* Returns the errors at the given nesting level (see forKey) in a single, flat array:
*
* <code>
* $result = Customer::create(...);
* $customerErrors = $result->errors->forKey('customer')->shallowAll();
* </code>
*/
public function shallowAll()
{
return $this->_errors->shallowAll();
}
/**
*
* @ignore
*/
public function __get($name)
{
$varName = "_$name";
return isset($this->$varName) ? $this->$varName : null;
}
/**
*
* @ignore
*/
public function __toString()
{
return sprintf('%s', $this->_errors);
}
}
class_alias('Braintree\Error\ErrorCollection', 'Braintree_Error_ErrorCollection');

View File

@@ -0,0 +1,60 @@
<?php
namespace Braintree\Error;
use Braintree\Util;
/**
* error object returned as part of a validation error collection
* provides read-only access to $attribute, $code, and $message
*
* <b>== More information ==</b>
*
* For more detailed information on Validation errors, see {@link https://developers.braintreepayments.com/reference/general/validation-errors/overview/php https://developers.braintreepayments.com/reference/general/validation-errors/overview/php}
*
* @package Braintree
* @subpackage Error
*
* @property-read string $attribute
* @property-read string $code
* @property-read string $message
*/
class Validation
{
private $_attribute;
private $_code;
private $_message;
/**
* @ignore
* @param array $attributes
*/
public function __construct($attributes)
{
$this->_initializeFromArray($attributes);
}
/**
* initializes instance properties from the keys/values of an array
* @ignore
* @access protected
* @param array $attributes array of properties to set - single level
* @return void
*/
private function _initializeFromArray($attributes)
{
foreach($attributes AS $name => $value) {
$varName = "_$name";
$this->$varName = Util::delimiterToCamelCase($value, '_');
}
}
/**
*
* @ignore
*/
public function __get($name)
{
$varName = "_$name";
return isset($this->$varName) ? $this->$varName : null;
}
}
class_alias('Braintree\Error\Validation', 'Braintree_Error_Validation');

View File

@@ -0,0 +1,131 @@
<?php
namespace Braintree\Error;
use Braintree\Collection;
/**
* collection of errors enumerating all validation errors for a given request
*
* <b>== More information ==</b>
*
* For more detailed information on Validation errors, see {@link https://developers.braintreepayments.com/reference/general/validation-errors/overview/php https://developers.braintreepayments.com/reference/general/validation-errors/overview/php}
*
* @package Braintree
* @subpackage Error
*
* @property-read array $errors
* @property-read array $nested
*/
class ValidationErrorCollection extends Collection
{
private $_errors = [];
private $_nested = [];
/**
* @ignore
*/
public function __construct($data)
{
foreach($data AS $key => $errorData)
// map errors to new collections recursively
if ($key == 'errors') {
foreach ($errorData AS $error) {
$this->_errors[] = new Validation($error);
}
} else {
$this->_nested[$key] = new ValidationErrorCollection($errorData);
}
}
public function deepAll()
{
$validationErrors = array_merge([], $this->_errors);
foreach($this->_nested as $nestedErrors)
{
$validationErrors = array_merge($validationErrors, $nestedErrors->deepAll());
}
return $validationErrors;
}
public function deepSize()
{
$total = sizeof($this->_errors);
foreach($this->_nested as $_nestedErrors)
{
$total = $total + $_nestedErrors->deepSize();
}
return $total;
}
public function forIndex($index)
{
return $this->forKey("index" . $index);
}
public function forKey($key)
{
return isset($this->_nested[$key]) ? $this->_nested[$key] : null;
}
public function onAttribute($attribute)
{
$matches = [];
foreach ($this->_errors AS $key => $error) {
if($error->attribute == $attribute) {
$matches[] = $error;
}
}
return $matches;
}
public function shallowAll()
{
return $this->_errors;
}
/**
*
* @ignore
*/
public function __get($name)
{
$varName = "_$name";
return isset($this->$varName) ? $this->$varName : null;
}
/**
* @ignore
*/
public function __toString()
{
$output = [];
// TODO: implement scope
if (!empty($this->_errors)) {
$output[] = $this->_inspect($this->_errors);
}
if (!empty($this->_nested)) {
foreach ($this->_nested AS $key => $values) {
$output[] = $this->_inspect($this->_nested);
}
}
return join(', ', $output);
}
/**
* @ignore
*/
private function _inspect($errors, $scope = null)
{
$eOutput = '[' . __CLASS__ . '/errors:[';
foreach($errors AS $error => $errorObj) {
$outputErrs[] = "({$errorObj->error['code']} {$errorObj->error['message']})";
}
$eOutput .= join(', ', $outputErrs) . ']]';
return $eOutput;
}
}
class_alias('Braintree\Error\ValidationErrorCollection', 'Braintree_Error_ValidationErrorCollection');

View File

@@ -0,0 +1 @@
<?php // Silence is golden.

View File

@@ -0,0 +1,67 @@
<?php
namespace Braintree;
/**
* Braintree EuropeBankAccount module
* Creates and manages Braintree Europe Bank Accounts
*
* <b>== More information ==</b>
*
* See {@link https://developers.braintreepayments.com/javascript+php}<br />
*
* @package Braintree
* @category Resources
*
* @property-read string $account-holder-name
* @property-read string $bic
* @property-read string $customerId
* @property-read string $default
* @property-read string $image-url
* @property-read string $mandate-reference-number
* @property-read string $masked-iban
* @property-read string $token
*/
class EuropeBankAccount extends Base
{
/* instance methods */
/**
* returns false if default is null or false
*
* @return boolean
*/
public function isDefault()
{
return $this->default;
}
/**
* factory method: returns an instance of EuropeBankAccount
* to the requesting method, with populated properties
*
* @ignore
* @return EuropeBankAccount
*/
public static function factory($attributes)
{
$defaultAttributes = [
];
$instance = new self();
$instance->_initialize(array_merge($defaultAttributes, $attributes));
return $instance;
}
/**
* sets instance properties from an array of values
*
* @access protected
* @param array $europeBankAccountAttribs array of EuropeBankAccount properties
* @return void
*/
protected function _initialize($europeBankAccountAttribs)
{
$this->_attributes = $europeBankAccountAttribs;
}
}
class_alias('Braintree\EuropeBankAccount', 'Braintree_EuropeBankAccount');

View File

@@ -0,0 +1,13 @@
<?php
namespace Braintree;
/**
* super class for all Braintree exceptions
*
* @package Braintree
* @subpackage Exception
*/
class Exception extends \Exception
{
}
class_alias('Braintree\Exception', 'Braintree_Exception');

View File

@@ -0,0 +1,17 @@
<?php
namespace Braintree\Exception;
use Braintree\Exception;
/**
* Raised when authentication fails.
* This may be caused by an incorrect Configuration
*
* @package Braintree
* @subpackage Exception
*/
class Authentication extends Exception
{
}
class_alias('Braintree\Exception\Authentication', 'Braintree_Exception_Authentication');

View File

@@ -0,0 +1,19 @@
<?php
namespace Braintree\Exception;
use Braintree\Exception;
/**
* Raised when authorization fails
* Raised when the API key being used is not authorized to perform
* the attempted action according to the roles assigned to the user
* who owns the API key.
*
* @package Braintree
* @subpackage Exception
*/
class Authorization extends Exception
{
}
class_alias('Braintree\Exception\Authorization', 'Braintree_Exception_Authorization');

View File

@@ -0,0 +1,17 @@
<?php
namespace Braintree\Exception;
use Braintree\Exception;
/**
* Raised when the Braintree library is not completely configured.
*
* @package Braintree
* @subpackage Exception
* @see Configuration
*/
class Configuration extends Exception
{
}
class_alias('Braintree\Exception\Configuration', 'Braintree_Exception_Configuration');

View File

@@ -0,0 +1,17 @@
<?php
namespace Braintree\Exception;
use Braintree\Exception;
/**
* Raised when the connection fails
*
* @package Braintree
* @subpackage Exception
* @copyright 2015 Braintree, a division of PayPal, Inc.
*/
class Connection extends Exception
{
}
class_alias('Braintree\Exception\Connection', 'Braintree_Exception_Connection');

View File

@@ -0,0 +1,16 @@
<?php
namespace Braintree\Exception;
use Braintree\Exception;
/**
* Raised when the gateway is down for maintenance.
*
* @package Braintree
* @subpackage Exception
*/
class DownForMaintenance extends Exception
{
}
class_alias('Braintree\Exception\DownForMaintenance', 'Braintree_Exception_DownForMaintenance');

View File

@@ -0,0 +1,20 @@
<?php
namespace Braintree\Exception;
use Braintree\Exception;
/**
* Raised when a suspected forged query string is present
* Raised from methods that confirm transparent redirect requests
* when the given query string cannot be verified. This may indicate
* an attempted hack on the merchant's transparent redirect
* confirmation URL.
*
* @package Braintree
* @subpackage Exception
*/
class ForgedQueryString extends Exception
{
}
class_alias('Braintree\Exception\ForgedQueryString', 'Braintree_Exception_ForgedQueryString');

View File

@@ -0,0 +1,9 @@
<?php
namespace Braintree\Exception;
use Braintree\Exception;
class InvalidChallenge extends Exception
{
}
class_alias('Braintree\Exception\InvalidChallenge', 'Braintree_Exception_InvalidChallenge');

View File

@@ -0,0 +1,9 @@
<?php
namespace Braintree\Exception;
use Braintree\Exception;
class InvalidSignature extends Exception
{
}
class_alias('Braintree\Exception\InvalidSignature', 'Braintree_Exception_InvalidSignature');

View File

@@ -0,0 +1,16 @@
<?php
namespace Braintree\Exception;
use Braintree\Exception;
/**
* Raised when a record could not be found.
*
* @package Braintree
* @subpackage Exception
*/
class NotFound extends Exception
{
}
class_alias('Braintree\Exception\NotFound', 'Braintree_Exception_NotFound');

View File

@@ -0,0 +1,16 @@
<?php
namespace Braintree\Exception;
use Braintree\Exception;
/**
* Raised when the SSL CaFile is not found.
*
* @package Braintree
* @subpackage Exception
*/
class SSLCaFileNotFound extends Exception
{
}
class_alias('Braintree\Exception\SSLCaFileNotFound', 'Braintree_Exception_SSLCaFileNotFound');

View File

@@ -0,0 +1,16 @@
<?php
namespace Braintree\Exception;
use Braintree\Exception;
/**
* Raised when the SSL certificate fails verification.
*
* @package Braintree
* @subpackage Exception
*/
class SSLCertificate extends Exception
{
}
class_alias('Braintree\Exception\SSLCertificate', 'Braintree_Exception_SSLCertificate');

View File

@@ -0,0 +1,16 @@
<?php
namespace Braintree\Exception;
use Braintree\Exception;
/**
* Raised when an unexpected server error occurs.
*
* @package Braintree
* @subpackage Exception
*/
class ServerError extends Exception
{
}
class_alias('Braintree\Exception\ServerError', 'Braintree_Exception_ServerError');

View File

@@ -0,0 +1,15 @@
<?php
namespace Braintree\Exception;
use Braintree\Exception;
/**
* Raised when a test method is used in production.
*
* @package Braintree
* @subpackage Exception
*/
class TestOperationPerformedInProduction extends Exception
{
}
class_alias('Braintree\Exception\TestOperationPerformedInProduction', 'Braintree_Exception_TestOperationPerformedInProduction');

View File

@@ -0,0 +1,16 @@
<?php
namespace Braintree\Exception;
use Braintree\Exception;
/**
* Raised when a Timeout occurs
*
* @package Braintree
* @subpackage Exception
*/
class Timeout extends Exception
{
}
class_alias('Braintree\Exception\Timeout', 'Braintree_Exception_Timeout');

View File

@@ -0,0 +1,16 @@
<?php
namespace Braintree\Exception;
use Braintree\Exception;
/**
* Raised when the gateway request rate-limit is exceeded.
*
* @package Braintree
* @subpackage Exception
*/
class TooManyRequests extends Exception
{
}
class_alias('Braintree\Exception\TooManyRequests', 'Braintree_Exception_TooManyRequests');

View File

@@ -0,0 +1,17 @@
<?php
namespace Braintree\Exception;
use Braintree\Exception;
/**
* Raised when an error occurs that the client library is not built to handle.
* This shouldn't happen.
*
* @package Braintree
* @subpackage Exception
*/
class Unexpected extends Exception
{
}
class_alias('Braintree\Exception\Unexpected', 'Braintree_Exception_Unexpected');

View File

@@ -0,0 +1,16 @@
<?php
namespace Braintree\Exception;
use Braintree\Exception;
/**
* Raised when a client library must be upgraded.
*
* @package Braintree
* @subpackage Exception
*/
class UpgradeRequired extends Exception
{
}
class_alias('Braintree\Exception\UpgradeRequired', 'Braintree_Exception_UpgradeRequired');

View File

@@ -0,0 +1,16 @@
<?php
namespace Braintree\Exception;
use Braintree\Exception;
/**
* Raised from non-validating methods when gateway validations fail.
*
* @package Braintree
* @subpackage Exception
*/
class ValidationsFailed extends Exception
{
}
class_alias('Braintree\Exception\ValidationsFailed', 'Braintree_Exception_ValidationsFailed');

View File

@@ -0,0 +1,34 @@
<?php
namespace Braintree;
/**
* @property-read string $merchantId
* @property-read string $merchantName
* @property-read string $paymentMethodNonce
*/
class FacilitatedDetails extends Base
{
public static function factory($attributes)
{
$instance = new self();
$instance->_initialize($attributes);
return $instance;
}
protected function _initialize($attributes)
{
$this->_attributes = $attributes;
}
/**
* returns a string representation of the facilitated details
* @return string
*/
public function __toString()
{
return __CLASS__ . '[' .
Util::attributesToString($this->_attributes) .']';
}
}
class_alias('Braintree\FacilitatedDetails', 'Braintree_FacilitatedDetails');

View File

@@ -0,0 +1,35 @@
<?php
namespace Braintree;
/**
* @property-read string $oauthApplicationClientId
* @property-read string $oauthApplicationName
* @property-read string $sourcePaymentMethodToken
*/
class FacilitatorDetails extends Base
{
public static function factory($attributes)
{
$instance = new self();
$instance->_initialize($attributes);
return $instance;
}
protected function _initialize($attributes)
{
$this->_attributes = $attributes;
}
/**
* returns a string representation of the facilitator details
* @return string
*/
public function __toString()
{
return __CLASS__ . '[' .
Util::attributesToString($this->_attributes) .']';
}
}
class_alias('Braintree\FacilitatorDetails', 'Braintree_FacilitatorDetails');

View File

@@ -0,0 +1,278 @@
<?php
namespace Braintree;
/**
* Braintree Gateway module
*
* @package Braintree
* @category Resources
*/
class Gateway
{
/**
*
* @var Configuration
*/
public $config;
public function __construct($config)
{
if (is_array($config)) {
$config = new Configuration($config);
}
$this->config = $config;
}
/**
*
* @return AddOnGateway
*/
public function addOn()
{
return new AddOnGateway($this);
}
/**
*
* @return AddressGateway
*/
public function address()
{
return new AddressGateway($this);
}
/**
*
* @return ApplePayGateway
*/
public function applePay()
{
return new ApplePayGateway($this);
}
/**
*
* @return ClientTokenGateway
*/
public function clientToken()
{
return new ClientTokenGateway($this);
}
/**
*
* @return CreditCardGateway
*/
public function creditCard()
{
return new CreditCardGateway($this);
}
/**
*
* @return CreditCardVerificationGateway
*/
public function creditCardVerification()
{
return new CreditCardVerificationGateway($this);
}
/**
*
* @return CustomerGateway
*/
public function customer()
{
return new CustomerGateway($this);
}
/**
*
* @return DiscountGateway
*/
public function discount()
{
return new DiscountGateway($this);
}
/**
*
* @return DisputeGateway
*/
public function dispute()
{
return new DisputeGateway($this);
}
/**
*
* @return DocumentUploadGateway
*/
public function documentUpload()
{
return new DocumentUploadGateway($this);
}
/**
*
* @return MerchantGateway
*/
public function merchant()
{
return new MerchantGateway($this);
}
/**
*
* @return MerchantAccountGateway
*/
public function merchantAccount()
{
return new MerchantAccountGateway($this);
}
/**
*
* @return OAuthGateway
*/
public function oauth()
{
return new OAuthGateway($this);
}
/**
*
* @return PaymentMethodGateway
*/
public function paymentMethod()
{
return new PaymentMethodGateway($this);
}
/**
*
* @return PaymentMethodNonceGateway
*/
public function paymentMethodNonce()
{
return new PaymentMethodNonceGateway($this);
}
/**
*
* @return PayPalAccountGateway
*/
public function payPalAccount()
{
return new PayPalAccountGateway($this);
}
/**
*
* @return PlanGateway
*/
public function plan()
{
return new PlanGateway($this);
}
/**
*
* @return SettlementBatchSummaryGateway
*/
public function settlementBatchSummary()
{
return new SettlementBatchSummaryGateway($this);
}
/**
*
* @return SubscriptionGateway
*/
public function subscription()
{
return new SubscriptionGateway($this);
}
/**
*
* @return TestingGateway
*/
public function testing()
{
return new TestingGateway($this);
}
/**
*
* @return TransactionGateway
*/
public function transaction()
{
return new TransactionGateway($this);
}
/**
*
* @return TransactionLineItemGateway
*/
public function transactionLineItem()
{
return new TransactionLineItemGateway($this);
}
/**
*
* @return TransparentRedirectGateway
*/
public function transparentRedirect()
{
return new TransparentRedirectGateway($this);
}
/**
*
* @return UsBankAccountGateway
*/
public function usBankAccount()
{
return new UsBankAccountGateway($this);
}
/**
*
* @return UsBankAccountVerificationGateway
*/
public function usBankAccountVerification()
{
return new UsBankAccountVerificationGateway($this);
}
/**
*
* @return IdealPaymentGateway
*/
public function idealPayment()
{
return new IdealPaymentGateway($this);
}
/**
*
* @return WebhookNotificationGateway
*/
public function webhookNotification()
{
return new WebhookNotificationGateway($this);
}
/**
*
* @return WebhookTestingGateway
*/
public function webhookTesting()
{
return new WebhookTestingGateway($this);
}
}
class_alias('Braintree\Gateway', 'Braintree_Gateway');

View File

@@ -0,0 +1,73 @@
<?php
namespace Braintree;
/**
* Braintree GrantedPaymentInstrumentUpdate module
*
* @package Braintree
* @category Resources
*/
/**
* Manages Braintree GrantedPaymentInstrumentUpdate
*
* <b>== More information ==</b>
*
*
* @package Braintree
* @category Resources
*
* @property-read string $grantOwnerMerchantId
* @property-read string $grantRecipientMerchantId
* @property-read string $paymentMethodNonce
* @property-read string $token
* @property-read string $updatedFields
*/
class GrantedPaymentInstrumentUpdate extends Base
{
/**
* factory method: returns an instance of GrantedPaymentInstrumentUpdate
* to the requesting method, with populated properties
*
* @ignore
* @return GrantedPaymentInstrumentUpdate
*/
public static function factory($attributes)
{
$instance = new self();
$instance->_initialize($attributes);
return $instance;
}
/* instance methods */
/**
* sets instance properties from an array of values
*
* @access protected
* @param array $GrantedPaymentInstrumentAttribs array of grantedPaymentInstrumentUpdate data
* @return void
*/
protected function _initialize($grantedPaymentInstrumentUpdateAttribs)
{
// set the attributes
$this->_attributes = $grantedPaymentInstrumentUpdateAttribs;
$paymentMethodNonce = isset($grantedPaymentInstrumentUpdateAttribs['paymentMethodNonce']) ?
GrantedPaymentInstrumentUpdate::factory($grantedPaymentInstrumentUpdateAttribs['paymentMethodNonce']) :
null;
$this->_set('paymentMethodNonce', $paymentMethodNonce);
}
/**
* create a printable representation of the object as:
* ClassName[property=value, property=value]
* @return string
*/
public function __toString()
{
return __CLASS__ . '[' .
Util::attributesToString($this->_attributes) . ']';
}
}
class_alias('Braintree\GrantedPaymentInstrumentUpdate', 'Braintree_GrantedPaymentInstrumentUpdate');

View File

@@ -0,0 +1,44 @@
<?php
namespace Braintree;
use finfo;
/**
* Braintree GraphQL Client
* process GraphQL requests using curl
*/
class GraphQL extends Http
{
public function __construct($config)
{
parent::__construct($config);
}
public function graphQLHeaders()
{
return [
'Accept: application/json',
'Braintree-Version: ' . Configuration::GRAPHQL_API_VERSION,
'Content-Type: application/json',
'User-Agent: Braintree PHP Library ' . Version::get(),
'X-ApiVersion: ' . Configuration::API_VERSION
];
}
public function request($definition, $variables)
{
$graphQLRequest = ["query" => $definition];
if ($variables) {
$graphQLRequest["variables"] = $variables;
}
$response = $this->_doUrlRequest('POST', $this->_config->graphQLBaseUrl(), json_encode($graphQLRequest), null, $this->graphQLHeaders());
$result = json_decode($response["body"], true);
Util::throwGraphQLResponseException($result);
return $result;
}
}
class_alias('Braintree\GraphQL', 'Braintree_GraphQL');

View File

@@ -0,0 +1,273 @@
<?php
namespace Braintree;
use finfo;
/**
* Braintree HTTP Client
* processes Http requests using curl
*/
class Http
{
protected $_config;
private $_useClientCredentials = false;
public function __construct($config)
{
$this->_config = $config;
}
public function delete($path, $params = null)
{
$response = $this->_doRequest('DELETE', $path, $this->_buildXml($params));
$responseCode = $response['status'];
if ($responseCode === 200 || $responseCode === 204) {
return true;
} else if ($responseCode === 422) {
return Xml::buildArrayFromXml($response['body']);
} else {
Util::throwStatusCodeException($response['status']);
}
}
public function get($path)
{
$response = $this->_doRequest('GET', $path);
if ($response['status'] === 200) {
return Xml::buildArrayFromXml($response['body']);
} else {
Util::throwStatusCodeException($response['status']);
}
}
public function post($path, $params = null)
{
$response = $this->_doRequest('POST', $path, $this->_buildXml($params));
$responseCode = $response['status'];
if ($responseCode === 200 || $responseCode === 201 || $responseCode === 422 || $responseCode == 400) {
return Xml::buildArrayFromXml($response['body']);
} else {
Util::throwStatusCodeException($responseCode);
}
}
public function postMultipart($path, $params, $file)
{
$headers = [
'User-Agent: Braintree PHP Library ' . Version::get(),
'X-ApiVersion: ' . Configuration::API_VERSION
];
$response = $this->_doRequest('POST', $path, $params, $file, $headers);
$responseCode = $response['status'];
if ($responseCode === 200 || $responseCode === 201 || $responseCode === 422 || $responseCode == 400) {
return Xml::buildArrayFromXml($response['body']);
} else {
Util::throwStatusCodeException($responseCode);
}
}
public function put($path, $params = null)
{
$response = $this->_doRequest('PUT', $path, $this->_buildXml($params));
$responseCode = $response['status'];
if ($responseCode === 200 || $responseCode === 201 || $responseCode === 422 || $responseCode == 400) {
return Xml::buildArrayFromXml($response['body']);
} else {
Util::throwStatusCodeException($responseCode);
}
}
private function _buildXml($params)
{
return empty($params) ? null : Xml::buildXmlFromArray($params);
}
private function _getHeaders()
{
return [
'Accept: application/xml',
];
}
private function _getAuthorization()
{
if ($this->_useClientCredentials) {
return [
'user' => $this->_config->getClientId(),
'password' => $this->_config->getClientSecret(),
];
} else if ($this->_config->isAccessToken()) {
return [
'token' => $this->_config->getAccessToken(),
];
} else {
return [
'user' => $this->_config->getPublicKey(),
'password' => $this->_config->getPrivateKey(),
];
}
}
public function useClientCredentials()
{
$this->_useClientCredentials = true;
}
private function _doRequest($httpVerb, $path, $requestBody = null, $file = null, $headers = null)
{
return $this->_doUrlRequest($httpVerb, $this->_config->baseUrl() . $path, $requestBody, $file, $headers);
}
public function _doUrlRequest($httpVerb, $url, $requestBody = null, $file = null, $customHeaders = null)
{
$curl = curl_init();
curl_setopt($curl, CURLOPT_TIMEOUT, $this->_config->timeout());
curl_setopt($curl, CURLOPT_CUSTOMREQUEST, $httpVerb);
curl_setopt($curl, CURLOPT_URL, $url);
if ($this->_config->acceptGzipEncoding()) {
curl_setopt($curl, CURLOPT_ENCODING, 'gzip');
}
if ($this->_config->sslVersion()) {
curl_setopt($curl, CURLOPT_SSLVERSION, $this->_config->sslVersion());
}
$headers = [];
if ($customHeaders) {
$headers = $customHeaders;
} else {
$headers = $this->_getHeaders($curl);
$headers[] = 'User-Agent: Braintree PHP Library ' . Version::get();
$headers[] = 'X-ApiVersion: ' . Configuration::API_VERSION;
$headers[] = 'Content-Type: application/xml';
}
$authorization = $this->_getAuthorization();
if (isset($authorization['user'])) {
curl_setopt($curl, CURLOPT_HTTPAUTH, CURLAUTH_BASIC);
curl_setopt($curl, CURLOPT_USERPWD, $authorization['user'] . ':' . $authorization['password']);
} else if (isset($authorization['token'])) {
$headers[] = 'Authorization: Bearer ' . $authorization['token'];
}
if ($this->_config->sslOn()) {
curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, true);
curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, 2);
curl_setopt($curl, CURLOPT_CAINFO, $this->getCaFile());
}
if (!empty($file)) {
$boundary = "---------------------" . md5(mt_rand() . microtime());
$headers[] = "Content-Type: multipart/form-data; boundary={$boundary}";
$this->prepareMultipart($curl, $requestBody, $file, $boundary);
} else if (!empty($requestBody)) {
curl_setopt($curl, CURLOPT_POSTFIELDS, $requestBody);
}
if ($this->_config->isUsingProxy()) {
$proxyHost = $this->_config->getProxyHost();
$proxyPort = $this->_config->getProxyPort();
$proxyType = $this->_config->getProxyType();
$proxyUser = $this->_config->getProxyUser();
$proxyPwd= $this->_config->getProxyPassword();
curl_setopt($curl, CURLOPT_PROXY, $proxyHost . ':' . $proxyPort);
if (!empty($proxyType)) {
curl_setopt($curl, CURLOPT_PROXYTYPE, $proxyType);
}
if ($this->_config->isAuthenticatedProxy()) {
curl_setopt($curl, CURLOPT_PROXYUSERPWD, $proxyUser . ':' . $proxyPwd);
}
}
curl_setopt($curl, CURLOPT_HTTPHEADER, $headers);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
$response = curl_exec($curl);
$httpStatus = curl_getinfo($curl, CURLINFO_HTTP_CODE);
$error_code = curl_errno($curl);
$error = curl_error($curl);
if ($error_code == 28 && $httpStatus == 0) {
throw new Exception\Timeout();
}
curl_close($curl);
if ($this->_config->sslOn()) {
if ($httpStatus == 0) {
throw new Exception\SSLCertificate($error, $error_code);
}
} else if ($error_code) {
throw new Exception\Connection($error, $error_code);
}
return ['status' => $httpStatus, 'body' => $response];
}
function prepareMultipart($ch, $requestBody, $file, $boundary) {
$disallow = ["\0", "\"", "\r", "\n"];
$fileInfo = new finfo(FILEINFO_MIME_TYPE);
$filePath = stream_get_meta_data($file)['uri'];
$data = file_get_contents($filePath);
$mimeType = $fileInfo->buffer($data);
// build normal parameters
foreach ($requestBody as $k => $v) {
$k = str_replace($disallow, "_", $k);
$body[] = implode("\r\n", [
"Content-Disposition: form-data; name=\"{$k}\"",
"",
filter_var($v),
]);
}
// build file parameter
$splitFilePath = explode(DIRECTORY_SEPARATOR, $filePath);
$filePath = end($splitFilePath);
$filePath = str_replace($disallow, "_", $filePath);
$body[] = implode("\r\n", [
"Content-Disposition: form-data; name=\"file\"; filename=\"{$filePath}\"",
"Content-Type: {$mimeType}",
"",
$data,
]);
// add boundary for each parameters
array_walk($body, function (&$part) use ($boundary) {
$part = "--{$boundary}\r\n{$part}";
});
// add final boundary
$body[] = "--{$boundary}--";
$body[] = "";
// set options
return curl_setopt_array($ch, [
CURLOPT_POST => true,
CURLOPT_POSTFIELDS => implode("\r\n", $body)
]);
}
private function getCaFile()
{
static $memo;
if ($memo === null) {
$caFile = $this->_config->caFile();
if (substr($caFile, 0, 7) !== 'phar://') {
return $caFile;
}
$extractedCaFile = sys_get_temp_dir() . '/api_braintreegateway_com.ca.crt';
if (!file_exists($extractedCaFile) || sha1_file($extractedCaFile) != sha1_file($caFile)) {
if (!copy($caFile, $extractedCaFile)) {
throw new Exception\SSLCaFileNotFound();
}
}
$memo = $extractedCaFile;
}
return $memo;
}
}
class_alias('Braintree\Http', 'Braintree_Http');

View File

@@ -0,0 +1,57 @@
<?php
namespace Braintree;
/**
* Braintree IbanBankAccount module
* PHP Version 5
*
* @package Braintree
*
* @property-read string $maskedIban
* @property-read string $bic
* @property-read string $ibanCountry
* @property-read string $description
* @property-read string $ibanAccountNumberLast4
*/
class IbanBankAccount extends Base
{
/**
* create a printable representation of the object as:
* ClassName[property=value, property=value]
* @ignore
* @return string
*/
public function __toString()
{
return __CLASS__ . '[' .
Util::attributesToString($this->_attributes) . ']';
}
/**
* sets instance properties from an array of values
*
* @ignore
* @access protected
* @param array $ibanAttribs array of ibanBankAccount data
* @return void
*/
protected function _initialize($ibanAttribs)
{
// set the attributes
$this->_attributes = $ibanAttribs;
}
/**
* factory method: returns an instance of IbanBankAccount
* to the requesting method, with populated properties
* @ignore
* @return IbanBankAccount
*/
public static function factory($attributes)
{
$instance = new self();
$instance->_initialize($attributes);
return $instance;
}
}
class_alias('Braintree\IbanBankAccount', 'Braintree_IbanBankAccount');

View File

@@ -0,0 +1,92 @@
<?php
namespace Braintree;
/**
* Braintree IdealPayment module
*
* @package Braintree
* @category Resources
*/
/**
* Manages Braintree IdealPayments
*
* <b>== More information ==</b>
*
*
* @package Braintree
* @category Resources
*
* @property-read string $id
* @property-read string $idealTransactionId
* @property-read string $currency
* @property-read string $amount
* @property-read string $status
* @property-read string $orderId
* @property-read string $issuer
* @property-read string $ibanBankAccount
*/
class IdealPayment extends Base
{
/**
* factory method: returns an instance of IdealPayment
* to the requesting method, with populated properties
*
* @ignore
* @return IdealPayment
*/
public static function factory($attributes)
{
$instance = new self();
$instance->_initialize($attributes);
return $instance;
}
/* instance methods */
/**
* sets instance properties from an array of values
*
* @access protected
* @param array $idealPaymentAttribs array of idealPayment data
* @return void
*/
protected function _initialize($idealPaymentAttribs)
{
// set the attributes
$this->_attributes = $idealPaymentAttribs;
$ibanBankAccount = isset($idealPaymentAttribs['ibanBankAccount']) ?
IbanBankAccount::factory($idealPaymentAttribs['ibanBankAccount']) :
null;
$this->_set('ibanBankAccount', $ibanBankAccount);
}
/**
* create a printable representation of the object as:
* ClassName[property=value, property=value]
* @return string
*/
public function __toString()
{
return __CLASS__ . '[' .
Util::attributesToString($this->_attributes) . ']';
}
// static methods redirecting to gateway
public static function find($idealPaymentId)
{
return Configuration::gateway()->idealPayment()->find($idealPaymentId);
}
public static function sale($idealPaymentId, $transactionAttribs)
{
$transactionAttribs['options'] = [
'submitForSettlement' => true
];
return Configuration::gateway()->idealPayment()->sale($idealPaymentId, $transactionAttribs);
}
}
class_alias('Braintree\IdealPayment', 'Braintree_IdealPayment');

View File

@@ -0,0 +1,104 @@
<?php
namespace Braintree;
use InvalidArgumentException;
/**
* Braintree IdealPaymentGateway module
*
* @package Braintree
* @category Resources
*/
/**
* Manages Braintree IdealPayments
*
* <b>== More information ==</b>
*
*
* @package Braintree
* @category Resources
*/
class IdealPaymentGateway
{
private $_gateway;
private $_config;
private $_http;
public function __construct($gateway)
{
$this->_gateway = $gateway;
$this->_config = $gateway->config;
$this->_config->assertHasAccessTokenOrKeys();
$this->_http = new Http($gateway->config);
}
/**
* find an IdealPayment by id
*
* @access public
* @param string $idealPaymentId
* @return IdealPayment
* @throws Exception\NotFound
*/
public function find($idealPaymentId)
{
try {
$path = $this->_config->merchantPath() . '/ideal_payments/' . $idealPaymentId;
$response = $this->_http->get($path);
return IdealPayment::factory($response['idealPayment']);
} catch (Exception\NotFound $e) {
throw new Exception\NotFound(
'iDEAL Payment with id ' . $idealPaymentId . ' not found'
);
}
}
/**
* create a new sale for the current IdealPayment
*
* @param string $idealPaymentId
* @param array $transactionAttribs
* @return Result\Successful|Result\Error
* @see Transaction::sale()
*/
public function sale($idealPaymentId, $transactionAttribs)
{
return Transaction::sale(
array_merge(
$transactionAttribs,
['paymentMethodNonce' => $idealPaymentId]
)
);
}
/**
* generic method for validating incoming gateway responses
*
* creates a new IdealPayment object and encapsulates
* it inside a Result\Successful object, or
* encapsulates a Errors object inside a Result\Error
* alternatively, throws an Unexpected exception if the response is invalid.
*
* @ignore
* @param array $response gateway response values
* @return Result\Successful|Result\Error
* @throws Exception\Unexpected
*/
private function _verifyGatewayResponse($response)
{
if (isset($response['idealPayment'])) {
// return a populated instance of IdealPayment
return new Result\Successful(
IdealPayment::factory($response['idealPayment'])
);
} else if (isset($response['apiErrorResponse'])) {
return new Result\Error($response['apiErrorResponse']);
} else {
throw new Exception\Unexpected(
'Expected Ideal Payment or apiErrorResponse'
);
}
}
}
class_alias('Braintree\IdealPaymentGateway', 'Braintree_IdealPaymentGateway');

View File

@@ -0,0 +1,74 @@
<?php
namespace Braintree;
/**
* Braintree Class Instance template
*
* @abstract
*/
abstract class Instance
{
protected $_attributes = [];
/**
*
* @param array $attributes
*/
public function __construct($attributes)
{
if (!empty($attributes)) {
$this->_initializeFromArray($attributes);
}
}
/**
* returns private/nonexistent instance properties
* @access public
* @param string $name property name
* @return mixed contents of instance properties
*/
public function __get($name)
{
if (array_key_exists($name, $this->_attributes)) {
return $this->_attributes[$name];
} else {
trigger_error('Undefined property on ' . get_class($this) . ': ' . $name, E_USER_NOTICE);
return null;
}
}
/**
* used by isset() and empty()
* @access public
* @param string $name property name
* @return boolean
*/
public function __isset($name)
{
return array_key_exists($name, $this->_attributes);
}
/**
* create a printable representation of the object as:
* ClassName[property=value, property=value]
* @return string
*/
public function __toString()
{
$objOutput = Util::implodeAssociativeArray($this->_attributes);
return get_class($this) .'[' . $objOutput . ']';
}
/**
* initializes instance properties from the keys/values of an array
* @ignore
* @access protected
* @param <type> $aAttribs array of properties to set - single level
* @return void
*/
private function _initializeFromArray($attributes)
{
$this->_attributes = $attributes;
}
}
class_alias('Braintree\Instance', 'Braintree_Instance');

View File

@@ -0,0 +1,24 @@
<?php
namespace Braintree;
class IsNode
{
public function __construct($name)
{
$this->name = $name;
$this->searchTerms = [];
}
public function is($value)
{
$this->searchTerms['is'] = strval($value);
return $this;
}
public function toParam()
{
return $this->searchTerms;
}
}
class_alias('Braintree\IsNode', 'Braintree_IsNode');

View File

@@ -0,0 +1,23 @@
<?php
namespace Braintree;
class KeyValueNode
{
public function __construct($name)
{
$this->name = $name;
$this->searchTerm = True;
}
public function is($value)
{
$this->searchTerm = $value;
return $this;
}
public function toParam()
{
return $this->searchTerm;
}
}
class_alias('Braintree\KeyValueNode', 'Braintree_KeyValueNode');

View File

@@ -0,0 +1,68 @@
<?php
namespace Braintree;
/**
* Braintree LocalPaymentCompleted module
*
* @package Braintree
* @category Resources
*/
/**
* Manages Braintree LocalPaymentCompleted
*
* <b>== More information ==</b>
*
*
* @package Braintree
* @category Resources
*
* @property-read string $grantOwnerMerchantId
* @property-read string $grantRecipientMerchantId
* @property-read string $paymentMethodNonce
* @property-read string $token
* @property-read string $updatedFields
*/
class LocalPaymentCompleted extends Base
{
/**
* factory method: returns an instance of GrantedPaymentInstrumentUpdate
* to the requesting method, with populated properties
*
* @ignore
* @return LocalPaymentCompleted
*/
public static function factory($attributes)
{
$instance = new self();
$instance->_initialize($attributes);
return $instance;
}
/* instance methods */
/**
* sets instance properties from an array of values
*
* @access protected
* @param array $LocalPaymentCompletedAttribs array of localPaymentCompleted data
* @return void
*/
protected function _initialize($localPaymentCompletedAttribs)
{
// set the attributes
$this->_attributes = $localPaymentCompletedAttribs;
}
/**
* create a printable representation of the object as:
* ClassName[property=value, property=value]
* @return string
*/
public function __toString()
{
return __CLASS__ . '[' .
Util::attributesToString($this->_attributes) . ']';
}
}
class_alias('Braintree\LocalPaymentCompleted', 'Braintree_LocalPaymentCompleted');

View File

@@ -0,0 +1,141 @@
<?php
namespace Braintree;
/**
* Braintree MasterpassCard module
* Creates and manages Braintree MasterpassCards
*
* <b>== More information ==</b>
*
* For more detailed information on CreditCard verifications, see {@link https://developers.braintreepayments.com/reference/response/credit-card-verification/php https://developers.braintreepayments.com/reference/response/credit-card-verification/php}
*
* @package Braintree
* @category Resources
*
* @property-read \Braintree\Address $billingAddress
* @property-read string $bin
* @property-read string $cardType
* @property-read string $cardholderName
* @property-read string $commercial
* @property-read string $countryOfIssuance
* @property-read \DateTime $createdAt
* @property-read string $customerId
* @property-read string $customerLocation
* @property-read string $debit
* @property-read boolean $default
* @property-read string $durbinRegulated
* @property-read string $expirationDate
* @property-read string $expirationMonth
* @property-read string $expirationYear
* @property-read boolean $expired
* @property-read string $healthcare
* @property-read string $imageUrl
* @property-read string $issuingBank
* @property-read string $last4
* @property-read string $maskedNumber
* @property-read string $payroll
* @property-read string $prepaid
* @property-read string $productId
* @property-read \Braintree\Subscription[] $subscriptions
* @property-read string $token
* @property-read string $uniqueNumberIdentifier
* @property-read \DateTime $updatedAt
*/
class MasterpassCard extends Base
{
/* instance methods */
/**
* returns false if default is null or false
*
* @return boolean
*/
public function isDefault()
{
return $this->default;
}
/**
* checks whether the card is expired based on the current date
*
* @return boolean
*/
public function isExpired()
{
return $this->expired;
}
/**
* sets instance properties from an array of values
*
* @access protected
* @param array $creditCardAttribs array of creditcard data
* @return void
*/
protected function _initialize($creditCardAttribs)
{
// set the attributes
$this->_attributes = $creditCardAttribs;
// map each address into its own object
$billingAddress = isset($creditCardAttribs['billingAddress']) ?
Address::factory($creditCardAttribs['billingAddress']) :
null;
$subscriptionArray = [];
if (isset($creditCardAttribs['subscriptions'])) {
foreach ($creditCardAttribs['subscriptions'] AS $subscription) {
$subscriptionArray[] = Subscription::factory($subscription);
}
}
$this->_set('subscriptions', $subscriptionArray);
$this->_set('billingAddress', $billingAddress);
$this->_set('expirationDate', $this->expirationMonth . '/' . $this->expirationYear);
$this->_set('maskedNumber', $this->bin . '******' . $this->last4);
}
/**
* returns false if comparing object is not a CreditCard,
* or is a CreditCard with a different id
*
* @param object $otherCreditCard customer to compare against
* @return boolean
*/
public function isEqual($otherMasterpassCard)
{
return !($otherMasterpassCard instanceof self) ? false : $this->token === $otherMasterpassCard->token;
}
/**
* create a printable representation of the object as:
* ClassName[property=value, property=value]
* @return string
*/
public function __toString()
{
return __CLASS__ . '[' .
Util::attributesToString($this->_attributes) .']';
}
/**
* factory method: returns an instance of CreditCard
* to the requesting method, with populated properties
*
* @ignore
* @return MasterpassCard
*/
public static function factory($attributes)
{
$defaultAttributes = [
'bin' => '',
'expirationMonth' => '',
'expirationYear' => '',
'last4' => '',
];
$instance = new self();
$instance->_initialize(array_merge($defaultAttributes, $attributes));
return $instance;
}
}
class_alias('Braintree\MasterpassCard', 'Braintree_MasterpassCard');

View File

@@ -0,0 +1,36 @@
<?php
namespace Braintree;
class Merchant extends Base
{
protected function _initialize($attribs)
{
$this->_attributes = $attribs;
$merchantAccountArray = [];
if (isset($attribs['merchantAccounts'])) {
foreach ($attribs['merchantAccounts'] AS $merchantAccount) {
$merchantAccountArray[] = MerchantAccount::factory($merchantAccount);
}
}
$this->_set('merchantAccounts', $merchantAccountArray);
}
public static function factory($attributes)
{
$instance = new self();
$instance->_initialize($attributes);
return $instance;
}
/**
* returns a string representation of the merchant
* @return string
*/
public function __toString()
{
return __CLASS__ . '[' .
Util::attributesToString($this->_attributes) .']';
}
}
class_alias('Braintree\Merchant', 'Braintree_Merchant');

View File

@@ -0,0 +1,74 @@
<?php
namespace Braintree;
/**
* @property-read \Braintree\MerchantAccount\BusinessDetails $businessDetails
* @property-read string $currencyIsoCode
* @property-read boolean $default
* @property-read \Braintree\MerchantAccount\FundingDetails $fundingDetails
* @property-read string $id
* @property-read \Braintree\MerchantAccount\IndividualDetails $individualDetails
* @property-read \Braintree\MerchantAccount $masterMerchantAccount
* @property-read string $status
*/
class MerchantAccount extends Base
{
const STATUS_ACTIVE = 'active';
const STATUS_PENDING = 'pending';
const STATUS_SUSPENDED = 'suspended';
const FUNDING_DESTINATION_BANK = 'bank';
const FUNDING_DESTINATION_EMAIL = 'email';
const FUNDING_DESTINATION_MOBILE_PHONE = 'mobile_phone';
public static function factory($attributes)
{
$instance = new self();
$instance->_initialize($attributes);
return $instance;
}
protected function _initialize($merchantAccountAttribs)
{
$this->_attributes = $merchantAccountAttribs;
if (isset($merchantAccountAttribs['individual'])) {
$individual = $merchantAccountAttribs['individual'];
$this->_set('individualDetails', MerchantAccount\IndividualDetails::Factory($individual));
}
if (isset($merchantAccountAttribs['business'])) {
$business = $merchantAccountAttribs['business'];
$this->_set('businessDetails', MerchantAccount\BusinessDetails::Factory($business));
}
if (isset($merchantAccountAttribs['funding'])) {
$funding = $merchantAccountAttribs['funding'];
$this->_set('fundingDetails', new MerchantAccount\FundingDetails($funding));
}
if (isset($merchantAccountAttribs['masterMerchantAccount'])) {
$masterMerchantAccount = $merchantAccountAttribs['masterMerchantAccount'];
$this->_set('masterMerchantAccount', self::Factory($masterMerchantAccount));
}
}
// static methods redirecting to gateway
public static function create($attribs)
{
return Configuration::gateway()->merchantAccount()->create($attribs);
}
public static function find($merchant_account_id)
{
return Configuration::gateway()->merchantAccount()->find($merchant_account_id);
}
public static function update($merchant_account_id, $attributes)
{
return Configuration::gateway()->merchantAccount()->update($merchant_account_id, $attributes);
}
}
class_alias('Braintree\MerchantAccount', 'Braintree_MerchantAccount');

View File

@@ -0,0 +1,10 @@
<?php
namespace Braintree\MerchantAccount;
use Braintree\Instance;
class AddressDetails extends Instance
{
protected $_attributes = [];
}
class_alias('Braintree\MerchantAccount\AddressDetails', 'Braintree_MerchantAccount_AddressDetails');

View File

@@ -0,0 +1,23 @@
<?php
namespace Braintree\MerchantAccount;
use Braintree\Base;
class BusinessDetails extends Base
{
protected function _initialize($businessAttribs)
{
$this->_attributes = $businessAttribs;
if (isset($businessAttribs['address'])) {
$this->_set('addressDetails', new AddressDetails($businessAttribs['address']));
}
}
public static function factory($attributes)
{
$instance = new self();
$instance->_initialize($attributes);
return $instance;
}
}
class_alias('Braintree\MerchantAccount\BusinessDetails', 'Braintree_MerchantAccount_BusinessDetails');

View File

@@ -0,0 +1,10 @@
<?php
namespace Braintree\MerchantAccount;
use Braintree\Instance;
class FundingDetails extends Instance
{
protected $_attributes = [];
}
class_alias('Braintree\MerchantAccount\FundingDetails', 'Braintree_MerchantAccount_FundingDetails');

View File

@@ -0,0 +1,23 @@
<?php
namespace Braintree\MerchantAccount;
use Braintree\Base;
class IndividualDetails extends Base
{
protected function _initialize($individualAttribs)
{
$this->_attributes = $individualAttribs;
if (isset($individualAttribs['address'])) {
$this->_set('addressDetails', new AddressDetails($individualAttribs['address']));
}
}
public static function factory($attributes)
{
$instance = new self();
$instance->_initialize($attributes);
return $instance;
}
}
class_alias('Braintree\MerchantAccount\IndividualDetails', 'Braintree_MerchantAccount_IndividualDetails');

View File

@@ -0,0 +1,182 @@
<?php
namespace Braintree;
class MerchantAccountGateway
{
private $_gateway;
private $_config;
private $_http;
public function __construct($gateway)
{
$this->_gateway = $gateway;
$this->_config = $gateway->config;
$this->_config->assertHasAccessTokenOrKeys();
$this->_http = new Http($gateway->config);
}
public function create($attribs)
{
Util::verifyKeys(self::detectSignature($attribs), $attribs);
return $this->_doCreate('/merchant_accounts/create_via_api', ['merchant_account' => $attribs]);
}
public function find($merchant_account_id)
{
try {
$path = $this->_config->merchantPath() . '/merchant_accounts/' . $merchant_account_id;
$response = $this->_http->get($path);
return MerchantAccount::factory($response['merchantAccount']);
} catch (Exception\NotFound $e) {
throw new Exception\NotFound('merchant account with id ' . $merchant_account_id . ' not found');
}
}
public function update($merchant_account_id, $attributes)
{
Util::verifyKeys(self::updateSignature(), $attributes);
return $this->_doUpdate('/merchant_accounts/' . $merchant_account_id . '/update_via_api', ['merchant_account' => $attributes]);
}
public static function detectSignature($attribs)
{
if (isset($attribs['applicantDetails'])) {
trigger_error("DEPRECATED: Passing applicantDetails to create is deprecated. Please use individual, business, and funding", E_USER_NOTICE);
return self::createDeprecatedSignature();
} else {
return self::createSignature();
}
}
public static function updateSignature()
{
$signature = self::createSignature();
unset($signature['tosAccepted']);
return $signature;
}
public function createForCurrency($attribs)
{
$response = $this->_http->post($this->_config->merchantPath() . '/merchant_accounts/create_for_currency', ['merchant_account' => $attribs]);
return $this->_verifyGatewayResponse($response);
}
public function all()
{
$pager = [
'object' => $this,
'method' => 'fetchMerchantAccounts',
];
return new PaginatedCollection($pager);
}
public function fetchMerchantAccounts($page)
{
$response = $this->_http->get($this->_config->merchantPath() . '/merchant_accounts?page=' . $page);
$body = $response['merchantAccounts'];
$merchantAccounts = Util::extractattributeasarray($body, 'merchantAccount');
$totalItems = $body['totalItems'][0];
$pageSize = $body['pageSize'][0];
return new PaginatedResult($totalItems, $pageSize, $merchantAccounts);
}
public static function createSignature()
{
$addressSignature = ['streetAddress', 'postalCode', 'locality', 'region'];
$individualSignature = [
'firstName',
'lastName',
'email',
'phone',
'dateOfBirth',
'ssn',
['address' => $addressSignature]
];
$businessSignature = [
'dbaName',
'legalName',
'taxId',
['address' => $addressSignature]
];
$fundingSignature = [
'routingNumber',
'accountNumber',
'destination',
'email',
'mobilePhone',
'descriptor',
];
return [
'id',
'tosAccepted',
'masterMerchantAccountId',
['individual' => $individualSignature],
['funding' => $fundingSignature],
['business' => $businessSignature]
];
}
public static function createDeprecatedSignature()
{
$applicantDetailsAddressSignature = ['streetAddress', 'postalCode', 'locality', 'region'];
$applicantDetailsSignature = [
'companyName',
'firstName',
'lastName',
'email',
'phone',
'dateOfBirth',
'ssn',
'taxId',
'routingNumber',
'accountNumber',
['address' => $applicantDetailsAddressSignature]
];
return [
['applicantDetails' => $applicantDetailsSignature],
'id',
'tosAccepted',
'masterMerchantAccountId'
];
}
public function _doCreate($subPath, $params)
{
$fullPath = $this->_config->merchantPath() . $subPath;
$response = $this->_http->post($fullPath, $params);
return $this->_verifyGatewayResponse($response);
}
private function _doUpdate($subPath, $params)
{
$fullPath = $this->_config->merchantPath() . $subPath;
$response = $this->_http->put($fullPath, $params);
return $this->_verifyGatewayResponse($response);
}
private function _verifyGatewayResponse($response)
{
if (isset($response['response'])) {
$response = $response['response'];
}
if (isset($response['merchantAccount'])) {
// return a populated instance of merchantAccount
return new Result\Successful(
MerchantAccount::factory($response['merchantAccount'])
);
} else if (isset($response['apiErrorResponse'])) {
return new Result\Error($response['apiErrorResponse']);
} else {
throw new Exception\Unexpected(
"Expected merchant account or apiErrorResponse"
);
}
}
}
class_alias('Braintree\MerchantAccountGateway', 'Braintree_MerchantAccountGateway');

View File

@@ -0,0 +1,42 @@
<?php
namespace Braintree;
class MerchantGateway
{
private $_gateway;
private $_config;
private $_http;
public function __construct($gateway)
{
$this->_gateway = $gateway;
$this->_config = $gateway->config;
$this->_config->assertHasClientCredentials();
$this->_http = new Http($gateway->config);
$this->_http->useClientCredentials();
}
public function create($attribs)
{
$response = $this->_http->post('/merchants/create_via_api', ['merchant' => $attribs]);
return $this->_verifyGatewayResponse($response);
}
private function _verifyGatewayResponse($response)
{
if (isset($response['response']['merchant'])) {
// return a populated instance of merchant
return new Result\Successful([
Merchant::factory($response['response']['merchant']),
OAuthCredentials::factory($response['response']['credentials']),
]);
} else if (isset($response['apiErrorResponse'])) {
return new Result\Error($response['apiErrorResponse']);
} else {
throw new Exception\Unexpected(
"Expected merchant or apiErrorResponse"
);
}
}
}
class_alias('Braintree\MerchantGateway', 'Braintree_MerchantGateway');

View File

@@ -0,0 +1,22 @@
<?php
namespace Braintree;
class Modification extends Base
{
protected function _initialize($attributes)
{
$this->_attributes = $attributes;
}
public static function factory($attributes)
{
$instance = new self();
$instance->_initialize($attributes);
return $instance;
}
public function __toString() {
return get_called_class() . '[' . Util::attributesToString($this->_attributes) . ']';
}
}
class_alias('Braintree\Modification', 'Braintree_Modification');

View File

@@ -0,0 +1,41 @@
<?php
namespace Braintree;
use InvalidArgumentException;
class MultipleValueNode
{
public function __construct($name, $allowedValues = [])
{
$this->name = $name;
$this->items = [];
$this->allowedValues = $allowedValues;
}
public function in($values)
{
$bad_values = array_diff($values, $this->allowedValues);
if (count($this->allowedValues) > 0 && count($bad_values) > 0) {
$message = 'Invalid argument(s) for ' . $this->name . ':';
foreach ($bad_values AS $bad_value) {
$message .= ' ' . $bad_value;
}
throw new InvalidArgumentException($message);
}
$this->items = $values;
return $this;
}
public function is($value)
{
return $this->in([$value]);
}
public function toParam()
{
return $this->items;
}
}
class_alias('Braintree\MultipleValueNode', 'Braintree_MultipleValueNode');

View File

@@ -0,0 +1,47 @@
<?php
namespace Braintree;
class MultipleValueOrTextNode extends MultipleValueNode
{
public function __construct($name)
{
parent::__construct($name);
$this->textNode = new TextNode($name);
}
public function contains($value)
{
$this->textNode->contains($value);
return $this;
}
public function endsWith($value)
{
$this->textNode->endsWith($value);
return $this;
}
public function is($value)
{
$this->textNode->is($value);
return $this;
}
public function isNot($value)
{
$this->textNode->isNot($value);
return $this;
}
public function startsWith($value)
{
$this->textNode->startsWith($value);
return $this;
}
public function toParam()
{
return array_merge(parent::toParam(), $this->textNode->toParam());
}
}
class_alias('Braintree\MultipleValueOrTextNode', 'Braintree_MultipleValueOrTextNode');

Some files were not shown because too many files have changed in this diff Show More