DateTime::createFromFormat( DateTime::RFC2822, 'Sun, 05 Jan 2014 21:31:40 GMT' ), ) ); $this->httpSignatureService = new HttpSignatureService( $dateTimeProvider ); } public function testItVerifies() { $testCases = array( array( 'id' => 'defaultTest', 'headers' => array( 'Authorization' => 'Signature keyId="Test",algorithm="rsa-sha256",signature="SjWJWbWN7i0wzBvtPl8rbASWz5xQW6mcJmn+ibttBqtifLN7Sazz6m79cNfwwb8DMJ5cou1s7uEGKKCs+FLEEaDV5lp7q25WqS+lavg7T8hc0GppauB6hbgEKTwblDHYGEtbGmtdHgVCk9SuS13F0hZ8FD0k/5OxEPXe5WozsbM="', ), 'expectedResult' => true, ), array( 'id' => 'basicTest', 'headers' => array( 'Authorization' => 'Signature keyId="Test",algorithm="rsa-sha256",headers="(request-target) host date", signature="qdx+H7PHHDZgy4y/Ahn9Tny9V3GP6YgBPyUXMmoxWtLbHpUnXS2mg2+SbrQDMCJypxBLSPQR2aAjn7ndmw2iicw3HMbe8VfEdKFYRqzic+efkb3nndiv/x1xSHDJWeSWkx3ButlYSuBskLu6kd9Fswtemr3lgdDEmn04swr2Os0="', ), 'expectedResult' => true, ), array( 'id' => 'allHeadersTest', 'headers' => array( 'Authorization' => 'Signature keyId="Test",algorithm="rsa-sha256",headers="(request-target) host date content-type digest content-length",signature="vSdrb+dS3EceC9bcwHSo4MlyKS59iFIrhgYkz8+oVLEEzmYZZvRs8rgOp+63LEM3v+MFHB32NfpB2bEKBIvB1q52LaEUHFv120V01IL+TAD48XaERZFukWgHoBTLMhYS2Gb51gWxpeIq8knRmPnYePbF5MOkR0Zkly4zKH7s1dE="', ), 'expectedResult' => true, ), array( 'id' => 'defaultTestSigHeader', 'headers' => array( 'Signature' => 'keyId="Test",algorithm="rsa-sha256",signature="SjWJWbWN7i0wzBvtPl8rbASWz5xQW6mcJmn+ibttBqtifLN7Sazz6m79cNfwwb8DMJ5cou1s7uEGKKCs+FLEEaDV5lp7q25WqS+lavg7T8hc0GppauB6hbgEKTwblDHYGEtbGmtdHgVCk9SuS13F0hZ8FD0k/5OxEPXe5WozsbM="', ), 'expectedResult' => true, ), array( 'id' => 'basicTestSigHeader', 'headers' => array( 'Signature' => 'keyId="Test",algorithm="rsa-sha256",headers="(request-target) host date", signature="qdx+H7PHHDZgy4y/Ahn9Tny9V3GP6YgBPyUXMmoxWtLbHpUnXS2mg2+SbrQDMCJypxBLSPQR2aAjn7ndmw2iicw3HMbe8VfEdKFYRqzic+efkb3nndiv/x1xSHDJWeSWkx3ButlYSuBskLu6kd9Fswtemr3lgdDEmn04swr2Os0="', ), 'expectedResult' => true, ), array( 'id' => 'allHeadersTestSigHeader', 'headers' => array( 'Signature' => 'keyId="Test",algorithm="rsa-sha256",headers="(request-target) host date content-type digest content-length",signature="vSdrb+dS3EceC9bcwHSo4MlyKS59iFIrhgYkz8+oVLEEzmYZZvRs8rgOp+63LEM3v+MFHB32NfpB2bEKBIvB1q52LaEUHFv120V01IL+TAD48XaERZFukWgHoBTLMhYS2Gb51gWxpeIq8knRmPnYePbF5MOkR0Zkly4zKH7s1dE="', ), 'expectedResult' => true, ), array( 'id' => 'noHeaders', 'headers' => array(), 'expectedResult' => false, ), array( 'id' => 'headerMissing', 'headers' => array( 'Authorization' => 'Signature keyId="Test",algorithm="rsa-sha256",headers="(request-target) host date content-type digest content-length x-foo-header",signature="vSdrb+dS3EceC9bcwHSo4MlyKS59iFIrhgYkz8+oVLEEzmYZZvRs8rgOp+63LEM3v+MFHB32NfpB2bEKBIvB1q52LaEUHFv120V01IL+TAD48XaERZFukWgHoBTLMhYS2Gb51gWxpeIq8knRmPnYePbF5MOkR0Zkly4zKH7s1dE="', ), 'expectedResult' => false, ), array( 'id' => 'malformedHeader', 'headers' => array( 'Authorization' => 'not a real auth header', ), 'expectedResult' => false, ), array( 'id' => 'partlyMalformedHeader', 'headers' => array( 'Authorization' => 'Signature keyId="Test",algorithm="rsa-sha256",headers-malformed="(request-target) host date content-type digest content-length",signature="vSdrb+dS3EceC9bcwHSo4MlyKS59iFIrhgYkz8+oVLEEzmYZZvRs8rgOp+63LEM3v+MFHB32NfpB2bEKBIvB1q52LaEUHFv120V01IL+TAD48XaERZFukWgHoBTLMhYS2Gb51gWxpeIq8knRmPnYePbF5MOkR0Zkly4zKH7s1dE="', ), 'expectedResult' => false, ), array( 'id' => 'dateTooFarInPast', 'headers' => array( 'Authorization' => 'Signature keyId="Test",algorithm="rsa-sha256",headers="(request-target) host date", signature="qdx+H7PHHDZgy4y/Ahn9Tny9V3GP6YgBPyUXMmoxWtLbHpUnXS2mg2+SbrQDMCJypxBLSPQR2aAjn7ndmw2iicw3HMbe8VfEdKFYRqzic+efkb3nndiv/x1xSHDJWeSWkx3ButlYSuBskLu6kd9Fswtemr3lgdDEmn04swr2Os0="', ), 'expectedResult' => false, 'currentDatetime' => DateTime::createFromFormat( DateTime::RFC2822, 'Sun, 05 Jan 2014 21:36:41 GMT' ), ), array( 'id' => 'dateTooFarInFuture', 'headers' => array( 'Authorization' => 'Signature keyId="Test",algorithm="rsa-sha256",headers="(request-target) host date", signature="qdx+H7PHHDZgy4y/Ahn9Tny9V3GP6YgBPyUXMmoxWtLbHpUnXS2mg2+SbrQDMCJypxBLSPQR2aAjn7ndmw2iicw3HMbe8VfEdKFYRqzic+efkb3nndiv/x1xSHDJWeSWkx3ButlYSuBskLu6kd9Fswtemr3lgdDEmn04swr2Os0="', ), 'expectedResult' => false, 'currentDatetime' => DateTime::createFromFormat( DateTime::RFC2822, 'Sun, 05 Jan 2014 21:26:39 GMT' ), ), ); foreach ( $testCases as $testCase ) { if ( array_key_exists( 'currentDatetime', $testCase ) ) { $dateTimeProvider = new TestDateTimeProvider( array( 'http-signature.verify' => $testCase['currentDatetime'], ) ); $this->httpSignatureService = new HttpSignatureService( $dateTimeProvider ); } $request = self::getSymfonyRequest(); foreach ( $testCase['headers'] as $header => $value ) { $request->headers->set( $header, $value ); } $actual = $this->httpSignatureService->verify( $request, self::PUBLIC_KEY ); $this->assertEquals( $testCase['expectedResult'], $actual, "Error on test $testCase[id]" ); } } private static function getSymfonyRequest() { $request = Request::create( 'https://example.com/foo?param=value&pet=dog', Request::METHOD_POST, array(), array(), array(), array(), '{"hello": "world"}' ); $request->headers->set( 'host', 'example.com' ); $request->headers->set( 'content-type', 'application/json' ); $request->headers->set( 'digest', 'SHA-256=X48E9qOokqqrvdts8nOJRJN3OWDUoyWxBf7kbu9DBPE=' ); $request->headers->set( 'content-length', 18 ); $request->headers->set( 'date', 'Sun, 05 Jan 2014 21:31:40 GMT' ); return $request; } public function testItSigns() { $testCases = array( array( 'id' => 'basicTest', 'keyId' => 'Test', 'expected' => 'keyId="Test",algorithm="rsa-sha256",headers="(request-target) host date",signature="qdx+H7PHHDZgy4y/Ahn9Tny9V3GP6YgBPyUXMmoxWtLbHpUnXS2mg2+SbrQDMCJypxBLSPQR2aAjn7ndmw2iicw3HMbe8VfEdKFYRqzic+efkb3nndiv/x1xSHDJWeSWkx3ButlYSuBskLu6kd9Fswtemr3lgdDEmn04swr2Os0="', ), array( 'id' => 'allHeadersTest', 'keyId' => 'Test', 'headers' => array( '(request-target)', 'host', 'date', 'content-type', 'digest', 'content-length', ), 'expected' => 'keyId="Test",algorithm="rsa-sha256",headers="(request-target) host date content-type digest content-length",signature="vSdrb+dS3EceC9bcwHSo4MlyKS59iFIrhgYkz8+oVLEEzmYZZvRs8rgOp+63LEM3v+MFHB32NfpB2bEKBIvB1q52LaEUHFv120V01IL+TAD48XaERZFukWgHoBTLMhYS2Gb51gWxpeIq8knRmPnYePbF5MOkR0Zkly4zKH7s1dE="', ), ); foreach ( $testCases as $testCase ) { $request = self::getPsrRequest(); if ( array_key_exists( 'headers', $testCase ) ) { $actual = $this->httpSignatureService->sign( $request, self::PRIVATE_KEY, $testCase['keyId'], $testCase['headers'] ); } else { $actual = $this->httpSignatureService->sign( $request, self::PRIVATE_KEY, $testCase['keyId'] ); } $this->assertEquals( $testCase['expected'], $actual, "Error on test $testCase[id]" ); } } private static function getPsrRequest() { $headers = array( 'Host' => 'example.com', 'Content-Type' => 'application/json', 'Digest' => 'SHA-256=X48E9qOokqqrvdts8nOJRJN3OWDUoyWxBf7kbu9DBPE=', 'Content-Length' => 18, 'Date' => 'Sun, 05 Jan 2014 21:31:40 GMT' ); $body = '{"hello": "world"}'; return new PsrRequest( 'POST', 'https://example.com/foo?param=value&pet=dog', $headers, $body ); } }