Skip to content

Commit

Permalink
Support PayPay ItemBag/Cart/Basket contents.
Browse files Browse the repository at this point in the history
  • Loading branch information
judgej committed Apr 14, 2018
1 parent 9bf5501 commit 2344b58
Show file tree
Hide file tree
Showing 2 changed files with 112 additions and 15 deletions.
30 changes: 24 additions & 6 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -38,8 +38,9 @@ Table of Contents
* [iframe Mode/Inline Mode](#iframe-modeinline-mode)
* [Lightbox Mode](#lightbox-mode)
* [Hidden Mode](#hidden-mode)
* [ItemBag/Basket](#itembagbasket)
* [TODO](#todo)
* [Shared Optional Parameters](#shared-optional-parameters)
* [Additional Parameters (for various payment methods)](#additional-parameters-for-various-payment-methods)
* [Functionality](#functionality)

This Gateway implements offsite payments via Datatrans.
Expand Down Expand Up @@ -167,6 +168,13 @@ They can be set in the `purchase()` parameter array, or via setters `setParamNam
If signing is configured in the account, then the shared key must be provided here.
* `hmacKey2` - alternative HMAC key used to sign inbound messages.
If not set, will default to the value of hmacKey1.
* A `cardReference` and optional expiry dates (in the `CreditCard` object, if the
`cardReference` is for a credit card) can be supplied. This will pre-populate the
card details for the user, so that they need only enter their CVV to authorize
a payment.
* Many other optional parameters are supported, generally all those in the official
documentaion except where listed in the TODO section here. These will be added as
time permits.

## Complete Response

Expand Down Expand Up @@ -206,7 +214,7 @@ used for responses as for the original request).
$notify->send();
```

This will return $notify, but will throw an exception if the signing checks fail.
This will return `$notify`, but will throw an exception if the signing checks fail.

## Void

Expand Down Expand Up @@ -343,12 +351,22 @@ TBC
This mode requires credit card details to be passed through your merchant application.
It is not supported by this release of the driver drue to the PCI requirements involved.

## ItemBag/Basket

The standard Omnipay Itembag is supported for the PayPal (PAP) mayment method.
Some notes, since the ItemBag can be inflexible and a little ambiguous:

* The `price` of each item is assumed to be the gross unit price.
* The `price` units are considered minor units if an integer (e.g. 123 or "123")
or major units if a floating point number (e.g. 4.56 or "4.56").
* Shipping is set to zero.
* Tax is set to zero.
* The total `ItemBag` amount *must* equal the total order amount.

## TODO

### Shared Optional Parameters
### Additional Parameters (for various payment methods)

* Basket details (PayPal only?)
* PayPal specific parameters
* Payolution mandatory parameters validation
* Aduno surprize specific parameters
* Migros Bank Payment mdpUserId and mdpAlias parameter + txnMbRefNo return param
Expand All @@ -366,9 +384,9 @@ It is not supported by this release of the driver drue to the PCI requirements i

### Functionality

* Additional parameters and results for different payment PAYMENT_METHOD
* Capture of customer address when using PayPal
* Support lightbox mode (iframe)
* Support inline mode (JavaScript)
* AVS (address verification) by web interface and XML back-end
* Tests needed especially around the multiple notification methods and formats.

97 changes: 88 additions & 9 deletions src/Message/AbstractRedirectRequest.php
Original file line number Diff line number Diff line change
Expand Up @@ -237,7 +237,7 @@ public function getData()
/**
* Populate the data array with any customer details supplied in the card.
*/
public function getCustomerData(array $data)
public function getCustomerData(array $data = [])
{
if (! $card = $this->getCard()) {
return $data;
Expand Down Expand Up @@ -323,7 +323,7 @@ public function getCustomerData(array $data)
/**
* Additional parameters for PayPal (PAP).
*/
protected function extraParamsPAP(array $data)
protected function extraParamsPAP(array $data = [])
{
// TODO: basket details (MUST add up correctly)

Expand Down Expand Up @@ -355,29 +355,108 @@ protected function extraParamsPAP(array $data)
$data['PayPalOrderId'] = 'get';
}

// Add the basket to PayPal.

$data = $this->getPapBasket($data);

return $data;
}

/**
* Get the basket/card/items into a PayPal format.
* @param array $data
* @return array The data with the ItemBag added if set.
*/
public function getPapBasket(array $data = [])
{
if (empty($this->getItems())) {
return $data;
}

// Some running totals need to be maintained.
// Amounts are sent to PayPal as minor units.
// The standard Omnipay Item does not support separate tax or shipping values,
// and these will be defaulted to zero when an extended basket is not used.

$itemsAmount = 0;
$taxAmount = 0;
$shippingAmount = 0;

$itemData = [];
$itemNumber = 0;

foreach ($this->getItems() as $item) {
$itemPrice = $this->priceMinorUnit($item->getPrice());
$itemQuantity = $item->getQuantity();

$itemData['L_NAME' . $itemNumber] = $item->getName();
$itemData['L_AMT' . $itemNumber] = $itemPrice;
$itemData['L_Number' . $itemNumber] = $itemNumber + 1;
$itemData['L_Desc' . $itemNumber] = $item->getDescription();
$itemData['L_QTY' . $itemNumber] = $itemQuantity;
$itemData['L_TAXAMT' . $itemNumber] = 0;

$itemsAmount += $itemPrice * $itemQuantity;

$itemNumber++;
}

$data['ITEMAMT'] = $itemsAmount;
$data['TAXAMT'] = $taxAmount;
$data['SHIPPINGAMT'] = $shippingAmount;

$data = array_merge($data, $itemData);

return $data;
}

/**
* Convert an Item price to minor units
* @param mixed $price
* @return int
*/
protected function priceMinorUnit($price)
{
if ($price instanceof Money) {
// Money::EUR(123)
return (int)$price->getAmount();
} elseif (is_int($price)) {
// 123
return $price;
} elseif (is_float($price)) {
// 1.23
return (int)($price * 100); // Horrible hack! Needs to take currency into account.
} elseif (is_string($price) && strpos($price, '.') !== false) {
// '1.23'
return (int)((float)$price * 100); // Horrible hack!
} elseif (is_string($price)) {
// '123'
return (int)$price;
}

return 0;
}

/**
* Additional parameters for Swiss PostFinance E-Finance (PEF).
*/
protected function extraParamsPEF(array $data)
protected function extraParamsPEF(array $data = [])
{
return $data;
}

/**
* Additional parameters for Swiss PostFinance Card (PFC).
*/
protected function extraParamsPFC(array $data)
protected function extraParamsPFC(array $data = [])
{
return $data;
}

/**
* Additional parameters for MFGroup Check Out (Credit Check) (MFA).
*/
protected function extraParamsMFA(array $data)
protected function extraParamsMFA(array $data = [])
{
if ($this->getMfaReference()) {
$data['mfaReference'] = $this->getMfaReference();
Expand All @@ -389,7 +468,7 @@ protected function extraParamsMFA(array $data)
/**
* Additional parameters for Curabill (CUR).
*/
protected function extraParamsCUR(array $data)
protected function extraParamsCUR(array $data = [])
{
// The XML document is base64 encoded before sending.

Expand All @@ -405,7 +484,7 @@ protected function extraParamsCUR(array $data)
* TODO: uppCustomerAirlineDeparture uppCustomerAirlineRoute uppCustomerAirlineFlightNumber
* uppCustomerAirlineBookingCode uppCustomerAirlineFrequentFlyer
*/
protected function extraParamsPYO(array $data)
protected function extraParamsPYO(array $data = [])
{
// TODO: plus most customer details are also mandatory.
$this->validate('customerType');
Expand All @@ -418,7 +497,7 @@ protected function extraParamsPYO(array $data)
/**
* Additional parameters for SEPA Direct Debit / ELV (ELV).
*/
protected function extraParamsELV(array $data)
protected function extraParamsELV(array $data = [])
{
if ($this->getRefno2()) {
$data['refno2'] = $this->getRefno2();
Expand All @@ -444,7 +523,7 @@ protected function extraParamsELV(array $data)
* Additional parameters for MFGroup Financial Request (authorization) (MFG).
* TODO: about a dozen more parameters, but the documentation is a little unclear.
*/
protected function extraParamsMFG(array $data)
protected function extraParamsMFG(array $data = [])
{
if ($this->getVirtualCardno()) {
$data['virtualCardno'] = $this->getVirtualCardno();
Expand Down

0 comments on commit 2344b58

Please sign in to comment.