test_archive.py 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383
  1. # -*- coding: utf-8 -*-
  2. """
  3. Tests for the archive state
  4. """
  5. # Import Python libs
  6. from __future__ import absolute_import, print_function, unicode_literals
  7. import errno
  8. import logging
  9. import os
  10. # Import Salt libs
  11. import salt.utils.files
  12. import salt.utils.platform
  13. # Import Salt Testing libs
  14. from tests.support.case import ModuleCase
  15. from tests.support.helpers import Webserver, skip_if_not_root
  16. from tests.support.mixins import SaltReturnAssertsMixin
  17. from tests.support.runtests import RUNTIME_VARS
  18. from tests.support.unit import skipIf
  19. # Setup logging
  20. log = logging.getLogger(__name__)
  21. ARCHIVE_DIR = (
  22. os.path.join("c:/", "tmp") if salt.utils.platform.is_windows() else "/tmp/archive"
  23. )
  24. ARCHIVE_NAME = "custom.tar.gz"
  25. ARCHIVE_TAR_SOURCE = "http://localhost:{0}/{1}".format(9999, ARCHIVE_NAME)
  26. ARCHIVE_TAR_HASH = "md5=7643861ac07c30fe7d2310e9f25ca514"
  27. ARCHIVE_TAR_SHA_HASH = (
  28. "sha256=9591159d86f0a180e4e0645b2320d0235e23e66c66797df61508bf185e0ac1d2"
  29. )
  30. ARCHIVE_TAR_BAD_HASH = "md5=d41d8cd98f00b204e9800998ecf8427e"
  31. ARCHIVE_TAR_HASH_UPPER = "md5=7643861AC07C30FE7D2310E9F25CA514"
  32. class ArchiveTest(ModuleCase, SaltReturnAssertsMixin):
  33. """
  34. Validate the archive state
  35. """
  36. @classmethod
  37. def setUpClass(cls):
  38. cls.webserver = Webserver()
  39. cls.webserver.start()
  40. cls.archive_tar_source = cls.webserver.url("custom.tar.gz")
  41. cls.archive_local_tar_source = "file://{0}".format(
  42. os.path.join(RUNTIME_VARS.BASE_FILES, ARCHIVE_NAME)
  43. )
  44. cls.untar_file = os.path.join(ARCHIVE_DIR, "custom/README")
  45. @classmethod
  46. def tearDownClass(cls):
  47. cls.webserver.stop()
  48. def setUp(self):
  49. self._clear_archive_dir()
  50. def tearDown(self):
  51. self._clear_archive_dir()
  52. @staticmethod
  53. def _clear_archive_dir():
  54. try:
  55. salt.utils.files.rm_rf(ARCHIVE_DIR)
  56. except OSError as exc:
  57. if exc.errno != errno.ENOENT:
  58. raise
  59. def _check_extracted(self, path):
  60. """
  61. function to check if file was extracted
  62. """
  63. log.debug("Checking for extracted file: %s", path)
  64. self.assertTrue(os.path.isfile(path))
  65. def run_function(self, *args, **kwargs): # pylint: disable=arguments-differ
  66. ret = super(ArchiveTest, self).run_function(*args, **kwargs)
  67. log.debug("ret = %s", ret)
  68. return ret
  69. def run_state(self, *args, **kwargs): # pylint: disable=arguments-differ
  70. ret = super(ArchiveTest, self).run_state(*args, **kwargs)
  71. log.debug("ret = %s", ret)
  72. return ret
  73. def test_archive_extracted_skip_verify(self):
  74. """
  75. test archive.extracted with skip_verify
  76. """
  77. ret = self.run_state(
  78. "archive.extracted",
  79. name=ARCHIVE_DIR,
  80. source=self.archive_tar_source,
  81. archive_format="tar",
  82. skip_verify=True,
  83. )
  84. if "Timeout" in ret:
  85. self.skipTest("Timeout talking to local tornado server.")
  86. self.assertSaltTrueReturn(ret)
  87. self._check_extracted(self.untar_file)
  88. def test_archive_extracted_with_source_hash(self):
  89. """
  90. test archive.extracted without skip_verify
  91. only external resources work to check to
  92. ensure source_hash is verified correctly
  93. """
  94. ret = self.run_state(
  95. "archive.extracted",
  96. name=ARCHIVE_DIR,
  97. source=self.archive_tar_source,
  98. archive_format="tar",
  99. source_hash=ARCHIVE_TAR_HASH,
  100. )
  101. if "Timeout" in ret:
  102. self.skipTest("Timeout talking to local tornado server.")
  103. self.assertSaltTrueReturn(ret)
  104. self._check_extracted(self.untar_file)
  105. @skip_if_not_root
  106. def test_archive_extracted_with_root_user_and_group(self):
  107. """
  108. test archive.extracted with user and group set to "root"
  109. """
  110. r_group = "root"
  111. if salt.utils.platform.is_darwin():
  112. r_group = "wheel"
  113. ret = self.run_state(
  114. "archive.extracted",
  115. name=ARCHIVE_DIR,
  116. source=self.archive_tar_source,
  117. archive_format="tar",
  118. source_hash=ARCHIVE_TAR_HASH,
  119. user="root",
  120. group=r_group,
  121. )
  122. if "Timeout" in ret:
  123. self.skipTest("Timeout talking to local tornado server.")
  124. self.assertSaltTrueReturn(ret)
  125. self._check_extracted(self.untar_file)
  126. @skipIf(True, "SLOWTEST skip")
  127. def test_archive_extracted_with_strip_in_options(self):
  128. """
  129. test archive.extracted with --strip in options
  130. """
  131. ret = self.run_state(
  132. "archive.extracted",
  133. name=ARCHIVE_DIR,
  134. source=self.archive_tar_source,
  135. source_hash=ARCHIVE_TAR_HASH,
  136. options="--strip=1",
  137. enforce_toplevel=False,
  138. )
  139. if "Timeout" in ret:
  140. self.skipTest("Timeout talking to local tornado server.")
  141. self.assertSaltTrueReturn(ret)
  142. self._check_extracted(os.path.join(ARCHIVE_DIR, "README"))
  143. def test_archive_extracted_with_strip_components_in_options(self):
  144. """
  145. test archive.extracted with --strip-components in options
  146. """
  147. ret = self.run_state(
  148. "archive.extracted",
  149. name=ARCHIVE_DIR,
  150. source=self.archive_tar_source,
  151. source_hash=ARCHIVE_TAR_HASH,
  152. options="--strip-components=1",
  153. enforce_toplevel=False,
  154. )
  155. if "Timeout" in ret:
  156. self.skipTest("Timeout talking to local tornado server.")
  157. self.assertSaltTrueReturn(ret)
  158. self._check_extracted(os.path.join(ARCHIVE_DIR, "README"))
  159. @skipIf(True, "SLOWTEST skip")
  160. def test_archive_extracted_without_archive_format(self):
  161. """
  162. test archive.extracted with no archive_format option
  163. """
  164. ret = self.run_state(
  165. "archive.extracted",
  166. name=ARCHIVE_DIR,
  167. source=self.archive_tar_source,
  168. source_hash=ARCHIVE_TAR_HASH,
  169. )
  170. if "Timeout" in ret:
  171. self.skipTest("Timeout talking to local tornado server.")
  172. self.assertSaltTrueReturn(ret)
  173. self._check_extracted(self.untar_file)
  174. def test_archive_extracted_with_cmd_unzip_false(self):
  175. """
  176. test archive.extracted using use_cmd_unzip argument as false
  177. """
  178. ret = self.run_state(
  179. "archive.extracted",
  180. name=ARCHIVE_DIR,
  181. source=self.archive_tar_source,
  182. source_hash=ARCHIVE_TAR_HASH,
  183. use_cmd_unzip=False,
  184. archive_format="tar",
  185. )
  186. if "Timeout" in ret:
  187. self.skipTest("Timeout talking to local tornado server.")
  188. self.assertSaltTrueReturn(ret)
  189. self._check_extracted(self.untar_file)
  190. def test_local_archive_extracted(self):
  191. """
  192. test archive.extracted with local file
  193. """
  194. ret = self.run_state(
  195. "archive.extracted",
  196. name=ARCHIVE_DIR,
  197. source=self.archive_local_tar_source,
  198. archive_format="tar",
  199. )
  200. self.assertSaltTrueReturn(ret)
  201. self._check_extracted(self.untar_file)
  202. def test_local_archive_extracted_skip_verify(self):
  203. """
  204. test archive.extracted with local file, bad hash and skip_verify
  205. """
  206. ret = self.run_state(
  207. "archive.extracted",
  208. name=ARCHIVE_DIR,
  209. source=self.archive_local_tar_source,
  210. archive_format="tar",
  211. source_hash=ARCHIVE_TAR_BAD_HASH,
  212. skip_verify=True,
  213. )
  214. self.assertSaltTrueReturn(ret)
  215. self._check_extracted(self.untar_file)
  216. @skipIf(True, "SLOWTEST skip")
  217. def test_local_archive_extracted_with_source_hash(self):
  218. """
  219. test archive.extracted with local file and valid hash
  220. """
  221. ret = self.run_state(
  222. "archive.extracted",
  223. name=ARCHIVE_DIR,
  224. source=self.archive_local_tar_source,
  225. archive_format="tar",
  226. source_hash=ARCHIVE_TAR_HASH,
  227. )
  228. self.assertSaltTrueReturn(ret)
  229. self._check_extracted(self.untar_file)
  230. @skipIf(True, "SLOWTEST skip")
  231. def test_local_archive_extracted_with_bad_source_hash(self):
  232. """
  233. test archive.extracted with local file and bad hash
  234. """
  235. ret = self.run_state(
  236. "archive.extracted",
  237. name=ARCHIVE_DIR,
  238. source=self.archive_local_tar_source,
  239. archive_format="tar",
  240. source_hash=ARCHIVE_TAR_BAD_HASH,
  241. )
  242. self.assertSaltFalseReturn(ret)
  243. def test_local_archive_extracted_with_uppercase_source_hash(self):
  244. """
  245. test archive.extracted with local file and bad hash
  246. """
  247. ret = self.run_state(
  248. "archive.extracted",
  249. name=ARCHIVE_DIR,
  250. source=self.archive_local_tar_source,
  251. archive_format="tar",
  252. source_hash=ARCHIVE_TAR_HASH_UPPER,
  253. )
  254. self.assertSaltTrueReturn(ret)
  255. self._check_extracted(self.untar_file)
  256. @skipIf(True, "SLOWTEST skip")
  257. def test_archive_extracted_with_non_base_saltenv(self):
  258. """
  259. test archive.extracted with a saltenv other than `base`
  260. """
  261. ret = self.run_function(
  262. "state.sls",
  263. ["issue45893"],
  264. pillar={"issue45893.name": ARCHIVE_DIR},
  265. saltenv="prod",
  266. )
  267. self.assertSaltTrueReturn(ret)
  268. self._check_extracted(os.path.join(ARCHIVE_DIR, self.untar_file))
  269. @skipIf(True, "SLOWTEST skip")
  270. def test_local_archive_extracted_with_skip_files_list_verify(self):
  271. """
  272. test archive.extracted with local file and skip_files_list_verify set to True
  273. """
  274. expected_comment = (
  275. "existing source sum is the same as the expected one and "
  276. "skip_files_list_verify argument was set to True. "
  277. "Extraction is not needed"
  278. )
  279. ret = self.run_state(
  280. "archive.extracted",
  281. name=ARCHIVE_DIR,
  282. source=self.archive_local_tar_source,
  283. archive_format="tar",
  284. skip_files_list_verify=True,
  285. source_hash_update=True,
  286. source_hash=ARCHIVE_TAR_SHA_HASH,
  287. )
  288. self.assertSaltTrueReturn(ret)
  289. self._check_extracted(self.untar_file)
  290. ret = self.run_state(
  291. "archive.extracted",
  292. name=ARCHIVE_DIR,
  293. source=self.archive_local_tar_source,
  294. archive_format="tar",
  295. skip_files_list_verify=True,
  296. source_hash_update=True,
  297. source_hash=ARCHIVE_TAR_SHA_HASH,
  298. )
  299. self.assertSaltTrueReturn(ret)
  300. self.assertInSaltComment(expected_comment, ret)
  301. @skipIf(True, "SLOWTEST skip")
  302. def test_local_archive_extracted_trim_output(self):
  303. """
  304. test archive.extracted with local file and trim_output set to 1
  305. """
  306. expected_changes = {
  307. "directories_created": ["/tmp/archive/"],
  308. "extracted_files": ["custom"],
  309. }
  310. ret = self.run_state(
  311. "archive.extracted",
  312. name=ARCHIVE_DIR,
  313. source=self.archive_local_tar_source,
  314. archive_format="tar",
  315. skip_files_list_verify=True,
  316. source_hash_update=True,
  317. source_hash=ARCHIVE_TAR_SHA_HASH,
  318. trim_output=1,
  319. )
  320. self.assertSaltTrueReturn(ret)
  321. self._check_extracted(self.untar_file)
  322. state_ret = ret["archive_|-/tmp/archive_|-/tmp/archive_|-extracted"]
  323. self.assertTrue(
  324. state_ret["comment"].endswith("Output was trimmed to 1 number of lines")
  325. )
  326. self.assertEqual(state_ret["changes"], expected_changes)