Server.php 3.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121
  1. <?php
  2. namespace App\Libs\TikTok\MiniProgram\Pay;
  3. use Closure;
  4. use App\Libs\TikTok\Kernel\Exceptions\InvalidArgumentException;
  5. use App\Libs\TikTok\Kernel\Exceptions\RuntimeException;
  6. use App\Libs\TikTok\Kernel\Http\Response;
  7. use App\Libs\TikTok\Kernel\ServiceContainer;
  8. use App\Libs\TikTok\Kernel\Traits\InteractWithHandlers;
  9. use EasyWeChat\Kernel\Contracts\Server as ServerInterface;
  10. use Psr\Http\Message\ResponseInterface;
  11. use Psr\Http\Message\ServerRequestInterface;
  12. class Server implements ServerInterface
  13. {
  14. use InteractWithHandlers;
  15. protected ?ServerRequestInterface $request;
  16. /**
  17. * @var ServiceContainer
  18. */
  19. protected ServiceContainer $app;
  20. public function __construct(ServiceContainer $app)
  21. {
  22. $this->app = $app;
  23. }
  24. public function serve(): Response
  25. {
  26. $message = $this->getRequestMessage();
  27. try {
  28. $default_response = new Response(
  29. 200,
  30. [],
  31. strval(json_encode(['err_no' => 0, 'err_tips' => 'success'], JSON_UNESCAPED_UNICODE))
  32. );
  33. $response = $this->handle($default_response, $message);
  34. if (!($response instanceof ResponseInterface)) {
  35. $response = $default_response;
  36. }
  37. return $response;
  38. } catch (\Exception $e) {
  39. return new Response(
  40. 200,
  41. [],
  42. strval(json_encode(['err_no' => 400, 'message' => $e->getMessage()], JSON_UNESCAPED_UNICODE))
  43. );
  44. }
  45. }
  46. /**
  47. * @link https://pay.weixin.qq.com/wiki/doc/apiv3/apis/chapter3_1_5.shtml
  48. *
  49. * @throws InvalidArgumentException
  50. */
  51. public function handlePaid(callable $handler): static
  52. {
  53. $this->with(function (Message $message, Closure $next) use ($handler) {
  54. return $message->getType() === Message::TYPE_PAY
  55. ? $handler($message, $next) : $next($message);
  56. });
  57. return $this;
  58. }
  59. /**
  60. * @link https://pay.weixin.qq.com/wiki/doc/apiv3/apis/chapter3_1_11.shtml
  61. *
  62. * @throws InvalidArgumentException
  63. */
  64. public function handleRefunded(callable $handler): static
  65. {
  66. $this->with(function (Message $message, Closure $next) use ($handler) {
  67. return $message->getType() === Message::TYPE_REFUND
  68. ? $handler($message, $next) : $next($message);
  69. });
  70. return $this;
  71. }
  72. /**
  73. * @link https://developer.open-douyin.com/docs/resource/zh-CN/mini-app/develop/server/ecpay/settlements/callback
  74. *
  75. * @throws InvalidArgumentException
  76. */
  77. public function handleSettled(callable $handler): static
  78. {
  79. $this->with(function (Message $message, Closure $next) use ($handler) {
  80. return $message->getType() === Message::TYPE_SETTLED
  81. ? $handler($message, $next) : $next($message);
  82. });
  83. return $this;
  84. }
  85. public function setRequest(ServerRequestInterface $request): ServerRequestInterface
  86. {
  87. return $this->request = $request;
  88. }
  89. public function getRequestMessage(): Message
  90. {
  91. if (empty($this->request)) {
  92. throw new RuntimeException('empty request.');
  93. }
  94. $request = $this->request->getBody();
  95. $attributes = json_decode($request, true);
  96. if (! is_array($attributes)) {
  97. throw new RuntimeException('Invalid request body.');
  98. }
  99. // todo验签
  100. $attributes['msg'] = is_array($attributes['msg']) ? $attributes['msg'] : json_decode($attributes['msg'] ?? '', true);
  101. return new Message($attributes);
  102. }
  103. }