diff --git a/src/Component/Signature/JWSBuilder.php b/src/Component/Signature/JWSBuilder.php index 4f2af279..f5ccf5a4 100644 --- a/src/Component/Signature/JWSBuilder.php +++ b/src/Component/Signature/JWSBuilder.php @@ -104,6 +104,27 @@ public function withPayload(string $payload, bool $isPayloadDetached = false): s return $clone; } + /** + * Set the payload to an already-encoded value. + * This method will return a new JWSBuilder object. + * + * @throws InvalidArgumentException if the payload is not UTF-8 encoded + * + * @return JWSBuilder + */ + public function withEncodedPayload(string $payload, bool $isPayloadDetached = false): self + { + if (false === mb_detect_encoding($payload, 'UTF-8', true)) { + throw new InvalidArgumentException('The payload must be encoded in UTF-8'); + } + $clone = clone $this; + $clone->payload = $payload; + $clone->isPayloadDetached = $isPayloadDetached; + $clone->isPayloadEncoded = false; + + return $clone; + } + /** * Adds the information needed to compute the signature. * This method will return a new JWSBuilder object. @@ -177,7 +198,10 @@ public function build(): JWS private function checkIfPayloadIsEncoded(array $protectedHeader): bool { - return !array_key_exists('b64', $protectedHeader) || true === $protectedHeader['b64']; + if(null === $this->isPayloadEncoded) + return !array_key_exists('b64', $protectedHeader) || true === $protectedHeader['b64']; + else + return $this->isPayloadEncoded; } /** diff --git a/tests/Component/Signature/SignerTest.php b/tests/Component/Signature/SignerTest.php index 62de2767..baf82be8 100644 --- a/tests/Component/Signature/SignerTest.php +++ b/tests/Component/Signature/SignerTest.php @@ -744,6 +744,30 @@ public function flattenedJSONWithUnencodedDetachedPayload(): void static::assertEquals($expected_result, json_decode($jws, true)); } + /** + * @test + */ + public function jWSWithExternallyEncodedPayload(): void + { + $payload = 'aaaaaaa'; + $jwsBuilder = $this->getJWSBuilderFactory()->create(['HS512']); + + $expected_result = [ + 'payload' => $payload, + 'protected' => 'eyJhbGciOiJIUzUxMiJ9', + 'signature' => '_CzoyjQh6gCXWY01DbJwXBJ5yZzeSgYTF5VbHpLRePP3Xt300n4yTEflj8xrrPNrvjApk6YpjTLX-CYX6YzsbA' + ]; + + $jws = $jwsBuilder + ->create()->withEncodedPayload($payload) + ->addSignature($this->getKey1(), ['alg' => 'HS512']) + ->build() + ; + $jws = $this->getJWSSerializerManager()->serialize('jws_json_flattened', $jws, 0); + + static::assertEquals($expected_result, json_decode($jws, true)); + } + /** * @test */