|
5 | 5 |
|
6 | 6 | class JWKTest extends TestCase |
7 | 7 | { |
8 | | - /* |
9 | | - * For compatibility with PHPUnit 4.8 and PHP < 5.6 |
10 | | - */ |
11 | | - public function setExpectedException($exceptionName, $message = '', $code = NULL) { |
12 | | - if (method_exists($this, 'expectException')) { |
13 | | - $this->expectException($exceptionName); |
14 | | - } else { |
15 | | - parent::setExpectedException($exceptionName, $message, $code); |
16 | | - } |
17 | | - } |
| 8 | + private static $keys; |
| 9 | + private static $privKey1; |
| 10 | + private static $privKey2; |
18 | 11 |
|
19 | | - public function testDecodeByJWKKeySetTokenExpired() |
| 12 | + public function testMissingKty() |
20 | 13 | { |
21 | | - $jsKey = array( |
22 | | - 'kty' => 'RSA', |
23 | | - 'e' => 'AQAB', |
24 | | - 'use' => 'sig', |
25 | | - 'kid' => 's1', |
26 | | - 'n' => 'kWp2zRA23Z3vTL4uoe8kTFptxBVFunIoP4t_8TDYJrOb7D1iZNDXVeEsYKp6ppmrTZDAgd-cNOTKLd4M39WJc5FN0maTAVKJc7NxklDeKc4dMe1BGvTZNG4MpWBo-taKULlYUu0ltYJuLzOjIrTHfarucrGoRWqM0sl3z2-fv9k', |
| 14 | + $this->setExpectedException( |
| 15 | + 'UnexpectedValueException', |
| 16 | + 'JWK must contain a "kty" parameter' |
27 | 17 | ); |
28 | 18 |
|
29 | | - $key = JWK::parseKeySet(array('keys' => array($jsKey))); |
| 19 | + $badJwk = array('kid' => 'foo'); |
| 20 | + $keys = JWK::parseKeySet(array('keys' => array($badJwk))); |
| 21 | + } |
30 | 22 |
|
31 | | - $header = array( |
32 | | - 'kid' => 's1', |
33 | | - 'alg' => 'RS256', |
34 | | - ); |
35 | | - $payload = array ( |
36 | | - 'scp' => array ('openid', 'email', 'profile', 'aas'), |
37 | | - 'sub' => 'tUCYtnfIBPWcrSJf4yBfvN1kww4KGcy3LIPk1GVzsE0', |
38 | | - 'clm' => array ('!5v8H'), |
39 | | - 'iss' => 'http://130.211.243.114:8080/c2id', |
40 | | - 'exp' => 1441126539, |
41 | | - 'uip' => array('groups' => array('admin', 'audit')), |
42 | | - 'cid' => 'pk-oidc-01', |
43 | | - ); |
44 | | - $signature = 'PvYrnf3k1Z0wgRwCgq0WXKaoIv1hHtzBFO5cGfCs6bl4suc6ilwCWmJqRxGYkU2fNTGyMOt3OUnnBEwl6v5qN6jv7zbkVAVKVvbQLxhHC2nXe3izvoCiVaMEH6hE7VTWwnPbX_qO72mCwTizHTJTZGLOsyXLYM6ctdOMf7sFPTI'; |
45 | | - $msg = sprintf('%s.%s.%s', |
46 | | - JWT::urlsafeB64Encode(json_encode($header)), |
47 | | - JWT::urlsafeB64Encode(json_encode($payload)), |
48 | | - $signature |
| 23 | + public function testInvalidAlgorithm() |
| 24 | + { |
| 25 | + $this->setExpectedException( |
| 26 | + 'UnexpectedValueException', |
| 27 | + 'No supported algorithms found in JWK Set' |
49 | 28 | ); |
50 | 29 |
|
51 | | - $this->setExpectedException('Firebase\JWT\ExpiredException'); |
52 | | - |
53 | | - JWT::decode($msg, $key, array('RS256')); |
| 30 | + $badJwk = array('kty' => 'BADALG'); |
| 31 | + $keys = JWK::parseKeySet(array('keys' => array($badJwk))); |
54 | 32 | } |
55 | 33 |
|
56 | | - public function testDecodeByJWKKeySet() |
| 34 | + public function testParseJwkKeySet() |
57 | 35 | { |
58 | | - $jsKey = array( |
59 | | - 'kty' => 'RSA', |
60 | | - 'e' => 'AQAB', |
61 | | - 'use' => 'sig', |
62 | | - 'kid' => 's1', |
63 | | - 'n' => 'kWp2zRA23Z3vTL4uoe8kTFptxBVFunIoP4t_8TDYJrOb7D1iZNDXVeEsYKp6ppmrTZDAgd-cNOTKLd4M39WJc5FN0maTAVKJc7NxklDeKc4dMe1BGvTZNG4MpWBo-taKULlYUu0ltYJuLzOjIrTHfarucrGoRWqM0sl3z2-fv9k', |
| 36 | + $jwkSet = json_decode( |
| 37 | + file_get_contents(__DIR__ . '/rsa-jwkset.json'), |
| 38 | + true |
64 | 39 | ); |
| 40 | + $keys = JWK::parseKeySet($jwkSet); |
| 41 | + $this->assertTrue(is_array($keys)); |
| 42 | + $this->assertArrayHasKey('jwk1', $keys); |
| 43 | + self::$keys = $keys; |
| 44 | + } |
65 | 45 |
|
66 | | - $key = JWK::parseKeySet(array('keys' => array($jsKey))); |
67 | | - |
68 | | - $header = array( |
69 | | - 'kid' => 's1', |
70 | | - 'alg' => 'RS256', |
71 | | - ); |
72 | | - $payload = array ( |
73 | | - 'scp' => array ('openid', 'email', 'profile', 'aas'), |
74 | | - 'sub' => 'tUCYtnfIBPWcrSJf4yBfvN1kww4KGcy3LIPk1GVzsE0', |
75 | | - 'clm' => array ('!5v8H'), |
76 | | - 'iss' => 'http://130.211.243.114:8080/c2id', |
77 | | - 'exp' => 1441126539, |
78 | | - 'uip' => array('groups' => array('admin', 'audit')), |
79 | | - 'cid' => 'pk-oidc-01', |
80 | | - ); |
81 | | - $signature = 'PvYrnf3k1Z0wgRwCgq0WXKaoIv1hHtzBFO5cGfCs6bl4suc6ilwCWmJqRxGYkU2fNTGyMOt3OUnnBEwl6v5qN6jv7zbkVAVKVvbQLxhHC2nXe3izvoCiVaMEH6hE7VTWwnPbX_qO72mCwTizHTJTZGLOsyXLYM6ctdOMf7sFPTI'; |
82 | | - $msg = sprintf('%s.%s.%s', |
83 | | - JWT::urlsafeB64Encode(json_encode($header)), |
84 | | - JWT::urlsafeB64Encode(json_encode($payload)), |
85 | | - $signature |
86 | | - ); |
| 46 | + /** |
| 47 | + * @depends testParseJwkKeySet |
| 48 | + */ |
| 49 | + public function testDecodeByJwkKeySetTokenExpired() |
| 50 | + { |
| 51 | + $privKey1 = file_get_contents(__DIR__ . '/rsa1-private.pem'); |
| 52 | + $payload = array('exp' => strtotime('-1 hour')); |
| 53 | + $msg = JWT::encode($payload, $privKey1, 'RS256', 'jwk1'); |
87 | 54 |
|
88 | 55 | $this->setExpectedException('Firebase\JWT\ExpiredException'); |
89 | 56 |
|
90 | | - $payload = JWT::decode($msg, $key, array('RS256')); |
91 | | - |
92 | | - $this->assertEquals("tUCYtnfIBPWcrSJf4yBfvN1kww4KGcy3LIPk1GVzsE0", $payload->sub); |
93 | | - $this->assertEquals(1441126539, $payload->exp); |
| 57 | + JWT::decode($msg, self::$keys, array('RS256')); |
94 | 58 | } |
95 | 59 |
|
96 | | - public function testDecodeByMultiJWKKeySet() |
| 60 | + /** |
| 61 | + * @depends testParseJwkKeySet |
| 62 | + */ |
| 63 | + public function testDecodeByJwkKeySet() |
97 | 64 | { |
98 | | - $jsKey1 = array( |
99 | | - 'kty' => 'RSA', |
100 | | - 'e' => 'AQAB', |
101 | | - 'use' => 'sig', |
102 | | - 'kid' => 'CXup', |
103 | | - 'n' => 'hrwD-lc-IwzwidCANmy4qsiZk11yp9kHykOuP0yOnwi36VomYTQVEzZXgh2sDJpGgAutdQudgwLoV8tVSsTG9SQHgJjH9Pd_9V4Ab6PANyZNG6DSeiq1QfiFlEP6Obt0JbRB3W7X2vkxOVaNoWrYskZodxU2V0ogeVL_LkcCGAyNu2jdx3j0DjJatNVk7ystNxb9RfHhJGgpiIkO5S3QiSIVhbBKaJHcZHPF1vq9g0JMGuUCI-OTSVg6XBkTLEGw1C_R73WD_oVEBfdXbXnLukoLHBS11p3OxU7f4rfxA_f_72_UwmWGJnsqS3iahbms3FkvqoL9x_Vj3GhuJSf97Q', |
104 | | - ); |
105 | | - $jsKey2 = array( |
106 | | - 'kty' => 'EC', |
107 | | - 'use' => 'sig', |
108 | | - 'crv' => 'P-256', |
109 | | - 'kid' => 'yGvt', |
110 | | - 'x' => 'pvgdqM3RCshljmuCF1D2Ez1w5ei5k7-bpimWLPNeEHI', |
111 | | - 'y' => 'JSmUhbUTqiFclVLEdw6dz038F7Whw4URobjXbAReDuM', |
112 | | - ); |
113 | | - $jsKey3 = array( |
114 | | - 'kty' => 'EC', |
115 | | - 'use' => 'sig', |
116 | | - 'crv' => 'P-384', |
117 | | - 'kid' => '9nHY', |
118 | | - 'x' => 'JPKhjhE0Bj579Mgj3Cn3ERGA8fKVYoGOaV9BPKhtnEobphf8w4GSeigMesL-038W', |
119 | | - 'y' => 'UbJa1QRX7fo9LxSlh7FOH5ABT5lEtiQeQUcX9BW0bpJFlEVGqwec80tYLdOIl59M', |
120 | | - ); |
121 | | - $jsKey4 = array( |
122 | | - 'kty' => 'EC', |
123 | | - 'use' => 'sig', |
124 | | - 'crv' => 'P-521', |
125 | | - 'kid' => 'tVzS', |
126 | | - 'x' => 'AZgkRHlIyNQJlPIwTWdHqouw41k9dS3GJO04BDEnJnd_Dd1owlCn9SMXA-JuXINn4slwbG4wcECbctXb2cvdGtmn', |
127 | | - 'y' => 'AdBC6N9lpupzfzcIY3JLIuc8y8MnzV-ItmzHQcC5lYWMTbuM9NU_FlvINeVo8g6i4YZms2xFB-B0VVdaoF9kUswC', |
128 | | - ); |
| 65 | + $privKey1 = file_get_contents(__DIR__ . '/rsa1-private.pem'); |
| 66 | + $payload = array('sub' => 'foo', 'exp' => strtotime('+10 seconds')); |
| 67 | + $msg = JWT::encode($payload, $privKey1, 'RS256', 'jwk1'); |
129 | 68 |
|
130 | | - $key = JWK::parseKeySet(array('keys' => array($jsKey1, $jsKey2, $jsKey3, $jsKey4))); |
| 69 | + $result = JWT::decode($msg, self::$keys, array('RS256')); |
131 | 70 |
|
132 | | - $header = array( |
133 | | - 'kid' => 'CXup', |
134 | | - 'alg' => 'RS256', |
135 | | - ); |
136 | | - $payload = array( |
137 | | - 'sub' => 'f8b67cc46030777efd8bce6c1bfe29c6c0f818ec', |
138 | | - 'scp' => array('openid', 'name', 'profile', 'picture', 'email', 'rs-pk-main', 'rs-pk-so', 'rs-pk-issue', 'rs-pk-web'), |
139 | | - 'clm' => array('!5v8H'), |
140 | | - 'iss' => 'https://id.projectkit.net/authenticate', |
141 | | - 'exp' => 1492228336, |
142 | | - 'iat' => 1491364336, |
143 | | - 'cid' => 'cid-pk-web', |
144 | | - ); |
145 | | - $signature = 'KW1K-72bMtiNwvyYBgffG6VaG6I59cELGYQR8M2q7HA8dmzliu6QREJrqyPtwW_rDJZbsD3eylvkRinK9tlsMXCOfEJbxLdAC9b4LKOsnsbuXXwsJHWkFG0a7osdW0ZpXJDoMFlO1aosxRGMkaqhf1wIkvQ5PM_EB08LJv7oz64Antn5bYaoajwgvJRl7ChatRDn9Sx5UIElKD1BK4Uw5WdrZwBlWdWZVNCSFhy4F6SdZvi3OBlXzluDwq61RC-pl2iivilJNljYWVrthHDS1xdtaVz4oteHW13-IS7NNEz6PVnzo5nyoPWMAB4JlRnxcfOFTTUqOA2mX5Csg0UpdQ'; |
146 | | - $msg = sprintf('%s.%s.%s', |
147 | | - JWT::urlsafeB64Encode(json_encode($header)), |
148 | | - JWT::urlsafeB64Encode(json_encode($payload)), |
149 | | - $signature |
150 | | - ); |
| 71 | + $this->assertEquals("foo", $result->sub); |
| 72 | + } |
151 | 73 |
|
152 | | - $this->setExpectedException('Firebase\JWT\ExpiredException'); |
| 74 | + /** |
| 75 | + * @depends testParseJwkKeySet |
| 76 | + */ |
| 77 | + public function testDecodeByMultiJwkKeySet() |
| 78 | + { |
| 79 | + $privKey2 = file_get_contents(__DIR__ . '/rsa2-private.pem'); |
| 80 | + $payload = array('sub' => 'bar', 'exp' => strtotime('+10 seconds')); |
| 81 | + $msg = JWT::encode($payload, $privKey2, 'RS256', 'jwk2'); |
153 | 82 |
|
154 | | - $payload = JWT::decode($msg, $key, array('RS256')); |
| 83 | + $result = JWT::decode($msg, self::$keys, array('RS256')); |
155 | 84 |
|
156 | | - $this->assertEquals("f8b67cc46030777efd8bce6c1bfe29c6c0f818ec", $payload->sub); |
157 | | - $this->assertEquals(1492228336, $payload->exp); |
| 85 | + $this->assertEquals("bar", $result->sub); |
| 86 | + } |
| 87 | + |
| 88 | + /* |
| 89 | + * For compatibility with PHPUnit 4.8 and PHP < 5.6 |
| 90 | + */ |
| 91 | + public function setExpectedException($exceptionName, $message = '', $code = NULL) |
| 92 | + { |
| 93 | + if (method_exists($this, 'expectException')) { |
| 94 | + $this->expectException($exceptionName); |
| 95 | + if ($message) { |
| 96 | + $this->expectExceptionMessage($message); |
| 97 | + } |
| 98 | + } else { |
| 99 | + parent::setExpectedException($exceptionName, $message, $code); |
| 100 | + } |
158 | 101 | } |
159 | 102 | } |
0 commit comments