diff --git a/Controller/Return/Index.php b/Controller/Return/Index.php index 0cfba293e..b68f4a322 100755 --- a/Controller/Return/Index.php +++ b/Controller/Return/Index.php @@ -161,25 +161,15 @@ protected function validateRedirectResponse(array $redirectResponse): bool $paymentsDetailsResponse['error'] = $e->getMessage(); } - $result = false; - - // Compare the merchant references - $merchantReference = $paymentsDetailsResponse['merchantReference'] ?? null; - if ($merchantReference) { - if ($order->getIncrementId() === $merchantReference) { - $this->order = $order; - $this->payment = $order->getPayment(); - $this->cleanUpRedirectAction(); - - $result = $this->paymentResponseHandler->handlePaymentsDetailsResponse( - $paymentsDetailsResponse, - $order - ); - } else { - $this->adyenLogger->error("Wrong merchantReference was set in the query or in the session"); - } - } else { - $this->adyenLogger->error("No merchantReference in the response"); + $result = $this->paymentResponseHandler->handlePaymentsDetailsResponse( + $paymentsDetailsResponse, + $order + ); + + if ($result) { + $this->order = $order; + $this->payment = $order->getPayment(); + $this->cleanUpRedirectAction(); } return $result; diff --git a/Helper/PaymentResponseHandler.php b/Helper/PaymentResponseHandler.php index 6c11537a9..8c3808222 100644 --- a/Helper/PaymentResponseHandler.php +++ b/Helper/PaymentResponseHandler.php @@ -139,6 +139,10 @@ public function handlePaymentsDetailsResponse( return false; } + if(!$this->isValidMerchantReference($paymentsDetailsResponse, $order)){ + return false; + } + $this->adyenLogger->addAdyenResult('Updating the order'); $payment = $order->getPayment(); @@ -312,4 +316,27 @@ public function handlePaymentsDetailsResponse( return $result; } + + /** + * Validate whether the merchant reference is present in the response and belongs to the current order. + * + * @param array $paymentsDetailsResponse + * @param OrderInterface $order + * @return bool + */ + private function isValidMerchantReference(array $paymentsDetailsResponse, OrderInterface $order): bool + { + $merchantReference = $paymentsDetailsResponse['merchantReference'] ?? null; + if (!$merchantReference) { + $this->adyenLogger->error("No merchantReference in the response"); + return false; + } + + if ($order->getIncrementId() !== $merchantReference) { + $this->adyenLogger->error("Wrong merchantReference was set in the query or in the session"); + return false; + } + + return true; + } } diff --git a/Test/Unit/Helper/PaymentResponseHandlerTest.php b/Test/Unit/Helper/PaymentResponseHandlerTest.php index 8a5b0fc76..6f88669d5 100644 --- a/Test/Unit/Helper/PaymentResponseHandlerTest.php +++ b/Test/Unit/Helper/PaymentResponseHandlerTest.php @@ -72,6 +72,7 @@ protected function setUp(): void $this->orderMock->method('getQuoteId')->willReturn(1); $this->orderMock->method('getPayment')->willReturn($this->paymentMock); $this->orderMock->method('getStatus')->willReturn('pending'); + $this->orderMock->method('getIncrementId')->willReturn('00123456'); $this->orderHelperMock->method('setStatusOrderCreation')->willReturn( $this->orderMock); @@ -117,7 +118,7 @@ public function testFormatPaymentResponseForFinalResultCodes($resultCode) $this->assertEquals($expectedResult, $result); } - private static function dataSourceForFormatPaymentResponseActionRequredPayments(): array + private static function dataSourceForFormatPaymentResponseActionRequiredPayments(): array { return [ ['resultCode' => PaymentResponseHandler::REDIRECT_SHOPPER, 'action' => ['type' => 'qrCode']], @@ -131,7 +132,7 @@ private static function dataSourceForFormatPaymentResponseActionRequredPayments( * @param $resultCode * @param $action * @return void - * @dataProvider dataSourceForFormatPaymentResponseActionRequredPayments + * @dataProvider dataSourceForFormatPaymentResponseActionRequiredPayments */ public function testFormatPaymentResponseForActionRequiredPayments($resultCode, $action) { @@ -239,7 +240,8 @@ public function testHandlePaymentsDetailsResponseAuthorised() 'details' => [ 'someData' => 'someValue' ], - 'donationToken' => 'XYZ123456789' + 'donationToken' => 'XYZ123456789', + 'merchantReference' => '00123456' ]; $this->quoteHelperMock->method('disableQuote')->willThrowException(new Exception()); @@ -281,7 +283,8 @@ public function testHandlePaymentsDetailsResponsePending($paymentMethodCode) 'pspReference' => 'ABC123456789', 'paymentMethod' => [ 'brand' => $paymentMethodCode - ] + ], + 'merchantReference' => '00123456' ]; $result = $this->paymentResponseHandler->handlePaymentsDetailsResponse( @@ -314,7 +317,8 @@ public function testHandlePaymentsDetailsResponseReceived($paymentMethodCode, $e 'pspReference' => 'ABC123456789', 'paymentMethod' => [ 'brand' => $paymentMethodCode - ] + ], + 'merchantReference' => '00123456' ]; $result = $this->paymentResponseHandler->handlePaymentsDetailsResponse( @@ -350,6 +354,7 @@ public function testHandlePaymentsDetailsResponseActionRequired($resultCode) 'paymentMethod' => [ 'brand' => 'ideal' ], + 'merchantReference' => '00123456', 'action' => [ 'actionData' => 'actionValue' ] @@ -388,6 +393,7 @@ public function testHandlePaymentsDetailsResponseCancelOrRefused($resultCode) 'paymentMethod' => [ 'brand' => 'ideal' ], + 'merchantReference' => '00123456', 'action' => [ 'actionData' => 'actionValue' ] @@ -431,4 +437,22 @@ public function testHandlePaymentsDetailsEmptyResponse() $this->assertFalse($result); } + + public function testHandlePaymentsDetailsResponseInvalidMerchantReference(){ + $paymentsDetailsResponse = [ + 'resultCode' => PaymentResponseHandler::AUTHORISED, + 'pspReference' => 'ABC123456789', + 'paymentMethod' => [ + 'brand' => 'ideal' + ], + 'merchantReference' => '00777777' + ]; + + $result = $this->paymentResponseHandler->handlePaymentsDetailsResponse( + $paymentsDetailsResponse, + $this->orderMock + ); + + $this->assertFalse($result); + } }