You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

SenangPayDriver.php 3.4KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115
  1. <?php
  2. namespace MirfalahTech\Laravel\Payment\Gateway\SenangPay;
  3. use Illuminate\Contracts\Config\Repository;
  4. use Illuminate\Http\Request;
  5. use Illuminate\Support\Facades\Response as Res;
  6. use MirfalahTech\Laravel\Payment\Contracts\PayableEntity;
  7. use MirfalahTech\Laravel\Payment\Contracts\PaymentGatewayDriver;
  8. use MirfalahTech\Laravel\Payment\Facade\Payment;
  9. use MirfalahTech\Laravel\Payment\Traits\BillStatusBoolean;
  10. use Symfony\Component\HttpFoundation\Response;
  11. class SenangPayDriver implements PaymentGatewayDriver
  12. {
  13. use BillStatusBoolean;
  14. /**
  15. * @var string
  16. */
  17. protected $endpoint;
  18. /**
  19. * @var string
  20. */
  21. protected $merchant_id;
  22. /**
  23. * @var string
  24. */
  25. protected $secret_key;
  26. /**
  27. * @var array
  28. */
  29. protected $keyMap;
  30. public function __construct(Repository $config, array $options)
  31. {
  32. $finalConfig = array_merge($config->get('payment.gateway'), $options);
  33. $this->endpoint = rtrim($finalConfig['endpoint'], '/');
  34. $this->merchant_id = $finalConfig['merchant_id'];
  35. $this->secret_key = $finalConfig['secret_key'];
  36. $this->keyMap = $finalConfig['key_map'];
  37. }
  38. public function createPaymentURL(PayableEntity $payable, array $options = []): string
  39. {
  40. return "$this->endpoint/payment/$this->merchant_id?" .
  41. http_build_query($this->preparePaymentParam($payable, $options));
  42. }
  43. public function verifyGatewayReturn(Request $request): bool
  44. {
  45. $hash = $request->query->get($this->keyMap['hash']);
  46. return $hash == $this->computeHash($request->request->all());
  47. }
  48. public function verifyGatewayCallback(Request $request, Response &$response = null): bool
  49. {
  50. $response = Res::make('OK');
  51. $hash = $request->request->get($this->keyMap['hash']);
  52. return $hash == $this->computeHash($request->request->all());
  53. }
  54. public function getBillIdFromRequest(Request $request): ?string
  55. {
  56. return $request->get($this->keyMap['order_id']);
  57. }
  58. public function getBillStatus(Request $request): ?int
  59. {
  60. $status = $request->get($this->keyMap['status_id']);
  61. if ($status == null) {
  62. return null;
  63. } else {
  64. return $status == 1 ? Payment::SUCCESS : Payment::PENDING;
  65. }
  66. }
  67. public function computeHash($payload)
  68. {
  69. $query = http_build_query($payload);
  70. $key = preg_quote(http_build_query([$this->keyMap['hash']=>'']), '/');
  71. $query = preg_replace('/(^|&)'.$key.'[^&]*($|&)/','$1hash=[HASH]$2', $query);
  72. return md5($this->secret_key . '?' . $query);
  73. }
  74. public function isPostMethodSupported(): bool
  75. {
  76. return true;
  77. }
  78. public function createPostMethodPayment(PayableEntity $payable, array $options = []): Response
  79. {
  80. $params = $this->preparePaymentParam($payable, $options);
  81. ob_start();
  82. include __DIR__.'../res/view/response.php';
  83. return new Response(ob_get_clean());
  84. }
  85. protected function preparePaymentParam(PayableEntity $payable, array $options = []): array{
  86. $detail = $payable->getBillDescription();
  87. $amount = $payable->getBillAmount();
  88. $order_id = $payable->getBillId();
  89. $detail = preg_replace('/[^A-Z0-9,\-_]/i', '_', $detail);
  90. $amount = sprintf('%0.2f', $amount);
  91. $hash = md5($this->secret_key . $detail . $amount . $order_id);
  92. return compact('detail', 'order_id', 'amount', 'hash');
  93. }
  94. }