| 1 |
<?php |
| 2 |
|
| 3 |
namespace IvyForms\Services\Payment; |
| 4 |
|
| 5 |
use IvyForms\Services\Translations\BackendStrings; |
| 6 |
|
| 7 |
/** |
| 8 |
* Maps Square Payments API HTTP responses to the gateway result shape. |
| 9 |
*/ |
| 10 |
final class SquarePaymentResponseParser |
| 11 |
{ |
| 12 |
/** |
| 13 |
* @param array<string, mixed>|\WP_Error $response |
| 14 |
* @return array<string, mixed> |
| 15 |
*/ |
| 16 |
public static function fromHttp($response): array |
| 17 |
{ |
| 18 |
$status = (int) wp_remote_retrieve_response_code($response); |
| 19 |
$decoded = json_decode((string) wp_remote_retrieve_body($response), true); |
| 20 |
|
| 21 |
if ($status < 200 || $status >= 300 || !is_array($decoded)) { |
| 22 |
return self::failure(self::extractErrorMessage($decoded)); |
| 23 |
} |
| 24 |
|
| 25 |
return self::fromSuccessfulBody($decoded); |
| 26 |
} |
| 27 |
|
| 28 |
/** |
| 29 |
* @return array<string, mixed> |
| 30 |
*/ |
| 31 |
public static function failure(string $message): array |
| 32 |
{ |
| 33 |
return [ |
| 34 |
'success' => false, |
| 35 |
'message' => $message, |
| 36 |
]; |
| 37 |
} |
| 38 |
|
| 39 |
/** |
| 40 |
* @param array<string, mixed> $decoded |
| 41 |
* @return array<string, mixed> |
| 42 |
*/ |
| 43 |
private static function fromSuccessfulBody(array $decoded): array |
| 44 |
{ |
| 45 |
$payment = is_array($decoded['payment'] ?? null) ? $decoded['payment'] : []; |
| 46 |
$paymentStatus = (string) ($payment['status'] ?? ''); |
| 47 |
$transactionId = (string) ($payment['id'] ?? ''); |
| 48 |
|
| 49 |
if ($paymentStatus !== 'COMPLETED' || $transactionId === '') { |
| 50 |
return self::failure(BackendStrings::getPaymentStrings()['payment_failed']); |
| 51 |
} |
| 52 |
|
| 53 |
return [ |
| 54 |
'success' => true, |
| 55 |
'payment' => $payment, |
| 56 |
'transactionId' => $transactionId, |
| 57 |
'receiptUrl' => (string) ($payment['receipt_url'] ?? ''), |
| 58 |
]; |
| 59 |
} |
| 60 |
|
| 61 |
/** |
| 62 |
* @param mixed $decoded |
| 63 |
*/ |
| 64 |
private static function extractErrorMessage($decoded): string |
| 65 |
{ |
| 66 |
$fallback = BackendStrings::getPaymentStrings()['payment_failed']; |
| 67 |
if (!is_array($decoded) || empty($decoded['errors'][0])) { |
| 68 |
return $fallback; |
| 69 |
} |
| 70 |
|
| 71 |
$firstError = $decoded['errors'][0]; |
| 72 |
if (!empty($firstError['detail'])) { |
| 73 |
return (string) $firstError['detail']; |
| 74 |
} |
| 75 |
|
| 76 |
if (!empty($firstError['code'])) { |
| 77 |
return (string) $firstError['code']; |
| 78 |
} |
| 79 |
|
| 80 |
return $fallback; |
| 81 |
} |
| 82 |
} |
| 83 |
|