Source for file SOAP.php
Documentation is available at SOAP.php
/* vim: set expandtab tabstop=4 shiftwidth=4 softtabstop=4: */
* Payment_PayPal_SOAP is a package to easily use PayPal's SOAP API from PHP
* By itself, this package isn't very useful. It should be used in combination
* with the documentation provided by PayPal at
* {@link https://www.paypal.com/en_US/pdf/PP_APIReference.pdf}. This package
* makes it easier to get up and running, and allows you to begin integration
* by making requests rather than by figuring out how to set SOAP
* authentication headers.
* Copyright (c) 2008-2011 silverorange
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* @package Payment_PayPal_SOAP
* @author Michael Gauthier <mike@silverorange.com>
* @copyright 2008-2009 silverorange
* @license http://www.opensource.org/licenses/mit-license.html MIT License
* @link http://pear.php.net/package/Payment_PayPal_SOAP
* @link https://www.paypal.com/en_US/pdf/PP_APIReference.pdf
* Package-specific exceptions classes.
require_once 'Payment/PayPal/SOAP/Exceptions.php';
* An easy to use SOAP client for the PayPal SOAP API
* By itself, this class isn't very useful. It should be used in combination
* with the documentation provided by PayPal at
* {@link https://www.paypal.com/en_US/pdf/PP_APIReference.pdf}. This class
* makes it easier to get up and running, and allows you to begin integration by
* making requests rather than by figuring out how to set SOAP authentication
* @package Payment_PayPal_SOAP
* @author Michael Gauthier <mike@silverorange.com>
* @copyright 2008-2011 silverorange
* @license http://www.opensource.org/licenses/mit-license.html MIT License
* @link http://pear.php.net/package/Payment_PayPal_SOAP
* Warning or informational error.
* Application-level error.
* Unknown error type reserved for future internal use by PayPal
// {{{ protected properties
* SOAP client used to make PayPal SOAP requests
* @see Payment_PayPal_SOAP::getSoapClient()
* SOAP header values specific to PayPal SOAP API
* This contains PayPal authentication values.
* @see Payment_PayPal_SOAP::getSoapHeaders()
* Options passed to the SOAP client when it is created
* PayPal's SOAP implementation uses SOAP 1.1 so the SOAP version option
* is specified by default. If using local certificates for authentication,
* the local certificate file is also included in these options.
* The API endpoint location is also specified in these options as the
* endpoint in the WSDL file is not always correct depending on the
* authentication mechanism used.
* @see Payment_PayPal_SOAP::setCertificateFile()
* @see Payment_PayPal_SOAP::__construct()
'soap_version' => SOAP_1_1
* Whether or not to use a local copy of the PayPal WSDL
* If true, a local copy of the PayPal WSDL is used instead of the copy
* hosted on PayPal's servers. This can be used if PayPal breaks the hosted
* WSDL files, as has happened in the past.
* @see Payment_PayPal_SOAP::__construct()
* @see Payment_PayPal_SOAP::getWsdlFile()
// {{{ private properties
* Mode to use for PayPal API
* - <kbd>sandbox</kbd> - for development and testing.
* - <kbd>live</kbd> - for processing live payments.
* @see Payment_PayPal_SOAP::__construct()
* @see Payment_PayPal_SOAP::setMode()
private $_mode = 'sandbox';
* @see Payment_PayPal_SOAP::__construct()
* @see Payment_PayPal_SOAP::setUsername()
* @see Payment_PayPal_SOAP::__construct()
* @see Payment_PayPal_SOAP::setPassword()
* Only set if using signature-based authentication instead of
* local-certificate-based authentication.
* @see Payment_PayPal_SOAP::__construct()
* @see Payment_PayPal_SOAP::setSignature()
private $_signature = '';
* PayPal subject used for making requests on behalf of a third-party
* This is the email address of the third-party the request should be made
* on behalf of. Your API username may require explicit access from the
* third-party before certain API actions will work.
* @see Payment_PayPal_SOAP::__construct()
* @see Payment_PayPal_SOAP::setSubject()
* API endpoints indexed by mode and security mode
* Certificate-based authentication uses a different API endpoint than
* signature (3 token)-based authentication.
* @see https://ppmts.custhelp.com/cgi-bin/ppdts.cfg/php/enduser/popup_adp.php?p_sid=undefined&p_lva=undefined&p_faqid=391&p_created=1169502818
static private $_apiEndpoints = array (
'certificate' => 'https://api.sandbox.paypal.com/2.0/',
'signature' => 'https://api-3t.sandbox.paypal.com/2.0/'
'certificate' => 'https://api.paypal.com/2.0/',
'signature' => 'https://api-3t.paypal.com/2.0/'
* Creates a new PayPal SOAP client
* Either signature-based or certificate-based authentication options
* are required. The username, password and optional signature fields may
* be retrieved from your PayPal account in the 'API Credentials' section.
* Sandbox and live modes require different PayPal accounts so all option
* values will require changing if you select a different mode.
* The available options are:
* - <kbd>mode</kbd> - optional. The mode to use for PayPal API
* calls. Valid modes are <kbd>sandbox</kbd>
* for development and testing, and
* <kbd>live</kbd> for live payments. If not
* specified, <em><kbd>sandbox</kbd></em> is
* - <kbd>username</kbd> - the username used for authentication.
* - <kbd>password</kbd> - the password used for authentication.
* - <kbd>subject</kbd> - optional. The third-party on whose behalf
* requests are to be made.
* - <kbd>signature</kbd> - optional. The signature used for signature-
* based authentication. Not required if
* certificate-based authentication is used.
* - <kbd>certificate</kbd> - optional. The local certificate filename used
* for certificate-based authentication. Not
* required if signature-based authentication is
* - <kbd>useLocalWsdl</kbd> - optional. When sepecified as true, a local
* copy of the PayPal WSDL is used instead of
* the copy hosted on PayPal's servers. This
* can be used if PayPal breaks the hosted
* WSDL files, as has happened in the past.
* @param array $options array of options.
* @throws InvalidArgumentException if neither a signature nor a
* certificate file is specified in the options array, or if the
* username or password options are not specified in the options
foreach ($options as $key => $value) {
throw new InvalidArgumentException ('A username is required.');
throw new InvalidArgumentException ('A password is required.');
if (!$hasSignature && !$hasCertificate) {
throw new InvalidArgumentException (
'Either a signature or a local certificate file is required.');
// set appropriate API endpoint
self ::$_apiEndpoints[$this->_mode ]['signature'];
self ::$_apiEndpoints[$this->_mode ]['certificate'];
* Makes a PayPal SOAP request
* If a structured array is used as the arguments, WSDL types with
* attributes may be specified as:
* 'OrderTotal' => array( // 'OrderTotal' is a type with attributes
* '_' => '1000.00', // this is the element value
* 'currencyID' => 'USD' // this is an attribute value
* @param string $requestName the name of the request. This should be a
* request documented in the PayPal SOAP API
* reference manual. Sending a request of an
* invalid type will cause a SoapFault to be
* @param mixed $arguments optional. Either a structured array or an
* object representing the SOAP request
* arguments. If the request requires no
* arguments, this parameter may be ommitted.
* @return mixed the PayPal SOAP response. If only one value is returned
* for the request, a simple value (e.g. an integer, a
* string, etc) is returned. For requests that return multiple
* values or complex types, a data structure composed of
* stdClass objects is returned.
* @throws Payment_PayPal_SOAP_InvalidRequestNameException if the specified
* request name is not a valid PayPal SOAP API request name.
* @throws Payment_PayPal_SOAP_MissingPropertyException if a required
* property for a request type is not specified in the request
* arguments. Refer to the PayPal SOAP API documentation at
* {@link https://www.paypal.com/en_US/pdf/PP_APIReference.pdf} for
* information about required fields.
* @throws Payment_PayPal_SOAP_ErrorException if a SOAP response contains
* one or more Error elements. A detailed error message will be
* present in the exception message and the PayPal error code will
* be in the exception code.
* @throws Payment_PayPal_SOAP_FaultException if a SOAP initialization
* error occurs or an unknown SOAP error occurs.
public function call($requestName, $arguments = array ())
// Use a unique client. If an exception is thrown, state will be
// preserved if subsequent requests are made.
$response = $client->__soapCall (
if (isset ($response->Errors )) {
$errors = $response->Errors;
$errors = array ($response->Errors );
foreach ($errors as $error) {
$message = (isset ($error->LongMessage ))
$code = intval($error->ErrorCode );
switch ($error->SeverityCode ) {
$expiredTokenExp = '/Token value is no longer valid\.$/';
if (preg_match($expiredTokenExp, $message) === 1 ) {
"Error(s) present in PayPal SOAP response: %s\n" .
foreach ($errorObjects as $error) {
$errorException->addError ($error);
$message = $e->getMessage ();
$badFunctionExp = '/^Function \(".*?"\) is not a valid method ' .
if (preg_match($badFunctionExp, $message) === 1 ) {
'Request name "' . $requestName . '" is not a valid ' .
'request name for the PayPal API.',
$e->getCode (), $requestName);
$badArgumentExp = '/^SOAP-ERROR: Encoding: object hasn\'t ' .
if (preg_match($badArgumentExp, $message, $matches) === 1 ) {
$propertyName = $matches[1 ];
'Arguments for "' . $requestName . '" request is missing ' .
'a "' . $propertyName . '" property. See the PayPal SOAP ' .
'API reference for details on required request properties.',
$e->getCode (), $propertyName);
// Unknown SOAP exception, pass it along.
$e->getMessage (), $e->getCode (), $e, $client);
* Gets the XML sent in the last SOAP request
* @return boolean|stringthe XML sent in the last SOAP request. If no
* request has been performed, false is returned.
* Gets the XML returned in the last SOAP response
* @return boolean|stringthe XML used in the last SOAP response. If no
* response has been retrieved, false is returned.
$response = $this->soapClient->__getLastResponse ();
* Gets the SOAP headers required for PayPal authentication
* If the header doesn't exist, it is created and stored in the protected
* property {@link PaymentPayPal_SOAP::$soapHeader}.
* This header is passed to all PayPal SOAP calls.
* @return SoapHeader the SOAP header required for PayPal authentication.
* @see Payment_PayPal_SOAP::call()
* @see Payment_PayPal_SOAP::setUsername()
* @see Payment_PayPal_SOAP::setPassword()
* @see Payment_PayPal_SOAP::setSubject()
* @see Payment_PayPal_SOAP::setSignature()
'Username' => $this->_username ,
'Password' => $this->_password
$credentials['Credentials']['Subject'] = $this->_subject;
$credentials['Credentials']['Signature'] = $this->_signature;
$this->soapHeader = new SoapHeader ('urn:ebay:api:PayPalAPI',
'RequesterCredentials', $credentials);
* Gets the SOAP client used to make PayPal SOAP calls
* If the client doesn't exist, it is created and stored in the protected
* property {@link PaymentPayPal_SOAP::$soapClient}.
* @return SoapClient the SOAP client used to make PayPal SOAP calls.
* @see Payment_PayPal_SOAP::call()
* @see Payment_PayPal_SOAP::setSoapClient()
* Sets a SOAP client to use for SOAP requests
* This is useful for testing.
* @param SoapClient $client the SOAP client to use.
* @return Payment_PayPal_SOAP the current object, for fluent interface.
* Sets the API username used for authentication
* @param string $username the API username used for authentication.
* @return Payment_PayPal_SOAP the current object, for fluent interface.
* @see Payment_PayPal_SOAP::__construct()
* @see Payment_PayPal_SOAP::$_username
$this->_username = strval($username);
* Sets the API password used for authentication
* @param string $password the API password used for authentication.
* @return Payment_PayPal_SOAP the current object, for fluent interface.
* @see Payment_PayPal_SOAP::__construct()
* @see Payment_PayPal_SOAP::$_password
$this->_password = strval($password);
* Sets the API signature used for signature-based authentication
* @param string $signature the API signature used for signature-based
* @return Payment_PayPal_SOAP the current object, for fluent interface.
* @see Payment_PayPal_SOAP::__construct()
* @see Payment_PayPal_SOAP::$_signature
$this->_signature = strval($signature);
* Sets the subject used for making requests on behalf of a third-party
* For example, you may be running a marketplace where customers will
* purchase goods directlry from your clients through your market. In this
* case, you can use the client's PayPal email address as the subject to
* initiate a checkout for the customer in your marketplace.
* @param string $subject the email address of the third-party. Your API
* username may require explicit access be granted
* from the third-party before certain API actions
* @return Payment_PayPal_SOAP the current object, for fluent interface.
* @see Payment_PayPal_SOAP::__construct()
* @see Payment_PayPal_SOAP::$_subject
$this->_subject = strval($subject);
// {{{ setCertificateFile()
* Sets the local certificate file used for certificate-based
* This file is downloaded from your API credentials page when logged into
* @param string $certificateFile the local certificate file used for
* certificate-based authentication.
* @return Payment_PayPal_SOAP the current object, for fluent interface.
* @see Payment_PayPal_SOAP::__construct()
* @see Payment_PayPal_SOAP::$soapOptions
$certificateFile = strval($certificateFile);
* Sets the mode to use for API calls
* @param string $mode the mode to use for PayPal API calls. Valid modes
* - <kbd>sandbox</kbd> - for development and testing
* - <kbd>live</kbd> - for live payments.
* @return Payment_PayPal_SOAP the current object, for fluent interface.
* @throws Payment_PayPal_SOAP_InvalidModeException if an invalid mode is
* @see Payment_PayPal_SOAP::__construct()
$validModes = array ('sandbox', 'live');
'Mode "' . $mode . '" is invalid. Mode must be either ' .
'"sandbox" or "live".', 0 , $mode);
* Gets the WSDL file to use when building the SOAP object
* @return string the WSDL file to use when building the SOAP object.
$path = '@data-dir@/Payment_PayPal_SOAP/data/wsdl';
if (substr($path, 0 , 1 ) === '@') {
$path = dirname(__FILE__ ) . '/../../data/wsdl';
$file = $path . '/live/PayPalSvc.wsdl';
$file = $path . '/sandbox/PayPalSvc.wsdl';
$file = 'https://www.paypal.com/wsdl/PayPalSvc.wsdl';
$file = 'https://www.sandbox.paypal.com/wsdl/PayPalSvc.wsdl';
Documentation generated on Tue, 25 Sep 2012 14:30:04 +0000 by phpDocumentor 1.4.3. PEAR Logo Copyright © PHP Group 2004.
|