jenkins-bot has submitted this change and it was merged. (
https://gerrit.wikimedia.org/r/345790 )
Change subject: Cache directory lookup 404s
......................................................................
Cache directory lookup 404s
These are legitimate responses in REST-ese. Don't failmail when
someone tries to pay with iDEAL in an unsupported currency.
We should still route them elsewhere in the frontend, tho!
Bug: T161072
Change-Id: I28a1bc71ffc7a8982b686028ab53a558032de3c7
---
M Core/Http/HttpStatusValidator.php
M PaymentProviders/Ingenico/Api.php
M PaymentProviders/Ingenico/ApiException.php
M PaymentProviders/Ingenico/BankPaymentProvider.php
A PaymentProviders/Ingenico/RestResponseValidator.php
A PaymentProviders/Ingenico/Tests/Data/emptyDirectory.response
M PaymentProviders/Ingenico/Tests/phpunit/BankPaymentProviderTest.php
M SmashPig.yaml
8 files changed, 90 insertions(+), 13 deletions(-)
Approvals:
jenkins-bot: Verified
Awight: Looks good to me, approved
diff --git a/Core/Http/HttpStatusValidator.php
b/Core/Http/HttpStatusValidator.php
index a36230b..68c6859 100644
--- a/Core/Http/HttpStatusValidator.php
+++ b/Core/Http/HttpStatusValidator.php
@@ -12,16 +12,13 @@
public function shouldRetry( $parsedResponse ) {
$statusCode = $parsedResponse['status'];
+ if ( array_search( $statusCode, $this->getSuccessCodes() ) !==
false ) {
+ Logger::debug( "Successful request" );
+ return false;
+ }
$body = $parsedResponse['body'];
switch ( $statusCode ) {
- case 200: // Everything is AWESOME
- case 201: // Also fine, and we created a thing
- $continue = false;
-
- Logger::debug( "Successful request" );
- break;
-
case 400: // Oh noes! Bad request.. BAD CODE, BAD BAD
CODE!
$continue = false;
Logger::error( "Request returned (400) BAD
REQUEST: $body" );
@@ -39,4 +36,11 @@
}
return $continue;
}
+
+ protected function getSuccessCodes() {
+ return array(
+ 200, // Everything is AWESOME
+ 201 // Also fine, and we created a thing
+ );
+ }
}
diff --git a/PaymentProviders/Ingenico/Api.php
b/PaymentProviders/Ingenico/Api.php
index 5da77bb..3a7f0cc 100644
--- a/PaymentProviders/Ingenico/Api.php
+++ b/PaymentProviders/Ingenico/Api.php
@@ -84,7 +84,9 @@
$messages[] = "Error code {$error['code']}:
{$error['message']}.";
}
$concatenated = implode( ' ', $messages );
- throw new ApiException( $concatenated );
+ $ex = new ApiException( $concatenated );
+ $ex->setRawErrors( $decoded['errors'] );
+ throw $ex;
}
}
}
diff --git a/PaymentProviders/Ingenico/ApiException.php
b/PaymentProviders/Ingenico/ApiException.php
index 44af1fc..3f3ed73 100644
--- a/PaymentProviders/Ingenico/ApiException.php
+++ b/PaymentProviders/Ingenico/ApiException.php
@@ -6,4 +6,13 @@
class ApiException extends SmashPigException {
+ protected $rawErrors;
+
+ public function setRawErrors( $errors ) {
+ $this->rawErrors = $errors;
+ }
+
+ public function getRawErrors() {
+ return $this->rawErrors;
+ }
}
diff --git a/PaymentProviders/Ingenico/BankPaymentProvider.php
b/PaymentProviders/Ingenico/BankPaymentProvider.php
index 87c034d..0f5b237 100644
--- a/PaymentProviders/Ingenico/BankPaymentProvider.php
+++ b/PaymentProviders/Ingenico/BankPaymentProvider.php
@@ -2,8 +2,9 @@
namespace SmashPig\PaymentProviders\Ingenico;
-use SmashPig\Core\Context;
use Psr\Cache\CacheItemPoolInterface;
+use SmashPig\Core\Context;
+use Symfony\Component\HttpFoundation\Response;
/**
* Handle bank payments via Ingenico
@@ -50,12 +51,21 @@
'currencyCode' => $currency
);
$path = "products/$productId/directory";
- $response = $this->api->makeApiCall( $path, 'GET',
$query );
-
$banks = array();
- foreach ( $response['entries'] as $entry ) {
- $banks[$entry['issuerId']] =
$entry['issuerName'];
+ try {
+ $response = $this->api->makeApiCall( $path,
'GET', $query );
+
+ foreach ( $response['entries'] as $entry ) {
+ $banks[$entry['issuerId']] =
$entry['issuerName'];
+ }
+ } catch ( ApiException $ex ) {
+ $errors = $ex->getRawErrors();
+ if ( empty( $errors ) ||
$errors[0]['httpStatusCode'] !== Response::HTTP_NOT_FOUND ) {
+ throw $ex;
+ }
+ // If there is a single 404 error, that means
there is no directory info for
+ // the country/currency/product. That's
legitimate, so cache the empty array
}
$duration = $this->cacheParameters['duration'];
$cacheItem->set( array(
diff --git a/PaymentProviders/Ingenico/RestResponseValidator.php
b/PaymentProviders/Ingenico/RestResponseValidator.php
new file mode 100644
index 0000000..0a74d33
--- /dev/null
+++ b/PaymentProviders/Ingenico/RestResponseValidator.php
@@ -0,0 +1,12 @@
+<?php
+namespace SmashPig\PaymentProviders\Ingenico;
+
+use SmashPig\Core\Http\HttpStatusValidator;
+
+class RestResponseValidator extends HttpStatusValidator {
+ protected function getSuccessCodes() {
+ $codes = parent::getSuccessCodes();
+ $codes[] = '404'; // also a valid response in REST-ese
+ return $codes;
+ }
+}
diff --git a/PaymentProviders/Ingenico/Tests/Data/emptyDirectory.response
b/PaymentProviders/Ingenico/Tests/Data/emptyDirectory.response
new file mode 100644
index 0000000..984a385
--- /dev/null
+++ b/PaymentProviders/Ingenico/Tests/Data/emptyDirectory.response
@@ -0,0 +1,16 @@
+HTTP/1.1 404 Not Found
+Date: Mon, 27 Mar 2017 12:08:10 GMT
+Server: Apache/2.4.23 (Unix) OpenSSL/1.0.1t
+X-Powered-By: Servlet/3.0 JSP/2.2
+Transfer-Encoding: chunked
+Content-Type: application/json
+
+{
+ "errorId" : "2036059b-1138-42b0-8734-21d669a79d44",
+ "errors" : [ {
+ "code" : "210390",
+ "message" : "NO DIRECTORY FOUND",
+ "httpStatusCode" : 404
+ } ]
+}
+
diff --git
a/PaymentProviders/Ingenico/Tests/phpunit/BankPaymentProviderTest.php
b/PaymentProviders/Ingenico/Tests/phpunit/BankPaymentProviderTest.php
index d9a2e3e..6a47874 100644
--- a/PaymentProviders/Ingenico/Tests/phpunit/BankPaymentProviderTest.php
+++ b/PaymentProviders/Ingenico/Tests/phpunit/BankPaymentProviderTest.php
@@ -69,6 +69,21 @@
$this->assertEquals( $results, $cachedResults );
}
+ /**
+ * When the lookup returns 404 we should cache the emptiness
+ */
+ public function testCacheEmptyBankList() {
+ $this->setUpResponse( 'emptyDirectory', 404 );
+ $this->curlWrapper->expects( $this->once() )
+ ->method( 'execute' );
+ $results = $this->provider->getBankList( 'NL', 'COP' );
+ $this->assertEquals( array(), $results );
+ $cached = $this->cache->getItem( 'BLAH_BLAH_NL_COP_809' );
+ $this->assertTrue( $cached->isHit() );
+ $again = $this->provider->getBankList( 'NL', 'COP' );
+ $this->assertEquals( $results, $again );
+ }
+
public function testBustedCacheExpiration() {
$cacheItem = new HashCacheItem(
'BLAH_BLAH_NL_EUR_809',
@@ -91,6 +106,12 @@
);
}
+ /**
+ * @param string $filename Name of a file in ../Data representing a
+ * response (headers, blank line, body), which must use dos-style
+ * \r\n line endings.
+ * @param integer $statusCode
+ */
protected function setUpResponse( $filename, $statusCode ) {
$contents = file_get_contents( __DIR__ .
"/../Data/$filename.response" );
$parsed = CurlWrapper::parseResponse(
diff --git a/SmashPig.yaml b/SmashPig.yaml
index 19e2f1b..ac7159b 100644
--- a/SmashPig.yaml
+++ b/SmashPig.yaml
@@ -477,6 +477,9 @@
key: SMASHPIG_IDEAL_BANK_STATUS
availability-url:
https://availability.ideal.nl/api/api/GetIssuers
+ curl:
+ validator:
+ class: SmashPig\PaymentProviders\Ingenico\RestResponseValidator
# deprecated, delete when projects using SmashPig rename adaptors
globalcollect:
--
To view, visit https://gerrit.wikimedia.org/r/345790
To unsubscribe, visit https://gerrit.wikimedia.org/r/settings
Gerrit-MessageType: merged
Gerrit-Change-Id: I28a1bc71ffc7a8982b686028ab53a558032de3c7
Gerrit-PatchSet: 3
Gerrit-Project: wikimedia/fundraising/SmashPig
Gerrit-Branch: master
Gerrit-Owner: Ejegg <[email protected]>
Gerrit-Reviewer: Awight <[email protected]>
Gerrit-Reviewer: Cdentinger <[email protected]>
Gerrit-Reviewer: Ejegg <[email protected]>
Gerrit-Reviewer: jenkins-bot <>
_______________________________________________
MediaWiki-commits mailing list
[email protected]
https://lists.wikimedia.org/mailman/listinfo/mediawiki-commits