We will be off from 27/1 (Monday) to 31/1 (Friday) (GMT +7) for our Tet Holiday (Lunar New Year) in our country

Commit 99397b67 authored by attilak's avatar attilak Committed by Rik ter Beek

- Modifications based on code review

- Card components instead of CSE
- 3D secure adjusted
- Installments adjusted

- Dependent php-api-library change (on the branch PW-306)
parent 687dc086
...@@ -51,9 +51,6 @@ class APIKeyMessage implements \Magento\Framework\Notification\MessageInterface ...@@ -51,9 +51,6 @@ class APIKeyMessage implements \Magento\Framework\Notification\MessageInterface
*/ */
protected $authSession; protected $authSession;
/**
* Message identity
*/
const MESSAGE_IDENTITY = 'Adyen API Key Control message'; const MESSAGE_IDENTITY = 'Adyen API Key Control message';
/** /**
...@@ -95,14 +92,20 @@ class APIKeyMessage implements \Magento\Framework\Notification\MessageInterface ...@@ -95,14 +92,20 @@ class APIKeyMessage implements \Magento\Framework\Notification\MessageInterface
public function isDisplayed() public function isDisplayed()
{ {
// Only execute the query the first time you access the Admin page // Only execute the query the first time you access the Admin page
if ($this->authSession->isFirstPageAfterLogin() && $this->_adyenHelper->getWsUsername()) { if ($this->authSession->isFirstPageAfterLogin() && empty($this->_adyenHelper->getAPIKey())) {
try { try {
$title = "Adyen extension requires the API KEY!"; $title = "Adyen extension requires the API KEY!";
if (!empty($this->_adyenHelper->getWsUsername())) {
$description = "Please provide API-KEY for the webservice user " . $this->_adyenHelper->getWsUsername() . " for default/store " . $this->storeManagerInterface->getStore()->getName();
}else{
$description = "Please provide API-KEY for default/store " . $this->storeManagerInterface->getStore()->getName();
}
$messageData[] = array( $messageData[] = array(
'severity' => $this->getSeverity(), 'severity' => $this->getSeverity(),
'date_added' => date("Y-m-d"), 'date_added' => date("Y-m-d"),
'title' => $title, 'title' => $title,
'description' => "Please provide API-KEY for the webserver user " . $this->_adyenHelper->getWsUsername() . " for default/store " . $this->storeManagerInterface->getStore()->getName(), 'description' => $description,
'url' => "https://docs.adyen.com/developers/plug-ins-and-partners/magento-2/set-up-the-plugin-in-magento#step3configuretheplugininmagento", 'url' => "https://docs.adyen.com/developers/plug-ins-and-partners/magento-2/set-up-the-plugin-in-magento#step3configuretheplugininmagento",
); );
...@@ -111,13 +114,8 @@ class APIKeyMessage implements \Magento\Framework\Notification\MessageInterface ...@@ -111,13 +114,8 @@ class APIKeyMessage implements \Magento\Framework\Notification\MessageInterface
* otherwise it will create it and add it to the inbox. * otherwise it will create it and add it to the inbox.
*/ */
$this->_inboxFactory->create()->parse(array_reverse($messageData)); $this->_inboxFactory->create()->parse(array_reverse($messageData));
return true;
/*
* Only show the message if the API Key is not set
*/
if (empty($this->_adyenHelper->getAPIKey())) {
return true;
}
} catch (\Exception $e) { } catch (\Exception $e) {
return false; return false;
} }
......
<?php
/**
* ######
* ######
* ############ ####( ###### #####. ###### ############ ############
* ############# #####( ###### #####. ###### ############# #############
* ###### #####( ###### #####. ###### ##### ###### ##### ######
* ###### ###### #####( ###### #####. ###### ##### ##### ##### ######
* ###### ###### #####( ###### #####. ###### ##### ##### ######
* ############# ############# ############# ############# ##### ######
* ############ ############ ############# ############ ##### ######
* ######
* #############
* ############
*
* Adyen Payment module (https://www.adyen.com/)
*
* Copyright (c) 2015 Adyen BV (https://www.adyen.com/)
* See LICENSE.txt for license details.
*
* Author: Adyen <magento@adyen.com>
*/
namespace Adyen\Payment\Gateway\Http\Client;
use Magento\Payment\Gateway\Http\ClientInterface;
/**
* Class TransactionSale
*/
class TransactionPayment implements ClientInterface
{
/**
* @var \Adyen\Client
*/
protected $client;
/**
* PaymentRequest constructor.
*
* @param \Magento\Framework\Model\Context $context
* @param \Magento\Framework\Encryption\EncryptorInterface $encryptor
* @param \Adyen\Payment\Helper\Data $adyenHelper
* @param \Adyen\Payment\Logger\AdyenLogger $adyenLogger
* @param \Adyen\Payment\Model\RecurringType $recurringType
* @param array $data
*/
public function __construct(
\Magento\Framework\Model\Context $context,
\Magento\Framework\Encryption\EncryptorInterface $encryptor,
\Adyen\Payment\Helper\Data $adyenHelper,
\Adyen\Payment\Logger\AdyenLogger $adyenLogger,
\Adyen\Payment\Model\RecurringType $recurringType,
array $data = []
) {
$this->_encryptor = $encryptor;
$this->_adyenHelper = $adyenHelper;
$this->_adyenLogger = $adyenLogger;
$this->_recurringType = $recurringType;
$this->_appState = $context->getAppState();
$this->client = $this->_adyenHelper->initializeAdyenClient();
}
/**
* @param \Magento\Payment\Gateway\Http\TransferInterface $transferObject
* @return mixed
* @throws ClientException
*/
public function placeRequest(\Magento\Payment\Gateway\Http\TransferInterface $transferObject)
{
$request = $transferObject->getBody();
$service = new \Adyen\Service\Checkout($this->client);
try {
$response = $service->payments($request);
} catch(\Adyen\AdyenException $e) {
$response['error'] = $e->getMessage();
}
return $response;
}
}
...@@ -38,57 +38,73 @@ class CcAuthorizationDataBuilder implements BuilderInterface ...@@ -38,57 +38,73 @@ class CcAuthorizationDataBuilder implements BuilderInterface
*/ */
private $appState; private $appState;
/** /**
* CcAuthorizationDataBuilder constructor. * @var \Adyen\Payment\Logger\AdyenLogger
* */
* @param \Adyen\Payment\Helper\Data $adyenHelper protected $_adyenLogger;
* @param \Magento\Framework\Model\Context $context
*/
public function __construct(
\Adyen\Payment\Helper\Data $adyenHelper,
\Magento\Framework\Model\Context $context
) {
$this->adyenHelper = $adyenHelper;
$this->appState = $context->getAppState();
}
/** /**
* @param array $buildSubject * CcAuthorizationDataBuilder constructor.
* @return mixed *
*/ * @param \Adyen\Payment\Helper\Data $adyenHelper
public function build(array $buildSubject) * @param \Magento\Framework\Model\Context $context
{ */
/** @var \Magento\Payment\Gateway\Data\PaymentDataObject $paymentDataObject */ public function __construct(
$paymentDataObject = \Magento\Payment\Gateway\Helper\SubjectReader::readPayment($buildSubject); \Adyen\Payment\Helper\Data $adyenHelper,
$payment = $paymentDataObject->getPayment(); \Magento\Framework\Model\Context $context,
$order = $paymentDataObject->getOrder(); \Adyen\Payment\Logger\AdyenLogger $adyenLogger
$storeId = $order->getStoreId(); )
$request = []; {
$this->adyenHelper = $adyenHelper;
$this->appState = $context->getAppState();
$this->_adyenLogger = $adyenLogger;
}
/**
* @param array $buildSubject
* @return mixed
*/
public function build(array $buildSubject)
{
/** @var \Magento\Payment\Gateway\Data\PaymentDataObject $paymentDataObject */
$paymentDataObject = \Magento\Payment\Gateway\Helper\SubjectReader::readPayment($buildSubject);
$payment = $paymentDataObject->getPayment();
$order = $paymentDataObject->getOrder();
$storeId = $order->getStoreId();
$request = [];
$request['additionalData']['card.encrypted.json'] = $request['paymentMethod']['type'] = "scheme";
$payment->getAdditionalInformation(AdyenCcDataAssignObserver::ENCRYPTED_DATA); $request['paymentMethod']['encryptedCardNumber'] = $payment->getAdditionalInformation(AdyenCcDataAssignObserver::CREDIT_CARD_NUMBER);
$request['paymentMethod']['encryptedExpiryMonth'] = $payment->getAdditionalInformation(AdyenCcDataAssignObserver::EXPIRY_MONTH);
$request['paymentMethod']['encryptedExpiryYear'] = $payment->getAdditionalInformation(AdyenCcDataAssignObserver::EXPIRY_YEAR);
$request['paymentMethod']['encryptedSecurityCode'] = $payment->getAdditionalInformation(AdyenCcDataAssignObserver::SECURITY_CODE);
$request['paymentMethod']['holderName'] = $payment->getAdditionalInformation(AdyenCcDataAssignObserver::HOLDER_NAME);
// Remove from additional data // Remove from additional data
$payment->unsAdditionalInformation(AdyenCcDataAssignObserver::ENCRYPTED_DATA); $payment->unsAdditionalInformation(AdyenCcDataAssignObserver::CREDIT_CARD_NUMBER);
$payment->unsAdditionalInformation(AdyenCcDataAssignObserver::EXPIRY_MONTH);
$payment->unsAdditionalInformation(AdyenCcDataAssignObserver::EXPIRY_YEAR);
$payment->unsAdditionalInformation(AdyenCcDataAssignObserver::SECURITY_CODE);
$payment->unsAdditionalInformation(AdyenCcDataAssignObserver::HOLDER_NAME);
$payment->unsAdditionalInformation(AdyenCcDataAssignObserver::ENCRYPTED_DATA);
/** /**
* if MOTO for backend is enabled use MOTO as shopper interaction type * if MOTO for backend is enabled use MOTO as shopper interaction type
*/ */
$enableMoto = $this->adyenHelper->getAdyenCcConfigDataFlag('enable_moto', $storeId); $enableMoto = $this->adyenHelper->getAdyenCcConfigDataFlag('enable_moto', $storeId);
if ($this->appState->getAreaCode() === \Magento\Backend\App\Area\FrontNameResolver::AREA_CODE && if ($this->appState->getAreaCode() === \Magento\Backend\App\Area\FrontNameResolver::AREA_CODE &&
$enableMoto $enableMoto
) { ) {
$request['shopperInteraction'] = "Moto"; $request['shopperInteraction'] = "Moto";
} }
// if installments is set add it into the request // if installments is set add it into the request
if ($payment->getAdditionalInformation('number_of_installments') && if ($payment->getAdditionalInformation(AdyenCcDataAssignObserver::NUMBER_OF_INSTALLMENTS) &&
$payment->getAdditionalInformation('number_of_installments') > 0 $payment->getAdditionalInformation(AdyenCcDataAssignObserver::NUMBER_OF_INSTALLMENTS) > 0
) { ) {
$request['installments']['value'] = $payment->getAdditionalInformation('number_of_installments'); $request['installments']['value'] = $payment->getAdditionalInformation(AdyenCcDataAssignObserver::NUMBER_OF_INSTALLMENTS);
} }
return $request; return $request;
} }
} }
\ No newline at end of file
<?php
/**
* ######
* ######
* ############ ####( ###### #####. ###### ############ ############
* ############# #####( ###### #####. ###### ############# #############
* ###### #####( ###### #####. ###### ##### ###### ##### ######
* ###### ###### #####( ###### #####. ###### ##### ##### ##### ######
* ###### ###### #####( ###### #####. ###### ##### ##### ######
* ############# ############# ############# ############# ##### ######
* ############ ############ ############# ############ ##### ######
* ######
* #############
* ############
*
* Adyen Payment module (https://www.adyen.com/)
*
* Copyright (c) 2015 Adyen BV (https://www.adyen.com/)
* See LICENSE.txt for license details.
*
* Author: Adyen <magento@adyen.com>
*/
namespace Adyen\Payment\Gateway\Response;
use Magento\Payment\Gateway\Response\HandlerInterface;
class CheckoutPaymentCommentHistoryHandler implements HandlerInterface
{
/**
* @param array $handlingSubject
* @param array $response
* @return $this
*/
public function handle(array $handlingSubject, array $response)
{
$payment = \Magento\Payment\Gateway\Helper\SubjectReader::readPayment($handlingSubject);
/** @var OrderPaymentInterface $payment */
$payment = $payment->getPayment();
$commentText = "Adyen Result response:";
if (isset($response['resultCode'])) {
$responseCode = $response['resultCode'];
} else {
// try to get response from response key (used for modifications
if (isset($response['response'])) {
$responseCode = $response['response'];
} else {
$responseCode = "";
}
}
if (isset($response['pspReference'])) {
$pspReference = $response['pspReference'];
} else {
$pspReference = "";
}
if ($responseCode) {
$commentText .= '<br /> authResult: ' . $responseCode;
$payment->getOrder()->setAdyenResulturlEventCode($responseCode);
}
if ($pspReference) {
$commentText .= '<br /> authResult: ' . $pspReference;
}
$comment = __($commentText);
$payment->getOrder()->addStatusHistoryComment($comment);
return $this;
}
}
<?php
/**
* ######
* ######
* ############ ####( ###### #####. ###### ############ ############
* ############# #####( ###### #####. ###### ############# #############
* ###### #####( ###### #####. ###### ##### ###### ##### ######
* ###### ###### #####( ###### #####. ###### ##### ##### ##### ######
* ###### ###### #####( ###### #####. ###### ##### ##### ######
* ############# ############# ############# ############# ##### ######
* ############ ############ ############# ############ ##### ######
* ######
* #############
* ############
*
* Adyen Payment module (https://www.adyen.com/)
*
* Copyright (c) 2015 Adyen BV (https://www.adyen.com/)
* See LICENSE.txt for license details.
*
* Author: Adyen <magento@adyen.com>
*/
namespace Adyen\Payment\Gateway\Response;
use Magento\Payment\Gateway\Response\HandlerInterface;
class CheckoutPaymentsDetailsHandler implements HandlerInterface
{
/**
* @param array $handlingSubject
* @param array $response
*/
public function handle(array $handlingSubject, array $response)
{
$payment = \Magento\Payment\Gateway\Helper\SubjectReader::readPayment($handlingSubject);
/** @var OrderPaymentInterface $payment */
$payment = $payment->getPayment();
// set transaction not to processing by default wait for notification
$payment->setIsTransactionPending(true);
// no not send order confirmation mail
$payment->getOrder()->setCanSendNewEmailFlag(false);
if (!empty($response['pspReference'])) {
// set pspReference as transactionId
$payment->setCcTransId($response['pspReference']);
$payment->setLastTransId($response['pspReference']);
// set transaction
$payment->setTransactionId($response['pspReference']);
}
// do not close transaction so you can do a cancel() and void
$payment->setIsTransactionClosed(false);
$payment->setShouldCloseParentTransaction(false);
}
}
<?php
/**
* ######
* ######
* ############ ####( ###### #####. ###### ############ ############
* ############# #####( ###### #####. ###### ############# #############
* ###### #####( ###### #####. ###### ##### ###### ##### ######
* ###### ###### #####( ###### #####. ###### ##### ##### ##### ######
* ###### ###### #####( ###### #####. ###### ##### ##### ######
* ############# ############# ############# ############# ##### ######
* ############ ############ ############# ############ ##### ######
* ######
* #############
* ############
*
* Adyen Payment module (https://www.adyen.com/)
*
* Copyright (c) 2015 Adyen BV (https://www.adyen.com/)
* See LICENSE.txt for license details.
*
* Author: Adyen <magento@adyen.com>
*/
namespace Adyen\Payment\Gateway\Validator;
use Magento\Payment\Gateway\Validator\AbstractValidator;
class CheckoutResponseValidator extends AbstractValidator
{
/**
* @var \Adyen\Payment\Logger\AdyenLogger
*/
private $adyenLogger;
/**
* GeneralResponseValidator constructor.
*
* @param \Magento\Payment\Gateway\Validator\ResultInterfaceFactory $resultFactory
* @param \Adyen\Payment\Logger\AdyenLogger $adyenLogger
*/
public function __construct(
\Magento\Payment\Gateway\Validator\ResultInterfaceFactory $resultFactory,
\Adyen\Payment\Logger\AdyenLogger $adyenLogger
) {
$this->adyenLogger = $adyenLogger;
parent::__construct($resultFactory);
}
/**
* @param array $validationSubject
* @return \Magento\Payment\Gateway\Validator\ResultInterface
*/
public function validate(array $validationSubject)
{
$response = \Magento\Payment\Gateway\Helper\SubjectReader::readResponse($validationSubject);
$paymentDataObjectInterface = \Magento\Payment\Gateway\Helper\SubjectReader::readPayment($validationSubject);
$payment = $paymentDataObjectInterface->getPayment();
$payment->setAdditionalInformation('3dActive', false);
$isValid = true;
$errorMessages = [];
// validate result
if ($response && isset($response['resultCode'])) {
switch ($response['resultCode']) {
case "Authorised":
$payment->setAdditionalInformation('pspReference', $response['pspReference']);
break;
case "Received":
$payment->setAdditionalInformation('pspReference', $response['pspReference']);
// set additionalData
if (isset($response['additionalData']) && is_array($response['additionalData'])) {
$additionalData = $response['additionalData'];
if (isset($additionalData['boletobancario.dueDate'])) {
$payment->setAdditionalInformation(
'dueDate',
$additionalData['boletobancario.dueDate']
);
}
if (isset($additionalData['boletobancario.expirationDate'])) {
$payment->setAdditionalInformation(
'expirationDate',
$additionalData['boletobancario.expirationDate']
);
}
if (isset($additionalData['boletobancario.url'])) {
$payment->setAdditionalInformation(
'url',
$additionalData['boletobancario.url']
);
}
}
break;
case "RedirectShopper":
$payment->setAdditionalInformation('3dActive', true);
$issuerUrl = $response['redirect']['url'];
$paReq = $response['redirect']['data']['PaReq'];
$md = $response['redirect']['data']['MD'];
if (!empty($paReq) && !empty($md) && !empty($issuerUrl)) {
$payment->setAdditionalInformation('issuerUrl', $issuerUrl);
$payment->setAdditionalInformation('paRequest', $paReq);
$payment->setAdditionalInformation('md', $md);
} else {
$isValid = false;
$errorMsg = __('3D secure is not valid.');
$this->adyenLogger->error($errorMsg);;
$errorMessages[] = $errorMsg;
}
break;
case "Refused":
$errorMsg = __('The payment is REFUSED.');
// this will result the specific error
throw new \Magento\Framework\Exception\LocalizedException(__($errorMsg));
break;
default:
$errorMsg = __('Error with payment method please select different payment method.');
throw new \Magento\Framework\Exception\LocalizedException(__($errorMsg));
break;
}
} else {
$errorMsg = __('Error with payment method please select different payment method.');
throw new \Magento\Framework\Exception\LocalizedException(__($errorMsg));
}
return $this->createResult($isValid, $errorMessages);
}
}
...@@ -33,8 +33,8 @@ class Data extends AbstractHelper ...@@ -33,8 +33,8 @@ class Data extends AbstractHelper
const MODULE_NAME = 'adyen-magento2'; const MODULE_NAME = 'adyen-magento2';
const TEST = 'test'; const TEST = 'test';
const LIVE = 'live'; const LIVE = 'live';
const SECURE_FIELDS_SDK_TEST = "https://checkoutshopper-test.adyen.com/checkoutshopper/assets/js/sdk/checkoutSecuredFields.1.3.0.min.js"; const CHECKOUT_CONTEXT_URL_LIVE = 'https://checkoutshopper-live.adyen.com/checkoutshopper/';
const SECURE_FIELDS_SDK_LIVE = "https://checkoutshopper-live.adyen.com/checkoutshopper/assets/js/sdk/checkoutSecuredFields.1.3.0.min.js"; const CHECKOUT_CONTEXT_URL_TEST = 'https://checkoutshopper-test.adyen.com/checkoutshopper/';
/** /**
* @var \Magento\Framework\Encryption\EncryptorInterface * @var \Magento\Framework\Encryption\EncryptorInterface
...@@ -97,14 +97,19 @@ class Data extends AbstractHelper ...@@ -97,14 +97,19 @@ class Data extends AbstractHelper
protected $adyenLogger; protected $adyenLogger;
/** /**
* @var \Magento\Framework\UrlInterface * @var \Adyen\Service\ServiceFactory
*/ */
protected $urlInterface; protected $adyenServiceFactory;
/** /**
* @var \Adyen\Service\ServiceFactory * @var \Magento\Store\Model\StoreManagerInterface
*/ */
protected $adyenServiceFactory; protected $storeManager;
/**
* @var \Magento\Framework\App\CacheInterface
*/
protected $cache;
/** /**
* Data constructor. * Data constructor.
...@@ -122,8 +127,9 @@ class Data extends AbstractHelper ...@@ -122,8 +127,9 @@ class Data extends AbstractHelper
* @param \Magento\Tax\Model\Calculation $taxCalculation * @param \Magento\Tax\Model\Calculation $taxCalculation
* @param \Magento\Framework\App\ProductMetadataInterface $productMetadata * @param \Magento\Framework\App\ProductMetadataInterface $productMetadata
* @param \Adyen\Payment\Logger\AdyenLogger $adyenLogger * @param \Adyen\Payment\Logger\AdyenLogger $adyenLogger
* @param \Magento\Framework\UrlInterface $urlInterface
* @param \Adyen\Service\ServiceFactory $adyenServiceFactory * @param \Adyen\Service\ServiceFactory $adyenServiceFactory
* @param \Magento\Store\Model\StoreManagerInterface $storeManager
* @param \Magento\Framework\App\CacheInterface $cache
*/ */
public function __construct( public function __construct(
\Magento\Framework\App\Helper\Context $context, \Magento\Framework\App\Helper\Context $context,
...@@ -139,8 +145,9 @@ class Data extends AbstractHelper ...@@ -139,8 +145,9 @@ class Data extends AbstractHelper
\Magento\Tax\Model\Calculation $taxCalculation, \Magento\Tax\Model\Calculation $taxCalculation,
\Magento\Framework\App\ProductMetadataInterface $productMetadata, \Magento\Framework\App\ProductMetadataInterface $productMetadata,
\Adyen\Payment\Logger\AdyenLogger $adyenLogger, \Adyen\Payment\Logger\AdyenLogger $adyenLogger,
\Magento\Framework\UrlInterface $urlInterface, \Adyen\Service\ServiceFactory $adyenServiceFactory,
\Adyen\Service\ServiceFactory $adyenServiceFactory \Magento\Store\Model\StoreManagerInterface $storeManager,
\Magento\Framework\App\CacheInterface $cache
) { ) {
parent::__construct($context); parent::__construct($context);
...@@ -156,8 +163,9 @@ class Data extends AbstractHelper ...@@ -156,8 +163,9 @@ class Data extends AbstractHelper
$this->_taxCalculation = $taxCalculation; $this->_taxCalculation = $taxCalculation;
$this->productMetadata = $productMetadata; $this->productMetadata = $productMetadata;
$this->adyenLogger = $adyenLogger; $this->adyenLogger = $adyenLogger;
$this->urlInterface = $urlInterface;
$this->adyenServiceFactory = $adyenServiceFactory; $this->adyenServiceFactory = $adyenServiceFactory;
$this->storeManager = $storeManager;
$this->cache = $cache;
} }
/** /**
...@@ -1042,20 +1050,6 @@ class Data extends AbstractHelper ...@@ -1042,20 +1050,6 @@ class Data extends AbstractHelper
; ;
} }
/**
* Retrieves secure field sdk url based on the demo mode
*
* @return string
*/
public function getSecureFieldsSdk()
{
if ($this->isDemoMode()) {
return self::SECURE_FIELDS_SDK_TEST;
} else {
return self::SECURE_FIELDS_SDK_LIVE;
}
}
/** /**
* @param $formFields * @param $formFields
* @param $count * @param $count
...@@ -1352,11 +1346,17 @@ class Data extends AbstractHelper ...@@ -1352,11 +1346,17 @@ class Data extends AbstractHelper
*/ */
public function getOriginKeyForBaseUrl() public function getOriginKeyForBaseUrl()
{ {
$originKey = ""; $baseUrl = $this->storeManager->getStore()->getBaseUrl(\Magento\Framework\UrlInterface::URL_TYPE_WEB);
$baseUrl = $this->urlInterface->getBaseUrl(); $parsed = parse_url($baseUrl);
$domain = $parsed['scheme'] . "://" . $parsed['host'];
if ($originKeys = $this->getOriginKeys($baseUrl)) { if (!$originKey = $this->cache->load("Adyen_origin_key_for_" . $domain)) {
$originKey = $originKeys[$baseUrl]; $originKey = "";
if ($originKeys = $this->getOriginKeys($domain)) {
$originKey = $originKeys[$domain];
$this->cache->save($originKey, "Adyen_origin_key_for_" . $domain, array(), 60 * 60 * 24);
}
} }
return $originKey; return $originKey;
...@@ -1383,4 +1383,16 @@ class Data extends AbstractHelper ...@@ -1383,4 +1383,16 @@ class Data extends AbstractHelper
$respone = $service->originKeys($params); $respone = $service->originKeys($params);
return $respone['originKeys']; return $respone['originKeys'];
} }
/**
* @param int|null $storeId
* @return string
*/
public function getCheckoutContextUrl($storeId = null) {
if ($this->isDemoMode($storeId)) {
return self::CHECKOUT_CONTEXT_URL_TEST;
}
return self::CHECKOUT_CONTEXT_URL_LIVE;
}
} }
...@@ -24,9 +24,6 @@ ...@@ -24,9 +24,6 @@
namespace Adyen\Payment\Model\Ui; namespace Adyen\Payment\Model\Ui;
use Magento\Checkout\Model\ConfigProviderInterface; use Magento\Checkout\Model\ConfigProviderInterface;
use Magento\Payment\Helper\Data as PaymentHelper;
use Magento\Framework\View\Asset\Source as Source;
use \Magento\Payment\Gateway\Config\Config as Config;
class AdyenCcConfigProvider implements ConfigProviderInterface class AdyenCcConfigProvider implements ConfigProviderInterface
{ {
...@@ -65,24 +62,30 @@ class AdyenCcConfigProvider implements ConfigProviderInterface ...@@ -65,24 +62,30 @@ class AdyenCcConfigProvider implements ConfigProviderInterface
*/ */
private $ccConfig; private $ccConfig;
/**
* @var \Magento\Store\Model\StoreManagerInterface
*/
private $storeManager;
/**
* AdyenCcConfigProvider constructor. /**
* * AdyenCcConfigProvider constructor.
* @param PaymentHelper $paymentHelper *
* @param \Adyen\Payment\Helper\Data $adyenHelper * @param \Magento\Payment\Helper\Data $paymentHelper
* @param \Magento\Framework\App\RequestInterface $request * @param \Adyen\Payment\Helper\Data $adyenHelper
* @param \Magento\Framework\UrlInterface $urlBuilder * @param \Magento\Framework\App\RequestInterface $request
* @param Source $assetSource * @param \Magento\Framework\UrlInterface $urlBuilder
* @param \Magento\Payment\Model\CcConfig $ccConfig * @param \Magento\Framework\View\Asset\Source $assetSource
* @param Config $config * @param \Magento\Store\Model\StoreManagerInterface $storeManager
*/ * @param \Magento\Payment\Model\CcConfig $ccConfig
*/
public function __construct( public function __construct(
PaymentHelper $paymentHelper, \Magento\Payment\Helper\Data $paymentHelper,
\Adyen\Payment\Helper\Data $adyenHelper, \Adyen\Payment\Helper\Data $adyenHelper,
\Magento\Framework\App\RequestInterface $request, \Magento\Framework\App\RequestInterface $request,
\Magento\Framework\UrlInterface $urlBuilder, \Magento\Framework\UrlInterface $urlBuilder,
Source $assetSource, \Magento\Framework\View\Asset\Source $assetSource,
\Magento\Store\Model\StoreManagerInterface $storeManager,
\Magento\Payment\Model\CcConfig $ccConfig \Magento\Payment\Model\CcConfig $ccConfig
) { ) {
$this->_paymentHelper = $paymentHelper; $this->_paymentHelper = $paymentHelper;
...@@ -91,6 +94,7 @@ class AdyenCcConfigProvider implements ConfigProviderInterface ...@@ -91,6 +94,7 @@ class AdyenCcConfigProvider implements ConfigProviderInterface
$this->_urlBuilder = $urlBuilder; $this->_urlBuilder = $urlBuilder;
$this->_assetSource = $assetSource; $this->_assetSource = $assetSource;
$this->ccConfig = $ccConfig; $this->ccConfig = $ccConfig;
$this->storeManager = $storeManager;
} }
/** /**
...@@ -117,6 +121,7 @@ class AdyenCcConfigProvider implements ConfigProviderInterface ...@@ -117,6 +121,7 @@ class AdyenCcConfigProvider implements ConfigProviderInterface
'payment' => [ 'payment' => [
'ccform' => [ 'ccform' => [
'availableTypes' => [$methodCode => $this->getCcAvailableTypes($methodCode)], 'availableTypes' => [$methodCode => $this->getCcAvailableTypes($methodCode)],
'availableTypesByAlt' => [$methodCode => $this->getCcAvailableTypesByAlt($methodCode)],
'months' => [$methodCode => $this->getCcMonths()], 'months' => [$methodCode => $this->getCcMonths()],
'years' => [$methodCode => $this->getCcYears()], 'years' => [$methodCode => $this->getCcYears()],
'hasVerification' => [$methodCode => $this->hasVerification($methodCode)], 'hasVerification' => [$methodCode => $this->hasVerification($methodCode)],
...@@ -126,17 +131,22 @@ class AdyenCcConfigProvider implements ConfigProviderInterface ...@@ -126,17 +131,22 @@ class AdyenCcConfigProvider implements ConfigProviderInterface
]); ]);
$recurringType = $this->_adyenHelper->getAdyenAbstractConfigData('recurring_type'); $recurringType = $this->_adyenHelper->getAdyenAbstractConfigData('recurring_type');
$canCreateBillingAgreement = false; $canCreateBillingAgreement = false;
if ($recurringType == "ONECLICK" || $recurringType == "ONECLICK,RECURRING") { if ($recurringType == "ONECLICK" || $recurringType == "ONECLICK,RECURRING") {
$canCreateBillingAgreement = true; $canCreateBillingAgreement = true;
} }
$config['payment']['adyenCc']['methodCode'] = self::CODE;
$config['payment']['adyenCc']['locale'] = $this->_adyenHelper->getStoreLocale($this->storeManager->getStore()->getId());
$config['payment']['adyenCc']['generationTime'] = date("c"); $config['payment']['adyenCc']['generationTime'] = date("c");
$config['payment']['adyenCc']['canCreateBillingAgreement'] = $canCreateBillingAgreement; $config['payment']['adyenCc']['canCreateBillingAgreement'] = $canCreateBillingAgreement;
$config['payment']['adyenCc']['icons'] = $this->getIcons(); $config['payment']['adyenCc']['icons'] = $this->getIcons();
$config['payment']['adyenCc']['originKey'] = $this->_adyenHelper->getOriginKeyForBaseUrl(); $config['payment']['adyenCc']['originKey'] = $this->_adyenHelper->getOriginKeyForBaseUrl();
$config['payment']['adyenCc']['secureFieldsSource'] = $this->_adyenHelper->getSecureFieldsSdk(); $config['payment']['adyenCc']['checkoutUrl'] = $this->_adyenHelper->getCheckoutContextUrl($this->storeManager->getStore()->getId());
// has installments by default false // has installments by default false
$config['payment']['adyenCc']['hasInstallments'] = false; $config['payment']['adyenCc']['hasInstallments'] = false;
...@@ -178,6 +188,29 @@ class AdyenCcConfigProvider implements ConfigProviderInterface ...@@ -178,6 +188,29 @@ class AdyenCcConfigProvider implements ConfigProviderInterface
return $types; return $types;
} }
/**
* Retrieve availables credit card type codes by alt code
*
* @param string $methodCode
* @return array
*/
protected function getCcAvailableTypesByAlt($methodCode)
{
$types = [];
$ccTypes = $this->_adyenHelper->getAdyenCcTypes();
$availableTypes = $this->_adyenHelper->getAdyenCcConfigData('cctypes');
if ($availableTypes) {
$availableTypes = explode(',', $availableTypes);
foreach (array_keys($ccTypes) as $code) {
if (in_array($code, $availableTypes)) {
$types[$ccTypes[$code]['code_alt']] = $code;
}
}
}
return $types;
}
/** /**
* Get icons for available payment methods * Get icons for available payment methods
* *
......
...@@ -138,7 +138,8 @@ class AdyenOneclickConfigProvider implements ConfigProviderInterface ...@@ -138,7 +138,8 @@ class AdyenOneclickConfigProvider implements ConfigProviderInterface
$canCreateBillingAgreement = true; $canCreateBillingAgreement = true;
} }
$config['payment'] ['adyenOneclick']['librarySource'] = $this->_adyenHelper->getLibrarySource(); // Commented out otherwise would break the checkoutsince the getLibrarySource is removed
//$config['payment'] ['adyenOneclick']['librarySource'] = $this->_adyenHelper->getLibrarySource();
$config['payment']['adyenOneclick']['generationTime'] = date("c"); $config['payment']['adyenOneclick']['generationTime'] = date("c");
$config['payment']['adyenOneclick']['canCreateBillingAgreement'] = $canCreateBillingAgreement; $config['payment']['adyenOneclick']['canCreateBillingAgreement'] = $canCreateBillingAgreement;
......
...@@ -32,18 +32,28 @@ use Magento\Quote\Api\Data\PaymentInterface; ...@@ -32,18 +32,28 @@ use Magento\Quote\Api\Data\PaymentInterface;
class AdyenCcDataAssignObserver extends AbstractDataAssignObserver class AdyenCcDataAssignObserver extends AbstractDataAssignObserver
{ {
const CC_TYPE = 'cc_type'; const CC_TYPE = 'cc_type';
const ENCRYPTED_DATA = 'encrypted_data';
const NUMBER_OF_INSTALLMENTS = 'number_of_installments'; const NUMBER_OF_INSTALLMENTS = 'number_of_installments';
const STORE_CC = 'store_cc'; const STORE_CC = 'store_cc';
const CREDIT_CARD_NUMBER = 'number';
const SECURITY_CODE = 'cvc';
const EXPIRY_MONTH = 'expiryMonth';
const EXPIRY_YEAR = 'expiryYear';
const HOLDER_NAME = 'holderName';
const ENCRYPTED_DATA = 'encrypted_data';
/** /**
* @var array * @var array
*/ */
protected $additionalInformationList = [ protected $additionalInformationList = [
self::CC_TYPE, self::CC_TYPE,
self::ENCRYPTED_DATA,
self::NUMBER_OF_INSTALLMENTS, self::NUMBER_OF_INSTALLMENTS,
self::STORE_CC self::STORE_CC,
self::CREDIT_CARD_NUMBER,
self::SECURITY_CODE,
self::EXPIRY_MONTH,
self::EXPIRY_YEAR,
self::HOLDER_NAME
]; ];
/** /**
......
...@@ -426,8 +426,8 @@ ...@@ -426,8 +426,8 @@
<arguments> <arguments>
<argument name="requestBuilder" xsi:type="object">AdyenPaymentCcAuthorizeRequest</argument> <argument name="requestBuilder" xsi:type="object">AdyenPaymentCcAuthorizeRequest</argument>
<argument name="transferFactory" xsi:type="object">Adyen\Payment\Gateway\Http\TransferFactory</argument> <argument name="transferFactory" xsi:type="object">Adyen\Payment\Gateway\Http\TransferFactory</argument>
<argument name="client" xsi:type="object">Adyen\Payment\Gateway\Http\Client\TransactionAuthorization</argument> <argument name="client" xsi:type="object">Adyen\Payment\Gateway\Http\Client\TransactionPayment</argument>
<argument name="validator" xsi:type="object">GeneralResponseValidator</argument> <argument name="validator" xsi:type="object">CheckoutResponseValidator</argument>
<argument name="handler" xsi:type="object">AdyenPaymentCcResponseHandlerComposite</argument> <argument name="handler" xsi:type="object">AdyenPaymentCcResponseHandlerComposite</argument>
</arguments> </arguments>
</virtualType> </virtualType>
...@@ -650,8 +650,8 @@ ...@@ -650,8 +650,8 @@
<virtualType name="AdyenPaymentCcResponseHandlerComposite" type="Magento\Payment\Gateway\Response\HandlerChain"> <virtualType name="AdyenPaymentCcResponseHandlerComposite" type="Magento\Payment\Gateway\Response\HandlerChain">
<arguments> <arguments>
<argument name="handlers" xsi:type="array"> <argument name="handlers" xsi:type="array">
<item name="payment_details" xsi:type="string">Adyen\Payment\Gateway\Response\PaymentAuthorisationDetailsHandler</item> <item name="payment_details" xsi:type="string">Adyen\Payment\Gateway\Response\CheckoutPaymentsDetailsHandler</item>
<item name="payment_comments" xsi:type="string">Adyen\Payment\Gateway\Response\PaymentCommentHistoryHandler</item> <item name="payment_comments" xsi:type="string">Adyen\Payment\Gateway\Response\CheckoutPaymentCommentHistoryHandler</item>
</argument> </argument>
</arguments> </arguments>
</virtualType> </virtualType>
...@@ -841,6 +841,13 @@ ...@@ -841,6 +841,13 @@
</arguments> </arguments>
</virtualType> </virtualType>
<!--Checkout Response validator-->
<virtualType name="CheckoutResponseValidator" type="Adyen\Payment\Gateway\Validator\CheckoutResponseValidator">
<arguments>
<argument name="loggerInterface" xsi:type="object">Adyen\Payment\Logger\AdyenLogger</argument>
</arguments>
</virtualType>
<virtualType name="PosCloudResponseValidator" type="Adyen\Payment\Gateway\Validator\PosCloudResponseValidator"> <virtualType name="PosCloudResponseValidator" type="Adyen\Payment\Gateway\Validator\PosCloudResponseValidator">
<arguments> <arguments>
<argument name="loggerInterface" xsi:type="object">Adyen\Payment\Logger\AdyenLogger</argument> <argument name="loggerInterface" xsi:type="object">Adyen\Payment\Logger\AdyenLogger</argument>
......
...@@ -51,4 +51,5 @@ ...@@ -51,4 +51,5 @@
"Failed to disable this contract","Failed to disable this contract" "Failed to disable this contract","Failed to disable this contract"
"You will be redirected to the Adyen App", "You will be redirected to the Adyen App" "You will be redirected to the Adyen App", "You will be redirected to the Adyen App"
"Continue to Adyen App", "Continue to Adyen App" "Continue to Adyen App", "Continue to Adyen App"
"Do not use Installments", "Do not use Installments" "Do not use Installments", "Do not use Installments"
\ No newline at end of file "(Please provide a card with the type from the list above)", "(Please provide a card with the type from the list above)"
\ No newline at end of file
...@@ -52,3 +52,4 @@ ...@@ -52,3 +52,4 @@
"You will be redirected to the Adyen App", "U wordt doorgestuurd naar de Adyen-app" "You will be redirected to the Adyen App", "U wordt doorgestuurd naar de Adyen-app"
"Continue to Adyen App", "Doorgaan naar Adyen-app" "Continue to Adyen App", "Doorgaan naar Adyen-app"
"Do not use Installments", "Gebruik geen wederkerende betalingen" "Do not use Installments", "Gebruik geen wederkerende betalingen"
"(Please provide a card with the type from the list above)", "(Please provide a card with the type from the list above)"
...@@ -25,8 +25,6 @@ ...@@ -25,8 +25,6 @@
<page xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:View/Layout/etc/layout_generic.xsd"> <page xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:View/Layout/etc/layout_generic.xsd">
<head> <head>
<css src="Adyen_Payment::css/styles.css"/> <css src="Adyen_Payment::css/styles.css"/>
<script src="Adyen_Payment::js/adyen.2.0.0.js"></script>
<script src="Adyen_Payment::js/adyen.checkout.js"></script>
</head> </head>
<body> <body>
<referenceBlock name="checkout.root"> <referenceBlock name="checkout.root">
......
...@@ -20,10 +20,35 @@ ...@@ -20,10 +20,35 @@
* Author: Adyen <magento@adyen.com> * Author: Adyen <magento@adyen.com>
*/ */
.hidden {
display: none;
}
.checkout-payment-method .ccard .changable-card-expiry { display:none; } .checkout-payment-method .ccard .changable-card-expiry { display:none; }
.checkout-payment-method .ccard .changable-card-expiry._active { display:block; } .checkout-payment-method .ccard .changable-card-expiry._active { display:block; }
.checkout-payment-method .ccard .expire-update._disable { display:none; } .checkout-payment-method .ccard .expire-update._disable { display:none; }
.checkout-payment-method .ccard .holdername .input-text { width: 225px; }
.checkout-payment-method .ccard .holdername .input-text {
width: 225px;
border: none;
padding: 0;
color: rgb(0, 27, 43);
font-size: 16px;
font-weight: 400;
}
.checkout-payment-method .ccard .holdername .input-text:focus {
border: none;
box-shadow: none;
}
.checkout-payment-method .ccard .holdername .input-text::placeholder,
.checkout-payment-method .ccard .holdername .input-text:placeholder-shown
{
color: rgb(144, 162, 189);
font-weight: 200;
}
.checkout-payment-method .payment-method-title, .checkout-payment-method .payment-method-title label { .checkout-payment-method .payment-method-title, .checkout-payment-method .payment-method-title label {
display: -webkit-flex; display: -webkit-flex;
...@@ -139,6 +164,22 @@ ...@@ -139,6 +164,22 @@
min-height: 42px; /* override magento min-height */ min-height: 42px; /* override magento min-height */
} }
/* Checkout card components style */
.adyen-checkout-card__form .adyen-checkout__input iframe{
max-height: 40px;
}
.adyen-checkout-card__form .adyen-checkout__input img{
display: none;
}
#adyen-cc-form .fieldset > .field > .label, .fieldset > .fields > .field > .label {
font-weight: 400;
}
#adyen-cc-form .helper-text{
font-size: 11px;
color: rgb(144, 162, 189);
font-weight: 100;
}
\ No newline at end of file
...@@ -29,133 +29,155 @@ define( ...@@ -29,133 +29,155 @@ define(
'Magento_Checkout/js/model/payment/additional-validators', 'Magento_Checkout/js/model/payment/additional-validators',
'Magento_Checkout/js/model/quote', 'Magento_Checkout/js/model/quote',
'Adyen_Payment/js/model/installments', 'Adyen_Payment/js/model/installments',
'mage/url' 'mage/url',
'Adyen_Payment/js/adyen.2.0.0',
'Adyen_Payment/js/adyen.checkout'
], ],
function ($, ko, Component, customer, creditCardData, additionalValidators, quote, installments, url) { function ($, ko, Component, customer, creditCardData, additionalValidators, quote, installments, url) {
'use strict'; 'use strict';
var cvcLength = ko.observable(4);
return Component.extend({ return Component.extend({
defaults: { defaults: {
template: 'Adyen_Payment/payment/cc-form', template: 'Adyen_Payment/payment/cc-form',
creditCardOwner: '', creditCardOwner: '',
encryptedData: '',
setStoreCc: true, setStoreCc: true,
installment: '' installment: '',
creditCardDetailsValid: false
}, },
initObservable: function () { initObservable: function () {
this._super() this._super()
.observe([ .observe([
'creditCardType', 'creditCardType',
'creditCardExpYear',
'creditCardExpMonth',
'creditCardNumber',
'creditCardVerificationNumber',
'creditCardSsStartMonth',
'creditCardSsStartYear',
'selectedCardType',
'creditCardOwner', 'creditCardOwner',
'encryptedData', 'creditCardNumber',
'generationtime', 'securityCode',
'expiryMonth',
'expiryYear',
'setStoreCc', 'setStoreCc',
'installment' 'installment',
'creditCardDetailsValid'
]); ]);
return this; return this;
}, },
getInstallments: installments.getInstallments(), getInstallments: installments.getInstallments(),
initialize: function () { /**
* Renders the secure fields,
* creates the card component,
* sets up the callbacks for card components and
* set up the installments
*/
renderSecureFields: function() {
var self = this; var self = this;
this._super();
self.creditCardOwner.subscribe(function () {
self.updateButton();
});
installments.setInstallments(0); installments.setInstallments(0);
// include secure fields sdk javascript // installments enabled ??
var secureFieldsScriptTag = document.createElement('script'); var allInstallments = self.getAllInstallments();
secureFieldsScriptTag.id = "secure-fields-script-tag"; var cardNode = document.getElementById('cardContainer');
secureFieldsScriptTag.src = this.getSecureFieldsSource();
secureFieldsScriptTag.type = "text/javascript";
document.body.appendChild(secureFieldsScriptTag)
//Set credit card number to credit card data object var checkout = new Adyen.Checkout({
this.creditCardNumber.subscribe(function (value) { locale: window.checkoutConfig.payment.adyenCc.locale
});
// installments enabled ?? var card = checkout.create('card', {
var allInstallments = self.getAllInstallments(); originKey: window.checkoutConfig.payment.adyenCc.originKey,
loadingContext: window.checkoutConfig.payment.adyenCc.checkoutUrl,
type: 'card',
groupTypes: self.getAvailableCardTypeAltCodes(),
// what card is this ?? onChange: function(state) {
// what card is this ??
// translate adyen card type to magento card type
var creditCardType = self.getCcCodeByAltCode(state.brand);
if (creditCardData.creditCard) { if (creditCardType) {
var creditcardType = creditCardData.creditCard.type; /* If the credit card type is already set, check if it changed or not */
if (!self.creditCardType() || self.creditCardType() && self.creditCardType() != creditCardType) {
if (creditCardType in allInstallments) {
cvcLength(4); // get for the creditcard the installments
if (creditcardType != "AE") { var installmentCreditcard = allInstallments[creditCardType];
cvcLength(3); var grandTotal = quote.totals().grand_total;
}
if (creditcardType in allInstallments) { var numberOfInstallments = [];
var dividedAmount = 0;
// get for the creditcard the installments var dividedString = "";
var installmentCreditcard = allInstallments[creditcardType]; $.each(installmentCreditcard, function (amount, installment) {
var grandTotal = quote.totals().grand_total;
if (grandTotal >= amount) {
var numberOfInstallments = []; dividedAmount = (grandTotal / installment).toFixed(quote.getPriceFormat().precision);
var dividedAmount = 0; dividedString = installment + " x " + dividedAmount + " " + quote.totals().quote_currency_code;
var dividedString = ""; numberOfInstallments.push({
$.each(installmentCreditcard, function (amount, installment) { key: [dividedString],
value: installment
if (grandTotal >= amount) { });
dividedAmount = (grandTotal / installment).toFixed(quote.getPriceFormat().precision); }
dividedString = installment + " x " + dividedAmount + " " + quote.totals().quote_currency_code; else {
numberOfInstallments.push({ return false;
key: [dividedString], }
value: installment
}); });
} }
if (numberOfInstallments) {
installments.setInstallments(numberOfInstallments);
}
else { else {
return false; installments.setInstallments(0);
} }
}); }
}
if (numberOfInstallments) { // Color the image of the credit card
installments.setInstallments(numberOfInstallments); self.creditCardType(creditCardType);
}else{
self.creditCardType("")
} }
else {
installments.setInstallments(0); if (state.isValid) {
// Here we enable the button if the component is now valid
self.creditCardNumber(state.data.encryptedCardNumber);
self.expiryMonth(state.data.encryptedExpiryMonth);
self.expiryYear(state.data.encryptedExpiryYear);
self.securityCode(state.data.encryptedSecurityCode);
self.creditCardDetailsValid(true);
}else{
self.creditCardDetailsValid(false);
} }
}
self.updateButton();
},
onError: function() {}
}); });
card.mount(cardNode);
self.isPlaceOrderActionAllowed(false);
}, },
setPlaceOrderHandler: function (handler) { /**
this.placeOrderHandler = handler; * Builds the payment details part of the payment information reqeust
}, *
setValidateHandler: function (handler) { * @returns {{method: *, additional_data: {cc_type: *, number: *, cvc, expiryMonth: *, expiryYear: *, holderName: *, generationtime: *, store_cc: *, number_of_installments: *}}}
this.validateHandler = handler; */
},
getCode: function () {
return 'adyen_cc';
},
getOriginKey: function () {
return window.checkoutConfig.payment.adyenCc.originKey;
},
getData: function () { getData: function () {
return { return {
'method': this.item.method, 'method': this.item.method,
additional_data: { additional_data: {
'cc_type': this.creditCardType(), 'cc_type': this.creditCardType(),
'encrypted_data': this.encryptedData(), 'number': this.creditCardNumber(),
'generationtime': this.generationtime(), 'cvc': this.securityCode(),
'expiryMonth': this.expiryMonth(),
'expiryYear': this.expiryYear(),
'holderName': this.creditCardOwner(),
'generationtime': this.getGenerationTime(),
'store_cc': this.setStoreCc(), 'store_cc': this.setStoreCc(),
'number_of_installments': this.installment() 'number_of_installments': this.installment()
} }
}; };
}, },
getCvcLength: function () {
return cvcLength();
},
isActive: function () {
return true;
},
/** /**
* Returns state of place order button * Returns state of place order button
* @returns {boolean} * @returns {boolean}
...@@ -163,9 +185,26 @@ define( ...@@ -163,9 +185,26 @@ define(
isButtonActive: function() { isButtonActive: function() {
return this.isActive() && this.getCode() == this.isChecked() && this.isPlaceOrderActionAllowed(); return this.isActive() && this.getCode() == this.isChecked() && this.isPlaceOrderActionAllowed();
}, },
/**
* Checks if the pay button can be enabled and enables if can
*/
updateButton: function() {
var self = this;
if (self.isCardOwnerValid() && self.isCreditCardDetailsValid()) {
self.isPlaceOrderActionAllowed(true);
} else {
self.isPlaceOrderActionAllowed(false);
}
},
/** /**
* Custom place order function
*
* @override * @override
*
* @param data
* @param event
* @returns {boolean}
*/ */
placeOrder: function (data, event) { placeOrder: function (data, event) {
var self = this; var self = this;
...@@ -174,22 +213,6 @@ define( ...@@ -174,22 +213,6 @@ define(
event.preventDefault(); event.preventDefault();
} }
var options = {};
var cseInstance = adyen.createEncryption(options);
var generationtime = this.getGenerationTime();
var cardData = {
number: this.creditCardNumber(),
cvc: this.creditCardVerificationNumber(),
expiryMonth: this.creditCardExpMonth(),
expiryYear: this.creditCardExpYear(),
holderName: this.creditCardOwner(),
generationtime: generationtime
};
var data = cseInstance.encrypt(cardData);
this.encryptedData(data);
if (this.validate() && additionalValidators.validate()) { if (this.validate() && additionalValidators.validate()) {
this.isPlaceOrderActionAllowed(false); this.isPlaceOrderActionAllowed(false);
...@@ -214,24 +237,88 @@ define( ...@@ -214,24 +237,88 @@ define(
return false; return false;
}, },
getControllerName: function () { /**
return window.checkoutConfig.payment.iframe.controllerName[this.getCode()]; * Validates the payment date when clicking the pay button
*
* @returns {boolean}
*/
validate: function () {
var self = this;
var form = 'form[data-role=adyen-cc-form]';
var validate = $(form).validation() && $(form).validation('isValid');
var owner = Boolean($(form + ' #creditCardHolderName').valid());
if (!validate || !owner) {
return false;
}
return true;
}, },
getPlaceOrderUrl: function () { /**
return window.checkoutConfig.payment.iframe.placeOrderUrl[this.getCode()]; * Validates if the typed in card holder is valid
* - length validation, can not be empty
*
* @returns {boolean}
*/
isCardOwnerValid: function() {
if (this.creditCardOwner().length == 0) {
return false;
}
return true;
}, },
context: function () { /**
return this; * The card component send the card details validity in a callback which is saved in the
* creditCardDetailsValid observable
*
* @returns {*}
*/
isCreditCardDetailsValid: function() {
return this.creditCardDetailsValid();
}, },
/**
* Translates the card type alt code (used in Adyen) to card type code (used in Magento) if it's available
*
* @param altCode
* @returns {*}
*/
getCcCodeByAltCode: function(altCode) {
var ccTypes = window.checkoutConfig.payment.ccform.availableTypesByAlt[this.getCode()];
if (ccTypes.hasOwnProperty(altCode)) {
return ccTypes[altCode];
}
isCseEnabled: function () { return "";
return window.checkoutConfig.payment.adyenCc.cseEnabled;
}, },
getCSEKey: function () { /**
return window.checkoutConfig.payment.adyenCc.cseKey; * Get available card types translated to the Adyen card type codes
* (The card type alt code is the Adyen card type code)
*
* @returns {string[]}
*/
getAvailableCardTypeAltCodes: function() {
var ccTypes = window.checkoutConfig.payment.ccform.availableTypesByAlt[this.getCode()];
return Object.keys(ccTypes);
}, },
getSecureFieldsSource: function () { /**
return window.checkoutConfig.payment.adyenCc.secureFieldsSource; * Return Payment method code
*
* @returns {*}
*/
getCode: function () {
return window.checkoutConfig.payment.adyenCc.methodCode;
},
isActive: function () {
return true;
},
getControllerName: function () {
return window.checkoutConfig.payment.iframe.controllerName[this.getCode()];
},
getPlaceOrderUrl: function () {
return window.checkoutConfig.payment.iframe.placeOrderUrl[this.getCode()];
}, },
getGenerationTime: function () { getGenerationTime: function () {
return window.checkoutConfig.payment.adyenCc.generationTime; return window.checkoutConfig.payment.adyenCc.generationTime;
...@@ -240,30 +327,12 @@ define( ...@@ -240,30 +327,12 @@ define(
if (customer.isLoggedIn()) { if (customer.isLoggedIn()) {
return window.checkoutConfig.payment.adyenCc.canCreateBillingAgreement; return window.checkoutConfig.payment.adyenCc.canCreateBillingAgreement;
} }
return false; return false;
}, },
isShowLegend: function () { isShowLegend: function () {
return true; return true;
}, },
validate: function () {
var form = 'form[data-role=adyen-cc-form]';
var validate = $(form).validation() && $(form).validation('isValid');
// add extra validation because jquery validation will not work on non name attributes
var ccNumber = Boolean($(form + ' #creditCardNumber').valid());
var owner = Boolean($(form + ' #creditCardHolderName').valid());
var expiration = Boolean($(form + ' #adyen_cc_expiration').valid());
var expiration_yr = Boolean($(form + ' #adyen_cc_expiration_yr').valid());
var cid = Boolean($(form + ' #adyen_cc_cc_cid').valid());
if (!validate || !ccNumber || !owner || !expiration || !expiration_yr || !cid) {
return false;
}
return true;
},
showLogo: function () { showLogo: function () {
return window.checkoutConfig.payment.adyen.showLogo; return window.checkoutConfig.payment.adyen.showLogo;
}, },
...@@ -277,9 +346,16 @@ define( ...@@ -277,9 +346,16 @@ define(
}, },
getAllInstallments: function () { getAllInstallments: function () {
return window.checkoutConfig.payment.adyenCc.installments; return window.checkoutConfig.payment.adyenCc.installments;
},
setPlaceOrderHandler: function (handler) {
this.placeOrderHandler = handler;
},
setValidateHandler: function (handler) {
this.validateHandler = handler;
},
context: function () {
return this;
} }
}); });
} }
); );
...@@ -68,14 +68,37 @@ ...@@ -68,14 +68,37 @@
<br/> <br/>
<!-- /ko --> <!-- /ko -->
<div class="field type required"> <div class="field holdername type">
<label data-bind="attr: {for: 'creditCardHolderName'}" class="label">
<span><!-- ko text: $t('Credit Card Owner')--><!-- /ko --></span>
</label>
<div class="control">
<input type="text"
class="input-text required-entry"
data-encrypted-name="holderName"
value=""
data-bind="attr: {
id: 'creditCardHolderName',
title: $t('Credit Card Owner'),
placeholder: $t('Credit Card Owner'),
'data-container': getCode() + '-cc-owner'
},
enable: isActive($parents),
value: creditCardOwner,
valueUpdate: 'keyup' "
data-validate="{required:true}"
/>
</div>
</div>
<div class="field type">
<label data-bind="attr: {for: getCode() + '_cc_type'}" class="label"> <label data-bind="attr: {for: getCode() + '_cc_type'}" class="label">
<span><!-- ko text: $t('Credit Card Type')--><!-- /ko --></span> <span><!-- ko text: $t('Credit Card Type')--><!-- /ko --></span>
</label> </label>
<div class="control"> <div class="control">
<ul class="credit-card-types"> <ul class="credit-card-types">
<!-- ko foreach: {data: getCcAvailableTypesValues(), as: 'item'} --> <!-- ko foreach: {data: getCcAvailableTypesValues(), as: 'item'} -->
<li class="item" data-bind="css: {_active: $parent.selectedCardType() == item.value} "> <li class="item" data-bind="css: {_active: $parent.creditCardType() == item.value} ">
<!--ko if: $parent.getIcons(item.value) --> <!--ko if: $parent.getIcons(item.value) -->
<img data-bind="attr: { <img data-bind="attr: {
'src': $parent.getIcons(item.value).url, 'src': $parent.getIcons(item.value).url,
...@@ -87,6 +110,7 @@ ...@@ -87,6 +110,7 @@
</li> </li>
<!--/ko--> <!--/ko-->
</ul> </ul>
<p class="helper-text" data-bind="css: {hidden: creditCardType() !== ''} "><!-- ko text: $t('(Please provide a card with the type from the list above)')--><!-- /ko --></p>
<input type="hidden" <input type="hidden"
name="payment[cc_type]" name="payment[cc_type]"
class="input-text" class="input-text"
...@@ -96,121 +120,11 @@ ...@@ -96,121 +120,11 @@
"> ">
</div> </div>
</div> </div>
<div class="field number required"> <div class="field number cardContainerField">
<label data-bind="attr: {for: 'creditCardNumber'}" class="label"> <div afterRender="renderSecureFields()" data-bind="attr: { id: 'cardContainer'}" ></div>
<span><!-- ko text: $t('Credit Card Number')--><!-- /ko --></span>
</label>
<div class="control">
<input type="tel" class="input-text" value=""
data-encrypted-name="number"
data-bind="attr: {
autocomplete: off,
id: 'creditCardNumber',
title: $t('Credit Card Number'),
'data-container': getCode() + '-cc-number',
'data-validate': JSON.stringify({'required-number':true, 'validate-card-type':getCcAvailableTypesValues(), 'validate-card-number':'#' + getCode() + '_cc_type', 'validate-cc-type':'#' + getCode() + '_cc_type'})},
enable: isActive($parents),
value: creditCardNumber,
valueUpdate: 'keyup' "/>
</div>
</div> </div>
<div class="field holdername type required">
<label data-bind="attr: {for: 'creditCardHolderName'}" class="label">
<span><!-- ko text: $t('Credit Card Owner')--><!-- /ko --></span>
</label>
<div class="control">
<input type="text"
class="input-text required-entry"
data-encrypted-name="holderName"
value=""
data-bind="attr: {
id: 'creditCardHolderName',
title: $t('Credit Card Owner'),
'data-container': getCode() + '-cc-owner'
},
enable: isActive($parents),
value: creditCardOwner,
valueUpdate: 'keyup' "
data-validate="{required:true}"
/>
</div>
</div>
<div class="field date required" data-bind="attr: {id: getCode() + '_cc_type_exp_div'}">
<label data-bind="attr: {for: 'cardExpirationMonth'}" class="label">
<span><!-- ko text: $t('Expiration Date')--><!-- /ko --></span>
</label>
<div class="control">
<div class="fields group group-2">
<div class="field no-label month">
<div class="control">
<select class="select select-month"
data-encrypted-name="expiryMonth"
data-bind="attr: {id: getCode() + '_expiration', 'data-container': getCode() + '-cc-month', 'data-validate': JSON.stringify({required:true, 'validate-cc-exp':'#' + getCode() + '_expiration_yr'})},
enable: isActive($parents),
options: getCcMonthsValues(),
optionsValue: 'value',
optionsText: 'month',
optionsCaption: $t('Month'),
value: creditCardExpMonth"
data-validate="{required:true}">
</select>
</div>
</div>
<div class="field no-label year">
<div class="control">
<select class="select select-year"
data-encrypted-name="expiryYear"
data-bind="attr: {id: getCode() + '_expiration_yr', 'data-container': getCode() + '-cc-year', 'data-validate': JSON.stringify({required:true})},
enable: isActive($parents),
options: getCcYearsValues(),
optionsValue: 'value',
optionsText: 'year',
optionsCaption: $t('Year'),
value: creditCardExpYear"
data-validate="{required:true}">
</select>
</div>
</div>
</div>
</div>
</div>
<!-- ko if: (hasVerification())-->
<div class="field cvv required" data-bind="attr: {id: getCode() + '_cc_type_cvv_div'}">
<label data-bind="attr: {for: getCode() + '_cc_cid'}" class="label">
<span><!-- ko text: $t('Card Verification Number')--><!-- /ko --></span>
</label>
<div class="control _with-tooltip">
<input type="number"
autocomplete="off"
class="input-text cvv"
data-encrypted-name="cvc"
value=""
data-bind="attr: {
id: getCode() + '_cc_cid',
title: $t('Card Verification Number'),
'data-container': getCode() + '-cc-cvv',
'data-validate': JSON.stringify({'required-number':true, 'validate-card-cvv':'#' + getCode() + '_cc_type'}),
maxLength : getCvcLength(),
oninput:'javascript: if (this.value.length > this.maxLength) this.value = this.value.slice(0, this.maxLength);'
},
enable: isActive($parents),
value: creditCardVerificationNumber" ,
data-validate="{required:true}"
/>
<div class="field-tooltip toggle">
<span class="field-tooltip-action action-cvv"
tabindex="0"
data-toggle="dropdown"
data-bind="attr: {title: $t('What is this?')}, mageInit: {'dropdown':{'activeClass': '_active'}}">
<span><!-- ko text: $t('What is this?')--><!-- /ko --></span>
</span>
<div class="field-tooltip-content"
data-target="dropdown"
data-bind="html: getCvvImageHtml()"></div>
</div>
</div>
</div>
<!-- /ko -->
<!-- ko if: (hasInstallments())--> <!-- ko if: (hasInstallments())-->
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment