Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add support for inline apple pay #111

Merged
merged 3 commits into from
Dec 16, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ test-results/
playwright-report/
hyva/
.idea/
nohup.out

vendor/
.env
11 changes: 10 additions & 1 deletion src/Magewire/Checkout/Payment/AbstractProcessor.php
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,12 @@ abstract class AbstractProcessor extends Component
/** @var array */
public $parameters = [];

/** @var string */
public $quoteCurrency = 'GBP';

/** @var string */
public $quoteAmount = '0';

/**
* @param SerializerInterface $serializer
* @param Assets $assetsModel
Expand All @@ -55,9 +61,12 @@ public function __construct(
$this->sdkProxy = $sdkProxy;
}

public function mount(): void

public function boot(): void
{
$this->parameters = $this->serializer->unserialize($this->assetsModel->getRvvupParametersJsObject());
$this->quoteAmount = $this->checkoutSession->getQuote()->getGrandTotal();
$this->quoteCurrency = $this->checkoutSession->getQuote()->getQuoteCurrencyCode();
}

abstract function getMethodCode(): string;
Expand Down
79 changes: 79 additions & 0 deletions src/Magewire/Checkout/Payment/ApplePayProcessor.php
Original file line number Diff line number Diff line change
Expand Up @@ -4,17 +4,96 @@

namespace Rvvup\PaymentsHyvaCheckout\Magewire\Checkout\Payment;

use Magento\Checkout\Model\Session;
use Magento\Framework\Serialize\SerializerInterface;
use Magento\Framework\UrlFactory;
use Rvvup\Payments\Controller\Redirect\In;
use Rvvup\Payments\Model\SdkProxy;
use Rvvup\Payments\Service\PaymentSessionService;
use Rvvup\Payments\ViewModel\Assets;
use Rvvup\PaymentsHyvaCheckout\Service\GetPaymentActions;

class ApplePayProcessor extends AbstractProcessor
{
protected $listeners = [
'shipping_method_selected' => 'refresh',
'coupon_code_applied' => 'refresh',
'coupon_code_revoked' => 'refresh'
];

/** @var PaymentSessionService */
private $paymentSessionService;

/** @var UrlFactory */
private $urlFactory;

/** @var array */
public $paymentSessionResult;

/**
* @param SerializerInterface $serializer
* @param Assets $assetsModel
* @param GetPaymentActions $getPaymentActions
* @param Session $checkoutSession
* @param SdkProxy $sdkProxy
* @param PaymentSessionService $paymentSessionService
* @param UrlFactory $urlFactory
*/
public function __construct(
SerializerInterface $serializer,
Assets $assetsModel,
GetPaymentActions $getPaymentActions,
Session $checkoutSession,
SdkProxy $sdkProxy,
PaymentSessionService $paymentSessionService,
UrlFactory $urlFactory
) {
parent::__construct($serializer, $assetsModel, $getPaymentActions, $checkoutSession, $sdkProxy);
$this->paymentSessionService = $paymentSessionService;
$this->urlFactory = $urlFactory;
}

public $hydrated = false;

public function getMethodCode(): string
{
return 'rvvup_APPLE_PAY';
}
public function boot(): void
{
parent::boot();

if ($this->showInline()) {
$this->switchTemplate('Rvvup_PaymentsHyvaCheckout::component/payment/apple-pay-inline-processor.phtml');
}
}

public function placeOrder(): void
{
$this->loadPaymentActions();
$redirectUrl = $this->getRedirectUrl();
$this->redirect($redirectUrl);
}

/**
* @return bool
*/
public function showInline(): bool
{
if (isset($this->parameters['settings']['apple_pay']['applePayFlow'])) {
return $this->parameters['settings']['apple_pay']['applePayFlow'] == 'INLINE';
}
return false;
}

public function createPaymentSession(string $checkoutId): void
{
$quote = $this->checkoutSession->getQuote();

$paymentSession = $this->paymentSessionService->create($quote, $checkoutId);

$url = $this->urlFactory->create();
$url->setQueryParam(In::PARAM_RVVUP_ORDER_ID, $paymentSession["id"]);
$this->paymentSessionResult = ["paymentSessionId" => $paymentSession["id"], "redirectUrl" => $url->getUrl('rvvup/redirect/in')];
}
}
2 changes: 1 addition & 1 deletion src/view/frontend/layout/hyva_checkout_index_index.xml
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,7 @@

<block name="checkout.payment.method.rvvup.apple-pay-processor"
as="rvvup.apple-pay-processor"
template="Rvvup_PaymentsHyvaCheckout::component/payment/apple-pay-processor.phtml"
template="Rvvup_PaymentsHyvaCheckout::component/payment/apple-pay-hosted-processor.phtml"
after="hyva.checkout.main">
<arguments>
<argument name="magewire" xsi:type="object">
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
<?php
declare(strict_types=1);

use Magento\Framework\Escaper;
use Magento\Framework\View\Element\Template;

