PageRenderTime 44ms CodeModel.GetById 17ms RepoModel.GetById 0ms app.codeStats 0ms

/boto-2.5.2/tests/unit/cloudfront/test_signed_urls.py

#
Python | 317 lines | 315 code | 2 blank | 0 comment | 2 complexity | 96a82c316a32d2fb31a6fb938d93bdd6 MD5 | raw file
  1. import unittest
  2. try:
  3. import simplejson as json
  4. except ImportError:
  5. import json
  6. from textwrap import dedent
  7. from boto.cloudfront.distribution import Distribution
  8. class CloudfrontSignedUrlsTest(unittest.TestCase):
  9. def setUp(self):
  10. self.pk_str = dedent("""
  11. -----BEGIN RSA PRIVATE KEY-----
  12. MIICXQIBAAKBgQDA7ki9gI/lRygIoOjV1yymgx6FYFlzJ+z1ATMaLo57nL57AavW
  13. hb68HYY8EA0GJU9xQdMVaHBogF3eiCWYXSUZCWM/+M5+ZcdQraRRScucmn6g4EvY
  14. 2K4W2pxbqH8vmUikPxir41EeBPLjMOzKvbzzQy9e/zzIQVREKSp/7y1mywIDAQAB
  15. AoGABc7mp7XYHynuPZxChjWNJZIq+A73gm0ASDv6At7F8Vi9r0xUlQe/v0AQS3yc
  16. N8QlyR4XMbzMLYk3yjxFDXo4ZKQtOGzLGteCU2srANiLv26/imXA8FVidZftTAtL
  17. viWQZBVPTeYIA69ATUYPEq0a5u5wjGyUOij9OWyuy01mbPkCQQDluYoNpPOekQ0Z
  18. WrPgJ5rxc8f6zG37ZVoDBiexqtVShIF5W3xYuWhW5kYb0hliYfkq15cS7t9m95h3
  19. 1QJf/xI/AkEA1v9l/WN1a1N3rOK4VGoCokx7kR2SyTMSbZgF9IWJNOugR/WZw7HT
  20. njipO3c9dy1Ms9pUKwUF46d7049ck8HwdQJARgrSKuLWXMyBH+/l1Dx/I4tXuAJI
  21. rlPyo+VmiOc7b5NzHptkSHEPfR9s1OK0VqjknclqCJ3Ig86OMEtEFBzjZQJBAKYz
  22. 470hcPkaGk7tKYAgP48FvxRsnzeooptURW5E+M+PQ2W9iDPPOX9739+Xi02hGEWF
  23. B0IGbQoTRFdE4VVcPK0CQQCeS84lODlC0Y2BZv2JxW3Osv/WkUQ4dslfAQl1T303
  24. 7uwwr7XTroMv8dIFQIPreoPhRKmd/SbJzbiKfS/4QDhU
  25. -----END RSA PRIVATE KEY-----
  26. """)
  27. self.pk_id = "PK123456789754"
  28. self.dist = Distribution()
  29. self.canned_policy = (
  30. '{"Statement":[{"Resource":'
  31. '"http://d604721fxaaqy9.cloudfront.net/horizon.jpg'
  32. '?large=yes&license=yes",'
  33. '"Condition":{"DateLessThan":{"AWS:EpochTime":1258237200}}}]}')
  34. self.custom_policy_1 = (
  35. '{ \n'
  36. ' "Statement": [{ \n'
  37. ' "Resource":"http://d604721fxaaqy9.cloudfront.net/training/*", \n'
  38. ' "Condition":{ \n'
  39. ' "IpAddress":{"AWS:SourceIp":"145.168.143.0/24"}, \n'
  40. ' "DateLessThan":{"AWS:EpochTime":1258237200} \n'
  41. ' } \n'
  42. ' }] \n'
  43. '}\n')
  44. self.custom_policy_2 = (
  45. '{ \n'
  46. ' "Statement": [{ \n'
  47. ' "Resource":"http://*", \n'
  48. ' "Condition":{ \n'
  49. ' "IpAddress":{"AWS:SourceIp":"216.98.35.1/32"},\n'
  50. ' "DateGreaterThan":{"AWS:EpochTime":1241073790},\n'
  51. ' "DateLessThan":{"AWS:EpochTime":1255674716}\n'
  52. ' } \n'
  53. ' }] \n'
  54. '}\n')
  55. def test_encode_custom_policy_1(self):
  56. """
  57. Test base64 encoding custom policy 1 from Amazon's documentation.
  58. """
  59. expected = ("eyAKICAgIlN0YXRlbWVudCI6IFt7IAogICAgICAiUmVzb3VyY2Ui"
  60. "OiJodHRwOi8vZDYwNDcyMWZ4YWFxeTkuY2xvdWRmcm9udC5uZXQv"
  61. "dHJhaW5pbmcvKiIsIAogICAgICAiQ29uZGl0aW9uIjp7IAogICAg"
  62. "ICAgICAiSXBBZGRyZXNzIjp7IkFXUzpTb3VyY2VJcCI6IjE0NS4x"
  63. "NjguMTQzLjAvMjQifSwgCiAgICAgICAgICJEYXRlTGVzc1RoYW4i"
  64. "OnsiQVdTOkVwb2NoVGltZSI6MTI1ODIzNzIwMH0gICAgICAKICAg"
  65. "ICAgfSAKICAgfV0gCn0K")
  66. encoded = self.dist._url_base64_encode(self.custom_policy_1)
  67. self.assertEqual(expected, encoded)
  68. def test_encode_custom_policy_2(self):
  69. """
  70. Test base64 encoding custom policy 2 from Amazon's documentation.
  71. """
  72. expected = ("eyAKICAgIlN0YXRlbWVudCI6IFt7IAogICAgICAiUmVzb3VyY2Ui"
  73. "OiJodHRwOi8vKiIsIAogICAgICAiQ29uZGl0aW9uIjp7IAogICAg"
  74. "ICAgICAiSXBBZGRyZXNzIjp7IkFXUzpTb3VyY2VJcCI6IjIxNi45"
  75. "OC4zNS4xLzMyIn0sCiAgICAgICAgICJEYXRlR3JlYXRlclRoYW4i"
  76. "OnsiQVdTOkVwb2NoVGltZSI6MTI0MTA3Mzc5MH0sCiAgICAgICAg"
  77. "ICJEYXRlTGVzc1RoYW4iOnsiQVdTOkVwb2NoVGltZSI6MTI1NTY3"
  78. "NDcxNn0KICAgICAgfSAKICAgfV0gCn0K")
  79. encoded = self.dist._url_base64_encode(self.custom_policy_2)
  80. self.assertEqual(expected, encoded)
  81. def test_sign_canned_policy(self):
  82. """
  83. Test signing the canned policy from amazon's cloudfront documentation.
  84. """
  85. expected = ("Nql641NHEUkUaXQHZINK1FZ~SYeUSoBJMxjdgqrzIdzV2gyEXPDN"
  86. "v0pYdWJkflDKJ3xIu7lbwRpSkG98NBlgPi4ZJpRRnVX4kXAJK6td"
  87. "Nx6FucDB7OVqzcxkxHsGFd8VCG1BkC-Afh9~lOCMIYHIaiOB6~5j"
  88. "t9w2EOwi6sIIqrg_")
  89. sig = self.dist._sign_string(self.canned_policy, private_key_string=self.pk_str)
  90. encoded_sig = self.dist._url_base64_encode(sig)
  91. self.assertEqual(expected, encoded_sig)
  92. def test_sign_canned_policy_unicode(self):
  93. """
  94. Test signing the canned policy from amazon's cloudfront documentation.
  95. """
  96. expected = ("Nql641NHEUkUaXQHZINK1FZ~SYeUSoBJMxjdgqrzIdzV2gyEXPDN"
  97. "v0pYdWJkflDKJ3xIu7lbwRpSkG98NBlgPi4ZJpRRnVX4kXAJK6td"
  98. "Nx6FucDB7OVqzcxkxHsGFd8VCG1BkC-Afh9~lOCMIYHIaiOB6~5j"
  99. "t9w2EOwi6sIIqrg_")
  100. unicode_policy = unicode(self.canned_policy)
  101. sig = self.dist._sign_string(unicode_policy, private_key_string=self.pk_str)
  102. encoded_sig = self.dist._url_base64_encode(sig)
  103. self.assertEqual(expected, encoded_sig)
  104. def test_sign_custom_policy_1(self):
  105. """
  106. Test signing custom policy 1 from amazon's cloudfront documentation.
  107. """
  108. expected = ("cPFtRKvUfYNYmxek6ZNs6vgKEZP6G3Cb4cyVt~FjqbHOnMdxdT7e"
  109. "T6pYmhHYzuDsFH4Jpsctke2Ux6PCXcKxUcTIm8SO4b29~1QvhMl-"
  110. "CIojki3Hd3~Unxjw7Cpo1qRjtvrimW0DPZBZYHFZtiZXsaPt87yB"
  111. "P9GWnTQoaVysMxQ_")
  112. sig = self.dist._sign_string(self.custom_policy_1, private_key_string=self.pk_str)
  113. encoded_sig = self.dist._url_base64_encode(sig)
  114. self.assertEqual(expected, encoded_sig)
  115. def test_sign_custom_policy_2(self):
  116. """
  117. Test signing custom policy 2 from amazon's cloudfront documentation.
  118. """
  119. expected = ("rc~5Qbbm8EJXjUTQ6Cn0LAxR72g1DOPrTmdtfbWVVgQNw0q~KHUA"
  120. "mBa2Zv1Wjj8dDET4XSL~Myh44CLQdu4dOH~N9huH7QfPSR~O4tIO"
  121. "S1WWcP~2JmtVPoQyLlEc8YHRCuN3nVNZJ0m4EZcXXNAS-0x6Zco2"
  122. "SYx~hywTRxWR~5Q_")
  123. sig = self.dist._sign_string(self.custom_policy_2, private_key_string=self.pk_str)
  124. encoded_sig = self.dist._url_base64_encode(sig)
  125. self.assertEqual(expected, encoded_sig)
  126. def test_create_canned_policy(self):
  127. """
  128. Test that a canned policy is generated correctly.
  129. """
  130. url = "http://1234567.cloudfront.com/test_resource.mp3?dog=true"
  131. expires = 999999
  132. policy = self.dist._canned_policy(url, expires)
  133. policy = json.loads(policy)
  134. self.assertEqual(1, len(policy.keys()))
  135. statements = policy["Statement"]
  136. self.assertEqual(1, len(statements))
  137. statement = statements[0]
  138. resource = statement["Resource"]
  139. self.assertEqual(url, resource)
  140. condition = statement["Condition"]
  141. self.assertEqual(1, len(condition.keys()))
  142. date_less_than = condition["DateLessThan"]
  143. self.assertEqual(1, len(date_less_than.keys()))
  144. aws_epoch_time = date_less_than["AWS:EpochTime"]
  145. self.assertEqual(expires, aws_epoch_time)
  146. def test_custom_policy_expires_and_policy_url(self):
  147. """
  148. Test that a custom policy can be created with an expire time and an
  149. arbitrary URL.
  150. """
  151. url = "http://1234567.cloudfront.com/*"
  152. expires = 999999
  153. policy = self.dist._custom_policy(url, expires=expires)
  154. policy = json.loads(policy)
  155. self.assertEqual(1, len(policy.keys()))
  156. statements = policy["Statement"]
  157. self.assertEqual(1, len(statements))
  158. statement = statements[0]
  159. resource = statement["Resource"]
  160. self.assertEqual(url, resource)
  161. condition = statement["Condition"]
  162. self.assertEqual(1, len(condition.keys()))
  163. date_less_than = condition["DateLessThan"]
  164. self.assertEqual(1, len(date_less_than.keys()))
  165. aws_epoch_time = date_less_than["AWS:EpochTime"]
  166. self.assertEqual(expires, aws_epoch_time)
  167. def test_custom_policy_valid_after(self):
  168. """
  169. Test that a custom policy can be created with a valid-after time and
  170. an arbitrary URL.
  171. """
  172. url = "http://1234567.cloudfront.com/*"
  173. valid_after = 999999
  174. policy = self.dist._custom_policy(url, valid_after=valid_after)
  175. policy = json.loads(policy)
  176. self.assertEqual(1, len(policy.keys()))
  177. statements = policy["Statement"]
  178. self.assertEqual(1, len(statements))
  179. statement = statements[0]
  180. resource = statement["Resource"]
  181. self.assertEqual(url, resource)
  182. condition = statement["Condition"]
  183. self.assertEqual(2, len(condition.keys()))
  184. date_less_than = condition["DateLessThan"]
  185. date_greater_than = condition["DateGreaterThan"]
  186. self.assertEqual(1, len(date_greater_than.keys()))
  187. aws_epoch_time = date_greater_than["AWS:EpochTime"]
  188. self.assertEqual(valid_after, aws_epoch_time)
  189. def test_custom_policy_ip_address(self):
  190. """
  191. Test that a custom policy can be created with an IP address and
  192. an arbitrary URL.
  193. """
  194. url = "http://1234567.cloudfront.com/*"
  195. ip_range = "192.168.0.1"
  196. policy = self.dist._custom_policy(url, ip_address=ip_range)
  197. policy = json.loads(policy)
  198. self.assertEqual(1, len(policy.keys()))
  199. statements = policy["Statement"]
  200. self.assertEqual(1, len(statements))
  201. statement = statements[0]
  202. resource = statement["Resource"]
  203. self.assertEqual(url, resource)
  204. condition = statement["Condition"]
  205. self.assertEqual(2, len(condition.keys()))
  206. ip_address = condition["IpAddress"]
  207. self.assertTrue("DateLessThan" in condition)
  208. self.assertEqual(1, len(ip_address.keys()))
  209. source_ip = ip_address["AWS:SourceIp"]
  210. self.assertEqual("%s/32" % ip_range, source_ip)
  211. def test_custom_policy_ip_range(self):
  212. """
  213. Test that a custom policy can be created with an IP address and
  214. an arbitrary URL.
  215. """
  216. url = "http://1234567.cloudfront.com/*"
  217. ip_range = "192.168.0.0/24"
  218. policy = self.dist._custom_policy(url, ip_address=ip_range)
  219. policy = json.loads(policy)
  220. self.assertEqual(1, len(policy.keys()))
  221. statements = policy["Statement"]
  222. self.assertEqual(1, len(statements))
  223. statement = statements[0]
  224. resource = statement["Resource"]
  225. self.assertEqual(url, resource)
  226. condition = statement["Condition"]
  227. self.assertEqual(2, len(condition.keys()))
  228. self.assertTrue("DateLessThan" in condition)
  229. ip_address = condition["IpAddress"]
  230. self.assertEqual(1, len(ip_address.keys()))
  231. source_ip = ip_address["AWS:SourceIp"]
  232. self.assertEqual(ip_range, source_ip)
  233. def test_custom_policy_all(self):
  234. """
  235. Test that a custom policy can be created with an IP address and
  236. an arbitrary URL.
  237. """
  238. url = "http://1234567.cloudfront.com/test.txt"
  239. expires = 999999
  240. valid_after = 111111
  241. ip_range = "192.168.0.0/24"
  242. policy = self.dist._custom_policy(url, expires=expires,
  243. valid_after=valid_after,
  244. ip_address=ip_range)
  245. policy = json.loads(policy)
  246. self.assertEqual(1, len(policy.keys()))
  247. statements = policy["Statement"]
  248. self.assertEqual(1, len(statements))
  249. statement = statements[0]
  250. resource = statement["Resource"]
  251. self.assertEqual(url, resource)
  252. condition = statement["Condition"]
  253. self.assertEqual(3, len(condition.keys()))
  254. #check expires condition
  255. date_less_than = condition["DateLessThan"]
  256. self.assertEqual(1, len(date_less_than.keys()))
  257. aws_epoch_time = date_less_than["AWS:EpochTime"]
  258. self.assertEqual(expires, aws_epoch_time)
  259. #check valid_after condition
  260. date_greater_than = condition["DateGreaterThan"]
  261. self.assertEqual(1, len(date_greater_than.keys()))
  262. aws_epoch_time = date_greater_than["AWS:EpochTime"]
  263. self.assertEqual(valid_after, aws_epoch_time)
  264. #check source ip address condition
  265. ip_address = condition["IpAddress"]
  266. self.assertEqual(1, len(ip_address.keys()))
  267. source_ip = ip_address["AWS:SourceIp"]
  268. self.assertEqual(ip_range, source_ip)
  269. def test_params_canned_policy(self):
  270. """
  271. Test the correct params are generated for a canned policy.
  272. """
  273. url = "http://d604721fxaaqy9.cloudfront.net/horizon.jpg?large=yes&license=yes"
  274. expire_time = 1258237200
  275. expected_sig = ("Nql641NHEUkUaXQHZINK1FZ~SYeUSoBJMxjdgqrzIdzV2gyE"
  276. "XPDNv0pYdWJkflDKJ3xIu7lbwRpSkG98NBlgPi4ZJpRRnVX4"
  277. "kXAJK6tdNx6FucDB7OVqzcxkxHsGFd8VCG1BkC-Afh9~lOCM"
  278. "IYHIaiOB6~5jt9w2EOwi6sIIqrg_")
  279. signed_url_params = self.dist._create_signing_params(url, self.pk_id, expire_time, private_key_string=self.pk_str)
  280. self.assertEqual(3, len(signed_url_params))
  281. self.assertEqual(signed_url_params["Expires"], "1258237200")
  282. self.assertEqual(signed_url_params["Signature"], expected_sig)
  283. self.assertEqual(signed_url_params["Key-Pair-Id"], "PK123456789754")
  284. def test_canned_policy(self):
  285. """
  286. Generate signed url from the Example Canned Policy in Amazon's
  287. documentation.
  288. """
  289. url = "http://d604721fxaaqy9.cloudfront.net/horizon.jpg?large=yes&license=yes"
  290. expire_time = 1258237200
  291. expected_url = "http://d604721fxaaqy9.cloudfront.net/horizon.jpg?large=yes&license=yes&Expires=1258237200&Signature=Nql641NHEUkUaXQHZINK1FZ~SYeUSoBJMxjdgqrzIdzV2gyEXPDNv0pYdWJkflDKJ3xIu7lbwRpSkG98NBlgPi4ZJpRRnVX4kXAJK6tdNx6FucDB7OVqzcxkxHsGFd8VCG1BkC-Afh9~lOCMIYHIaiOB6~5jt9w2EOwi6sIIqrg_&Key-Pair-Id=PK123456789754"
  292. signed_url = self.dist.create_signed_url(
  293. url, self.pk_id, expire_time, private_key_string=self.pk_str)
  294. self.assertEqual(expected_url, signed_url)