3
votes

I am using the REST API in PHP to try and create a PayPal purchase, but I only get a generic 400 error whenever I run it. Apparently this means bad request, but there are barely any details given. Here is the main portion of my code:

define("PP_CONFIG_PATH", "../vendor/");

$apiContext = new ApiContext(new OAuthTokenCredential('-redacted-', '-redacted-')); // id, secret

$addr = new Address();
$addr->setLine1($_POST['addr1']);
if(isset($_POST['addr2']) && !empty($_POST['addr2'])) $addr->setLine2($_POST['addr2']);
$addr->setCity($_POST['city']);
$addr->setCountry_code($_POST['country']);
$addr->setPostal_code($_POST['zip']);
$addr->setState($_POST['state']);
$addr->setPhone('9179261285'); // TODO put in actual phone

$card = new CreditCard();
$card->setNumber($_POST['card_num']);
$card->setExpire_month($_POST['expire_mon']);
$card->setExpire_year($_POST['expire_yr']);
$card->setCvv2($_POST['cvv2']);
$card->setFirst_name($_GET['fname']);
$card->setLast_name($_GET['lname']);
$card->setBilling_address($addr);

$fi = new FundingInstrument();
$fi->setCredit_card($card);

$payer = new Payer();
$payer->setPayment_method('credit_card');
$payer->setFunding_instruments(array($fi));

$cost = $_POST['plan'] == 1 ? '19.95' : '29.95';

$amountDetails = new AmountDetails();
$amountDetails->setSubtotal($cost);
$amountDetails->setTax('0.00');
$amountDetails->setShipping('0.00');

$amount = new Amount();
$amount->setCurrency('USD');
$amount->setTotal($cost);
$amount->setDetails($amountDetails);

$transaction = new Transaction();
$transaction->setAmount($amount);
$transaction->setDescription('MyTrustCo membership subscription.');

$payment = new Payment();
$payment->setIntent('sale');
$payment->setPayer($payer);
$payment->setTransactions(array($transaction));

try {
    $response = $payment->create($apiContext);
} catch (PPConnectionException $e) {
    echo "<br />exception:<br />" . $e->getMessage() . "<br />";
}

echo "response: " . $response;
die();

The last part of the code outputs:

exception:
Got Http response code 400 when accessing https://api.sandbox.paypal.com/v1/payments/payment.
got response
response:

I have no idea what could be causing this error. I was following this tutorial: https://developer.paypal.com/webapps/developer/docs/api/#create-a-payment

1
Sure, if you can tell me what a sample dump is and how to get one. - Greg
He did provide a dump in the output. I have the same error but it's a 404 instead, and that's the only thing that gets returned. - cj5
Having the same problem myself at present (getting 400 response). Anybody uncovered the cause of this? - John Rix
My ultimate solution was to switch to Braintree (braintreepayments.com). Rates are similar to Paypal, and you can control every part of the payment process. Also, as a developer, setting it up was a breeze. I highly recommend it. Best of luck! - Greg
As it happens, I'll be working on that integration next! Am working on a system involving multiple payment provider integrations. They definitely look easier to deal with than PayPal from what I've seen so far. Also looking at Stripe, which is very similar to Braintree in terms of APIs I think. - John Rix

1 Answers

2
votes

I was having the same problem but ultimately uncovered the root cause by capturing Exception instead of PPConnectionException (as per the SDK sample code which fooled both of us). Once I did this, I was able to dump the exception details which revealed that PayPal was complaining that my transaction amount was not formatted correctly - I only had a single digit after the decimal point. Looking at your code above, this is not likely to be the case, but changing the exception handler should reveal the real problem quickly.

You may also be susceptible to the formatting problem for other values though in future, which you can resolve with the following:

money_format('%!i', $amount)