/** @var Template $block */
/** @var Escaper $escaper */
?>
<div wire:ignore>
<style>
#payment-method-option-rvvup_APPLE_PAY {
display: none;
}
</style>
<script>
(() => {
window.addEventListener('checkout:payment:method-activate', event => {
if (event.detail.method !== 'rvvup_APPLE_PAY') {
return;
}

const component = Magewire.find('<?= $escaper->escapeJs($block->getNameInLayout()) ?>');
hyvaCheckout.payment.activate('rvvup_APPLE_PAY', {
placeOrderViaJs() {
return document.querySelector('[wire\\:key="rvvup_APPLE_PAY"].active') !== null;
},

placeOrder() {
return component.placeOrder();
}
}, document.querySelector('[wire\\:key="rvvup_APPLE_PAY"].active'));
});
window.addEventListener('checkout:payment:method-activate', () => {
enableApplePay();
}, {once: false});
window.addEventListener('checkout:shipping:method-activate', () => {
enableApplePay();
}, {once: false});
window.addEventListener('checkout:step:loaded', () => {
enableApplePay();
}, {once: false});

function enableApplePay() {
let applePay = document.getElementById('payment-method-option-rvvup_APPLE_PAY');
if (applePay && window.ApplePaySession && window.ApplePaySession.canMakePayments()) {
applePay.style.display = 'block';
}
}
})();
</script>
</div>
Original file line number Diff line number Diff line change
@@ -0,0 +1,132 @@
<?php
declare(strict_types=1);

use Magento\Framework\Escaper;
use Magento\Framework\View\Element\Template;

/** @var Template $block */
/** @var Escaper $escaper */
/** @var \Rvvup\PaymentsHyvaCheckout\Magewire\Checkout\Payment\ApplePayProcessor $magewire */
?>
<div id="rvvup-apple-pay-inline" data-quoteamount="<?php echo $magewire->quoteAmount; ?>" data-quotecurrency="<?php echo $magewire->quoteCurrency; ?>">
<style>
#payment-method-option-rvvup_APPLE_PAY {
display: block;
}
.rvvup_APPLE_PAY_place_order_button {
display: none;
}
</style>
<script>
(() => {
const getQuoteTotal = () => {
const dataSet = document.querySelector('#rvvup-apple-pay-inline').dataset;
return {
amount: dataSet.quoteamount,
currency: dataSet.quotecurrency
};
};
const triggerApplePayDisplayEvent = () => {
if (!$showApplePay) {
window.dispatchEvent(new CustomEvent('rvvup:methods:apple-pay:hide'));
}
};
let applePayPromise = window.rvvup_sdk.createPaymentMethod("APPLE_PAY", {
checkoutSessionKey: rvvup_parameters.checkout.token,
total: getQuoteTotal(),
}).catch(e => {
console.error("Error creating Apple Pay payment method", e);
});
let $showApplePay = true;

applePayPromise.then(applePay => {
applePay.on("ready", async () => {
$showApplePay = await applePay.canMakePayment();
triggerApplePayDisplayEvent();
});
});
window.addEventListener('checkout:payment:method-activate', triggerApplePayDisplayEvent);
window.addEventListener('checkout:step:loaded', triggerApplePayDisplayEvent);

window.addEventListener('rvvup:methods:apple-pay:hide', () => {
let element = document.getElementById("payment-method-option-rvvup_APPLE_PAY");
if (element) {
element.parentElement.removeChild(element);
}
});

window.addEventListener('checkout:payment:method-activate', event => {
let placeOrderButton = document.querySelector('.nav-main .btn-primary');
const divId = "rvvup-apple-pay-button";

if (event.detail.method !== 'rvvup_APPLE_PAY') {
if (document.getElementById(divId)) {
document.getElementById(divId).style.display = 'none';
document.querySelector('.nav-main .btn-primary').classList.remove('rvvup_APPLE_PAY_place_order_button');
}
return;
}


const component = Magewire.find('<?= $escaper->escapeJs($block->getNameInLayout()) ?>');
hyvaCheckout.payment.activate('rvvup_APPLE_PAY', {
initialize() {
if(document.getElementById(divId)){
document.getElementById(divId).style.display = 'block';
placeOrderButton.classList.add('rvvup_APPLE_PAY_place_order_button');

return;
}
const applePayButtonDiv = document.createElement('div');
applePayButtonDiv.id = divId;
applePayButtonDiv.className = 'rvvup-applepay-button z-0';
if (placeOrderButton.className && placeOrderButton.className.indexOf("w-full") > -1) {
applePayButtonDiv.className += ' w-full';
}
placeOrderButton.classList.add('rvvup_APPLE_PAY_place_order_button');
placeOrderButton.appendChild(applePayButtonDiv);
placeOrderButton.parentNode.insertBefore(applePayButtonDiv, placeOrderButton);


applePayPromise.then(async function (applePay) {
if($showApplePay){
await applePay.mount({
selector: "#rvvup-apple-pay-button",
});
}
applePay.on("click", () => {
applePay.update({total: getQuoteTotal()});
});
applePay.on("beforePaymentAuth", async () => {
await component.createPaymentSession(rvvup_parameters.checkout.id)
return {
paymentSessionId: component.paymentSessionResult.paymentSessionId
};
});
applePay.on("paymentAuthorized", () => {
let magewire = document.getElementById('magewire-loader');
magewire.children[0].style.display = 'block';
window.location.href = component.paymentSessionResult.redirectUrl;
});
applePay.on("paymentFailed", (data) => {
window.dispatchMessages && window.dispatchMessages([{
type: 'error',
text: 'Payment ' + data.reason
}], 5000);
});
});

},
placeOrderViaJs() {
return document.querySelector('[wire\\:key="rvvup_APPLE_PAY"].active') !== null;
},

placeOrder() {
return component.placeOrder();
}
}, document.querySelector('[wire\\:key="rvvup_APPLE_PAY"].active'));

});
})();
</script>
</div>

This file was deleted.

Loading
Loading