'123456', ]); $payload = [ 'k2' => [1, 2], 'empty' => '', 'k3' => [ 'b1' => 'test1', 'a2' => 'test2', ], 'k1' => 1, 'null_value' => null, ]; $sign = $service->signPayoutPayload($payload); $this->assertSame( hash('sha256', 'k1=1&k2=[1,2]&k3_a2=test2&k3_b1=test1' . '123456'), $sign ); } /** @test */ public function it_formats_payout_notify_amounts_to_four_decimals_when_verifying_signature() { $service = new PayPlus([ 'appKey' => '123456', ]); $payload = [ 'transaction_id' => 'T100', 'reference_id' => 'TX100', 'status' => 'PAID', 'timestamp' => 162856465000, 'payout_amount' => 10, 'source_amount' => '11', 'payout_fee' => 1, ]; $signString = 'payout_amount=10.0000&payout_fee=1.0000&reference_id=TX100' . '&source_amount=11.0000&status=PAID×tamp=162856465000&transaction_id=T100'; $this->assertTrue($service->verifyPayoutSignature( $payload, hash('sha256', $signString . '123456') )); } /** @test */ public function it_encrypts_and_decrypts_component_delta_with_aes_gcm() { $service = new PayPlus([]); $aesKey = str_repeat('01', 32); $iv = str_repeat('02', 12); $payload = '{"hello":"payplus"}'; $encrypted = $service->encryptComponentDelta($payload, $aesKey, $iv); $decrypted = $service->decryptComponentDelta($encrypted, $aesKey, $iv); $this->assertSame($payload, $decrypted); } /** @test */ public function it_encrypts_payin_payload_with_native_rsa_oaep_sha512() { $service = new PayPlus([ 'publicKey' => 'MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAnuDnY8u7a9EvUBAG7jJd' . 'KNkPS2vPpHo/gp7f2TA62cHXRW0AmeqHoWkcW6s8mMyP9EC6zNOcaVbPZrh6o9q0' . 'X06eZadexSK8bBY24c1j+uR1mivRcyB8bPiaNMGLaKKXpkbwttP+No7AOpAkWXx3' . 'pemXJeO8CRZGGRT79gv4v8Sd9KXJvsV4tdOU/RObMBtjtyWnGbNWWkxyJfq/sU4e' . 'DnFUr9J3jc1U6pPty/6ziukt6dMXth5qaod8kf7QMI0gXMlIi9znTLLSsQUzcZA0' . 'pB4/QvEExJxq0mtCtrq80UWITeE0frgbS4djq9XFGU+YlEXEX9DWgby5E9uX05vV' . 'UQIDAQAB', ]); $encrypted = $service->encryptPayinPayload([ 'platform_order_id' => 'P100', 'amount' => '10.00', ]); $this->assertSame(64, strlen($encrypted['aes_key'])); $this->assertSame(24, strlen($encrypted['iv'])); $this->assertSame(344, strlen($encrypted['body']['componentX'])); $this->assertSame(344, strlen($encrypted['body']['componentY'])); $this->assertNotEmpty($encrypted['body']['componentDelta']); } /** @test */ public function it_builds_beneficiary_payload_with_safe_defaults() { $service = new PayPlus([]); $payload = $service->buildBeneficiaryPayload([ 'user_id' => 10001, 'email' => '', 'phone' => '', 'first_name' => '', 'last_name' => '', ], 1234567890); $this->assertSame('10001', $payload['payee_id']); $this->assertSame('en', $payload['language']); $this->assertSame('US', $payload['country']); $this->assertSame('+1-0000000000', $payload['phone']); $this->assertSame('unknown10001@example.com', $payload['email']); $this->assertSame('unknown', $payload['first_name']); $this->assertSame('user', $payload['last_name']); $this->assertSame(1234567890, $payload['timestamp']); } /** @test */ public function it_keeps_only_english_letters_for_beneficiary_names() { $service = new PayPlus([]); $payload = $service->buildBeneficiaryPayload([ 'user_id' => 10002, 'first_name' => '张San-123', 'last_name' => '李User_456', ], 1234567890); $this->assertSame('San', $payload['first_name']); $this->assertSame('User', $payload['last_name']); $payload = $service->buildBeneficiaryPayload([ 'user_id' => 10003, 'first_name' => '张三123', 'last_name' => '456-', ], 1234567890); $this->assertSame('unknown', $payload['first_name']); $this->assertSame('user', $payload['last_name']); } }