1
0
mirror of https://github.com/invoiceninja/invoiceninja.git synced 2024-11-13 22:54:25 +01:00
invoiceninja/app/PaymentDrivers/PayPalExpressPaymentDriver.php

250 lines
7.9 KiB
PHP
Raw Normal View History

2019-09-26 07:14:07 +02:00
<?php
2019-09-26 07:14:07 +02:00
/**
* Invoice Ninja (https://invoiceninja.com).
2019-09-26 07:14:07 +02:00
*
* @link https://github.com/invoiceninja/invoiceninja source repository
*
2024-04-12 06:15:41 +02:00
* @copyright Copyright (c) 2024. Invoice Ninja LLC (https://invoiceninja.com)
2019-09-26 07:14:07 +02:00
*
2021-06-16 08:58:16 +02:00
* @license https://www.elastic.co/licensing/elastic-license
2019-09-26 07:14:07 +02:00
*/
namespace App\PaymentDrivers;
2020-11-26 16:36:43 +01:00
use App\Exceptions\PaymentFailed;
use App\Jobs\Util\SystemLogger;
2019-09-26 07:14:07 +02:00
use App\Models\GatewayType;
2020-11-26 16:36:43 +01:00
use App\Models\Invoice;
2019-10-01 03:56:48 +02:00
use App\Models\PaymentType;
use App\Models\SystemLog;
2019-09-26 07:14:07 +02:00
use App\Utils\Traits\MakesHash;
2019-09-30 01:26:37 +02:00
use Omnipay\Common\Item;
2020-11-26 16:36:43 +01:00
use Omnipay\Omnipay;
class PayPalExpressPaymentDriver extends BaseDriver
2019-09-26 07:14:07 +02:00
{
use MakesHash;
2019-09-26 07:14:07 +02:00
2020-11-26 16:36:43 +01:00
public $token_billing = false;
2019-09-26 07:14:07 +02:00
2020-11-26 16:36:43 +01:00
public $can_authorise_credit_card = false;
2019-09-26 07:14:07 +02:00
2020-11-26 16:36:43 +01:00
private $omnipay_gateway;
2019-09-26 07:14:07 +02:00
2022-04-15 01:51:39 +02:00
private float $fee = 0;
2024-01-14 05:05:00 +01:00
public const SYSTEM_LOG_TYPE = SystemLog::TYPE_PAYPAL;
2019-09-26 07:14:07 +02:00
public function gatewayTypes()
{
return [
GatewayType::PAYPAL,
];
}
2022-11-09 21:55:40 +01:00
public function init()
{
return $this;
}
2020-11-26 16:36:43 +01:00
/**
* Initialize Omnipay PayPal_Express gateway.
2020-11-27 11:12:05 +01:00
*
* @return void
2020-11-26 16:36:43 +01:00
*/
private function initializeOmnipayGateway(): void
{
2020-11-26 16:36:43 +01:00
$this->omnipay_gateway = Omnipay::create(
$this->company_gateway->gateway->provider
);
2020-11-26 16:36:43 +01:00
$this->omnipay_gateway->initialize((array) $this->company_gateway->getConfig());
}
2020-11-26 16:36:43 +01:00
public function setPaymentMethod($payment_method_id)
{
2020-11-27 11:12:05 +01:00
// PayPal doesn't have multiple ways of paying.
2020-11-26 16:36:43 +01:00
// There's just one, off-site redirect.
2020-11-26 16:36:43 +01:00
return $this;
}
2020-11-26 16:36:43 +01:00
public function authorizeView($payment_method)
{
// PayPal doesn't support direct authorization.
return $this;
}
2020-11-26 16:36:43 +01:00
public function authorizeResponse($request)
{
2020-11-26 16:36:43 +01:00
// PayPal doesn't support direct authorization.
2020-11-26 16:36:43 +01:00
return $this;
}
2020-11-26 16:36:43 +01:00
public function processPaymentView($data)
2019-09-26 07:14:07 +02:00
{
2020-11-26 16:36:43 +01:00
$this->initializeOmnipayGateway();
2020-12-21 12:10:47 +01:00
$this->payment_hash->data = array_merge((array) $this->payment_hash->data, ['amount' => $data['total']['amount_with_fee']]);
2020-11-26 16:36:43 +01:00
$this->payment_hash->save();
2020-11-26 16:36:43 +01:00
$response = $this->omnipay_gateway
->purchase($this->generatePaymentDetails($data))
->setItems($this->generatePaymentItems($data))
->send();
2019-10-02 00:44:13 +02:00
if ($response->isRedirect()) {
2020-11-26 16:36:43 +01:00
return $response->redirect();
}
2019-10-02 00:44:13 +02:00
// $this->sendFailureMail($response->getMessage() ?: '');
2019-10-02 00:44:13 +02:00
2020-11-26 16:36:43 +01:00
$message = [
'server_response' => $response->getMessage(),
2021-06-09 04:24:32 +02:00
'data' => $this->payment_hash->data,
2020-11-26 16:36:43 +01:00
];
2019-09-26 07:14:07 +02:00
2020-11-26 16:36:43 +01:00
SystemLogger::dispatch(
$message,
SystemLog::CATEGORY_GATEWAY_RESPONSE,
SystemLog::EVENT_GATEWAY_FAILURE,
SystemLog::TYPE_PAYPAL,
$this->client,
$this->client->company,
2020-11-26 16:36:43 +01:00
);
2020-11-26 16:36:43 +01:00
throw new PaymentFailed($response->getMessage(), $response->getCode());
}
2019-09-26 07:14:07 +02:00
public function processPaymentResponse($request)
{
2020-11-26 16:36:43 +01:00
$this->initializeOmnipayGateway();
2019-10-01 03:56:48 +02:00
2020-11-26 16:36:43 +01:00
$response = $this->omnipay_gateway
2021-05-24 13:11:47 +02:00
->completePurchase(['amount' => $this->payment_hash->data->amount, 'currency' => $this->client->getCurrencyCode()])
2020-11-26 16:36:43 +01:00
->send();
2019-09-30 03:15:57 +02:00
if ($response->isCancelled() && $this->client->getSetting('enable_client_portal')) {
2020-07-06 13:22:36 +02:00
return redirect()->route('client.invoices.index')->with('warning', ctrans('texts.status_cancelled'));
2023-10-26 04:57:44 +02:00
} elseif($response->isCancelled() && !$this->client->getSetting('enable_client_portal')) {
redirect()->route('client.invoices.show', ['invoice' => $this->payment_hash->fee_invoice])->with('warning', ctrans('texts.status_cancelled'));
}
2020-11-26 16:36:43 +01:00
if ($response->isSuccessful()) {
$data = [
'payment_method' => $response->getData()['TOKEN'],
'payment_type' => PaymentType::PAYPAL,
'amount' => $this->payment_hash->data->amount,
'transaction_reference' => $response->getTransactionReference(),
2021-01-27 11:38:28 +01:00
'gateway_type_id' => GatewayType::PAYPAL,
2020-11-26 16:36:43 +01:00
];
$payment = $this->createPayment($data, \App\Models\Payment::STATUS_COMPLETED);
SystemLogger::dispatch(
['response' => (array) $response->getData(), 'data' => $data],
SystemLog::CATEGORY_GATEWAY_RESPONSE,
SystemLog::EVENT_GATEWAY_SUCCESS,
SystemLog::TYPE_PAYPAL,
$this->client,
$this->client->company,
);
2020-11-26 16:36:43 +01:00
return redirect()->route('client.payments.show', ['payment' => $this->encodePrimaryKey($payment->id)]);
}
if (! $response->isSuccessful()) {
$data = $response->getData();
2021-11-18 01:19:22 +01:00
$this->sendFailureMail($response->getMessage() ?: '');
2020-11-26 16:36:43 +01:00
$message = [
'server_response' => $data['L_LONGMESSAGE0'],
2020-11-26 16:36:43 +01:00
'data' => $this->payment_hash->data,
];
SystemLogger::dispatch(
2020-11-26 16:36:43 +01:00
$message,
SystemLog::CATEGORY_GATEWAY_RESPONSE,
SystemLog::EVENT_GATEWAY_FAILURE,
SystemLog::TYPE_PAYPAL,
$this->client,
$this->client->company,
);
2019-10-02 00:44:13 +02:00
2020-11-26 16:36:43 +01:00
throw new PaymentFailed($response->getMessage(), $response->getCode());
2019-09-30 01:26:37 +02:00
}
2019-09-29 23:49:43 +02:00
}
2019-09-30 01:26:37 +02:00
2020-11-26 16:36:43 +01:00
public function generatePaymentDetails(array $data)
2019-09-30 01:26:37 +02:00
{
2022-04-15 01:51:39 +02:00
$_invoice = collect($this->payment_hash->data->invoices)->first();
$invoice = Invoice::withTrashed()->find($this->decodePrimaryKey($_invoice->invoice_id));
2022-05-18 12:30:57 +02:00
// $this->fee = $this->feeCalc($invoice, $data['total']['amount_with_fee']);
2022-04-15 01:51:39 +02:00
2020-11-26 16:36:43 +01:00
return [
'currency' => $this->client->getCurrencyCode(),
'transactionType' => 'Purchase',
'clientIp' => request()->getClientIp(),
2022-05-10 01:20:25 +02:00
// 'amount' => round(($data['total']['amount_with_fee'] + $this->fee),2),
'amount' => round($data['total']['amount_with_fee'], 2),
2020-11-26 16:36:43 +01:00
'returnUrl' => route('client.payments.response', [
'company_gateway_id' => $this->company_gateway->id,
'payment_hash' => $this->payment_hash->hash,
'payment_method_id' => GatewayType::PAYPAL,
]),
'cancelUrl' => $this->client->company->domain()."/client/invoices/{$invoice->hashed_id}",
2020-11-26 16:36:43 +01:00
'description' => implode(',', collect($this->payment_hash->data->invoices)
->map(function ($invoice) {
2021-06-08 02:29:43 +02:00
return sprintf('%s: %s', ctrans('texts.invoice_number'), $invoice->invoice_number);
2020-11-26 16:36:43 +01:00
})->toArray()),
'transactionId' => $this->payment_hash->hash.'-'.time(),
2020-11-26 16:36:43 +01:00
'ButtonSource' => 'InvoiceNinja_SP',
'solutionType' => 'Sole',
2023-09-27 00:51:33 +02:00
'no_shipping' => $this->company_gateway->require_shipping_address ? 0 : 1,
2020-11-26 16:36:43 +01:00
];
2019-09-30 01:26:37 +02:00
}
2020-11-26 16:36:43 +01:00
public function generatePaymentItems(array $data)
2019-09-30 01:26:37 +02:00
{
$_invoice = collect($this->payment_hash->data->invoices)->first();
$invoice = Invoice::withTrashed()->find($this->decodePrimaryKey($_invoice->invoice_id));
$items = [];
$items[] = new Item([
'name' => ' ',
'description' => ctrans('texts.invoice_number').'# '.$invoice->number,
'price' => $data['total']['amount_with_fee'],
'quantity' => 1,
]);
2019-09-30 01:26:37 +02:00
return $items;
}
2022-04-15 01:51:39 +02:00
private function feeCalc($invoice, $invoice_total)
{
$invoice->service()->removeUnpaidGatewayFees();
$invoice = $invoice->fresh();
2022-04-15 01:51:39 +02:00
$balance = floatval($invoice->balance);
$_updated_invoice = $invoice->service()->addGatewayFee($this->company_gateway, GatewayType::PAYPAL, $invoice_total)->save();
if (floatval($_updated_invoice->balance) > $balance) {
2022-04-15 01:51:39 +02:00
$fee = floatval($_updated_invoice->balance) - $balance;
$this->payment_hash->fee_total = $fee;
$this->payment_hash->save();
return $fee;
}
return 0;
}
}