chef-dk 0.8.0 → 0.9.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (299) hide show
  1. checksums.yaml +4 -4
  2. data/CONTRIBUTING.md +190 -190
  3. data/Gemfile +26 -0
  4. data/LICENSE +201 -201
  5. data/README.md +276 -276
  6. data/Rakefile +18 -18
  7. data/bin/chef +25 -25
  8. data/lib/chef-dk.rb +19 -19
  9. data/lib/chef-dk/authenticated_http.rb +40 -40
  10. data/lib/chef-dk/builtin_commands.rb +60 -60
  11. data/lib/chef-dk/chef_runner.rb +98 -98
  12. data/lib/chef-dk/cli.rb +200 -200
  13. data/lib/chef-dk/command/base.rb +79 -75
  14. data/lib/chef-dk/command/clean_policy_cookbooks.rb +116 -116
  15. data/lib/chef-dk/command/clean_policy_revisions.rb +113 -113
  16. data/lib/chef-dk/command/delete_policy.rb +122 -122
  17. data/lib/chef-dk/command/delete_policy_group.rb +122 -122
  18. data/lib/chef-dk/command/diff.rb +316 -316
  19. data/lib/chef-dk/command/env.rb +90 -90
  20. data/lib/chef-dk/command/exec.rb +45 -45
  21. data/lib/chef-dk/command/export.rb +151 -153
  22. data/lib/chef-dk/command/gem.rb +47 -47
  23. data/lib/chef-dk/command/generate.rb +120 -118
  24. data/lib/chef-dk/command/generator_commands.rb +80 -80
  25. data/lib/chef-dk/command/generator_commands/app.rb +107 -107
  26. data/lib/chef-dk/command/generator_commands/attribute.rb +37 -37
  27. data/lib/chef-dk/command/generator_commands/base.rb +121 -121
  28. data/lib/chef-dk/command/generator_commands/cookbook.rb +119 -108
  29. data/lib/chef-dk/command/generator_commands/cookbook_code_file.rb +100 -100
  30. data/lib/chef-dk/command/generator_commands/cookbook_file.rb +45 -45
  31. data/lib/chef-dk/command/generator_commands/generator_generator.rb +177 -0
  32. data/lib/chef-dk/command/generator_commands/lwrp.rb +36 -36
  33. data/lib/chef-dk/command/generator_commands/policyfile.rb +86 -83
  34. data/lib/chef-dk/command/generator_commands/recipe.rb +36 -36
  35. data/lib/chef-dk/command/generator_commands/repo.rb +96 -96
  36. data/lib/chef-dk/command/generator_commands/template.rb +46 -46
  37. data/lib/chef-dk/command/install.rb +121 -121
  38. data/lib/chef-dk/command/provision.rb +438 -438
  39. data/lib/chef-dk/command/push.rb +118 -118
  40. data/lib/chef-dk/command/push_archive.rb +126 -126
  41. data/lib/chef-dk/command/shell_init.rb +180 -180
  42. data/lib/chef-dk/command/show_policy.rb +165 -165
  43. data/lib/chef-dk/command/undelete.rb +155 -155
  44. data/lib/chef-dk/command/update.rb +129 -129
  45. data/lib/chef-dk/command/verify.rb +490 -453
  46. data/lib/chef-dk/commands_map.rb +115 -115
  47. data/lib/chef-dk/completions/bash.sh.erb +5 -5
  48. data/lib/chef-dk/completions/chef.fish.erb +10 -10
  49. data/lib/chef-dk/completions/zsh.zsh.erb +21 -21
  50. data/lib/chef-dk/component_test.rb +171 -171
  51. data/lib/chef-dk/configurable.rb +57 -52
  52. data/lib/chef-dk/cookbook_metadata.rb +45 -45
  53. data/lib/chef-dk/cookbook_omnifetch.rb +32 -32
  54. data/lib/chef-dk/cookbook_profiler/git.rb +151 -151
  55. data/lib/chef-dk/cookbook_profiler/identifiers.rb +72 -72
  56. data/lib/chef-dk/cookbook_profiler/null_scm.rb +32 -32
  57. data/lib/chef-dk/exceptions.rb +113 -113
  58. data/lib/chef-dk/generator.rb +163 -162
  59. data/lib/chef-dk/helpers.rb +159 -159
  60. data/lib/chef-dk/pager.rb +106 -106
  61. data/lib/chef-dk/policyfile/chef_repo_cookbook_source.rb +122 -122
  62. data/lib/chef-dk/policyfile/chef_server_cookbook_source.rb +54 -54
  63. data/lib/chef-dk/policyfile/community_cookbook_source.rb +82 -82
  64. data/lib/chef-dk/policyfile/comparison_base.rb +124 -124
  65. data/lib/chef-dk/policyfile/cookbook_location_specification.rb +133 -133
  66. data/lib/chef-dk/policyfile/cookbook_locks.rb +466 -466
  67. data/lib/chef-dk/policyfile/cookbook_sources.rb +21 -21
  68. data/lib/chef-dk/policyfile/differ.rb +266 -266
  69. data/lib/chef-dk/policyfile/dsl.rb +197 -197
  70. data/lib/chef-dk/policyfile/lister.rb +232 -232
  71. data/lib/chef-dk/policyfile/null_cookbook_source.rb +45 -45
  72. data/lib/chef-dk/policyfile/read_cookbook_for_compat_mode_upload.rb +124 -124
  73. data/lib/chef-dk/policyfile/reports/install.rb +70 -70
  74. data/lib/chef-dk/policyfile/reports/table_printer.rb +58 -58
  75. data/lib/chef-dk/policyfile/reports/upload.rb +70 -70
  76. data/lib/chef-dk/policyfile/solution_dependencies.rb +298 -298
  77. data/lib/chef-dk/policyfile/storage_config.rb +100 -100
  78. data/lib/chef-dk/policyfile/undo_record.rb +142 -142
  79. data/lib/chef-dk/policyfile/undo_stack.rb +130 -130
  80. data/lib/chef-dk/policyfile/uploader.rb +213 -213
  81. data/lib/chef-dk/policyfile_compiler.rb +322 -322
  82. data/lib/chef-dk/policyfile_lock.rb +552 -552
  83. data/lib/chef-dk/policyfile_services/clean_policies.rb +95 -95
  84. data/lib/chef-dk/policyfile_services/clean_policy_cookbooks.rb +125 -125
  85. data/lib/chef-dk/policyfile_services/export_repo.rb +309 -281
  86. data/lib/chef-dk/policyfile_services/install.rb +125 -125
  87. data/lib/chef-dk/policyfile_services/push.rb +114 -114
  88. data/lib/chef-dk/policyfile_services/push_archive.rb +173 -173
  89. data/lib/chef-dk/policyfile_services/rm_policy.rb +142 -142
  90. data/lib/chef-dk/policyfile_services/rm_policy_group.rb +86 -86
  91. data/lib/chef-dk/policyfile_services/show_policy.rb +237 -237
  92. data/lib/chef-dk/policyfile_services/undelete.rb +108 -108
  93. data/lib/chef-dk/policyfile_services/update_attributes.rb +104 -104
  94. data/lib/chef-dk/service_exception_inspectors.rb +25 -25
  95. data/lib/chef-dk/service_exception_inspectors/base.rb +40 -40
  96. data/lib/chef-dk/service_exception_inspectors/http.rb +121 -121
  97. data/lib/chef-dk/service_exceptions.rb +143 -143
  98. data/lib/chef-dk/shell_out.rb +36 -36
  99. data/lib/chef-dk/skeletons/code_generator/files/default/Berksfile +3 -3
  100. data/lib/chef-dk/skeletons/code_generator/files/default/chefignore +100 -100
  101. data/lib/chef-dk/skeletons/code_generator/files/default/cookbook_readmes/README-policy.md +9 -9
  102. data/lib/chef-dk/skeletons/code_generator/files/default/cookbook_readmes/README.md +54 -54
  103. data/lib/chef-dk/skeletons/code_generator/files/default/gitignore +16 -16
  104. data/lib/chef-dk/skeletons/code_generator/files/default/repo/README.md +28 -28
  105. data/lib/chef-dk/skeletons/code_generator/files/default/repo/cookbooks/example/README.md +27 -0
  106. data/lib/chef-dk/skeletons/code_generator/files/default/repo/cookbooks/example/attributes/default.rb +7 -7
  107. data/lib/chef-dk/skeletons/code_generator/files/default/repo/cookbooks/example/metadata.rb +3 -3
  108. data/lib/chef-dk/skeletons/code_generator/files/default/repo/cookbooks/example/recipes/default.rb +8 -8
  109. data/lib/chef-dk/skeletons/code_generator/files/default/repo/data_bags/README.md +57 -57
  110. data/lib/chef-dk/skeletons/code_generator/files/default/repo/data_bags/example/example_item.json +3 -3
  111. data/lib/chef-dk/skeletons/code_generator/files/default/repo/environments/README.md +9 -9
  112. data/lib/chef-dk/skeletons/code_generator/files/default/repo/environments/example.json +12 -12
  113. data/lib/chef-dk/skeletons/code_generator/files/default/repo/roles/README.md +8 -8
  114. data/lib/chef-dk/skeletons/code_generator/files/default/repo/roles/example.json +12 -12
  115. data/lib/chef-dk/skeletons/code_generator/files/default/serverspec_spec_helper.rb +8 -3
  116. data/lib/chef-dk/skeletons/code_generator/files/default/spec_helper.rb +2 -2
  117. data/lib/chef-dk/skeletons/code_generator/metadata.rb +8 -8
  118. data/lib/chef-dk/skeletons/code_generator/recipes/app.rb +97 -97
  119. data/lib/chef-dk/skeletons/code_generator/recipes/attribute.rb +12 -12
  120. data/lib/chef-dk/skeletons/code_generator/recipes/cookbook.rb +104 -92
  121. data/lib/chef-dk/skeletons/code_generator/recipes/cookbook_file.rb +24 -24
  122. data/lib/chef-dk/skeletons/code_generator/recipes/lwrp.rb +23 -23
  123. data/lib/chef-dk/skeletons/code_generator/recipes/policyfile.rb +8 -8
  124. data/lib/chef-dk/skeletons/code_generator/recipes/recipe.rb +27 -27
  125. data/lib/chef-dk/skeletons/code_generator/recipes/repo.rb +48 -47
  126. data/lib/chef-dk/skeletons/code_generator/recipes/template.rb +32 -32
  127. data/lib/chef-dk/skeletons/code_generator/templates/default/LICENSE.all_rights.erb +3 -3
  128. data/lib/chef-dk/skeletons/code_generator/templates/default/LICENSE.apache2.erb +201 -201
  129. data/lib/chef-dk/skeletons/code_generator/templates/default/LICENSE.gplv2.erb +339 -339
  130. data/lib/chef-dk/skeletons/code_generator/templates/default/LICENSE.gplv3.erb +674 -674
  131. data/lib/chef-dk/skeletons/code_generator/templates/default/LICENSE.mit.erb +21 -21
  132. data/lib/chef-dk/skeletons/code_generator/templates/default/Policyfile.rb.erb +20 -16
  133. data/lib/chef-dk/skeletons/code_generator/templates/default/README.md.erb +4 -4
  134. data/lib/chef-dk/skeletons/code_generator/templates/default/kitchen.yml.erb +16 -16
  135. data/lib/chef-dk/skeletons/code_generator/templates/default/kitchen_policyfile.yml.erb +27 -0
  136. data/lib/chef-dk/skeletons/code_generator/templates/default/metadata.rb.erb +7 -7
  137. data/lib/chef-dk/skeletons/code_generator/templates/default/recipe.rb.erb +5 -5
  138. data/lib/chef-dk/skeletons/code_generator/templates/default/recipe_spec.rb.erb +20 -20
  139. data/lib/chef-dk/skeletons/code_generator/templates/default/repo/gitignore.erb +11 -11
  140. data/lib/chef-dk/skeletons/code_generator/templates/default/serverspec_default_spec.rb.erb +9 -9
  141. data/lib/chef-dk/ui.rb +58 -58
  142. data/lib/chef-dk/version.rb +20 -20
  143. data/lib/kitchen/provisioner/policyfile_zero.rb +193 -164
  144. data/spec/shared/a_file_generator.rb +125 -125
  145. data/spec/shared/a_generated_file.rb +12 -12
  146. data/spec/shared/command_with_ui_object.rb +11 -11
  147. data/spec/shared/custom_generator_cookbook.rb +117 -117
  148. data/spec/shared/fixture_cookbook_checksums.rb +47 -47
  149. data/spec/shared/setup_git_cookbooks.rb +53 -53
  150. data/spec/spec_helper.rb +49 -48
  151. data/spec/test_helpers.rb +84 -84
  152. data/spec/unit/chef_runner_spec.rb +111 -110
  153. data/spec/unit/cli_spec.rb +357 -357
  154. data/spec/unit/command/base_spec.rb +169 -136
  155. data/spec/unit/command/clean_policy_cookbooks_spec.rb +181 -181
  156. data/spec/unit/command/clean_policy_revisions_spec.rb +181 -181
  157. data/spec/unit/command/delete_policy_group_spec.rb +207 -207
  158. data/spec/unit/command/delete_policy_spec.rb +207 -207
  159. data/spec/unit/command/diff_spec.rb +312 -312
  160. data/spec/unit/command/env_spec.rb +52 -52
  161. data/spec/unit/command/exec_spec.rb +179 -179
  162. data/spec/unit/command/export_spec.rb +189 -189
  163. data/spec/unit/command/generate_spec.rb +142 -142
  164. data/spec/unit/command/generator_commands/app_spec.rb +169 -169
  165. data/spec/unit/command/generator_commands/attribute_spec.rb +32 -32
  166. data/spec/unit/command/generator_commands/cookbook_file_spec.rb +32 -32
  167. data/spec/unit/command/generator_commands/cookbook_spec.rb +320 -240
  168. data/spec/unit/command/generator_commands/generator_generator_spec.rb +229 -0
  169. data/spec/unit/command/generator_commands/lwrp_spec.rb +32 -32
  170. data/spec/unit/command/generator_commands/policyfile_spec.rb +125 -125
  171. data/spec/unit/command/generator_commands/recipe_spec.rb +34 -34
  172. data/spec/unit/command/generator_commands/repo_spec.rb +283 -283
  173. data/spec/unit/command/generator_commands/template_spec.rb +32 -32
  174. data/spec/unit/command/install_spec.rb +179 -179
  175. data/spec/unit/command/provision_spec.rb +592 -592
  176. data/spec/unit/command/push_archive_spec.rb +153 -153
  177. data/spec/unit/command/push_spec.rb +199 -199
  178. data/spec/unit/command/shell_init_spec.rb +329 -329
  179. data/spec/unit/command/show_policy_spec.rb +235 -235
  180. data/spec/unit/command/undelete_spec.rb +246 -246
  181. data/spec/unit/command/update_spec.rb +251 -251
  182. data/spec/unit/command/verify_spec.rb +323 -322
  183. data/spec/unit/commands_map_spec.rb +57 -57
  184. data/spec/unit/component_test_spec.rb +126 -126
  185. data/spec/unit/cookbook_metadata_spec.rb +98 -98
  186. data/spec/unit/cookbook_profiler/git_spec.rb +176 -176
  187. data/spec/unit/cookbook_profiler/identifiers_spec.rb +83 -83
  188. data/spec/unit/fixtures/chef-runner-cookbooks/test_cookbook/recipes/recipe_one.rb +9 -9
  189. data/spec/unit/fixtures/chef-runner-cookbooks/test_cookbook/recipes/recipe_two.rb +9 -9
  190. data/spec/unit/fixtures/command/cli_test_command.rb +26 -26
  191. data/spec/unit/fixtures/command/explicit_path_example.rb +7 -7
  192. data/spec/unit/fixtures/cookbook_cache/baz-f59ee7a5bca6a4e606b67f7f856b768d847c39bb/.kitchen.yml +16 -16
  193. data/spec/unit/fixtures/cookbook_cache/baz-f59ee7a5bca6a4e606b67f7f856b768d847c39bb/Berksfile +3 -3
  194. data/spec/unit/fixtures/cookbook_cache/baz-f59ee7a5bca6a4e606b67f7f856b768d847c39bb/README.md +4 -4
  195. data/spec/unit/fixtures/cookbook_cache/baz-f59ee7a5bca6a4e606b67f7f856b768d847c39bb/chefignore +96 -96
  196. data/spec/unit/fixtures/cookbook_cache/baz-f59ee7a5bca6a4e606b67f7f856b768d847c39bb/metadata.rb +8 -8
  197. data/spec/unit/fixtures/cookbook_cache/baz-f59ee7a5bca6a4e606b67f7f856b768d847c39bb/recipes/default.rb +8 -8
  198. data/spec/unit/fixtures/cookbook_cache/dep_of_bar-1.2.3/.kitchen.yml +16 -16
  199. data/spec/unit/fixtures/cookbook_cache/dep_of_bar-1.2.3/Berksfile +3 -3
  200. data/spec/unit/fixtures/cookbook_cache/dep_of_bar-1.2.3/README.md +4 -4
  201. data/spec/unit/fixtures/cookbook_cache/dep_of_bar-1.2.3/chefignore +96 -96
  202. data/spec/unit/fixtures/cookbook_cache/dep_of_bar-1.2.3/metadata.rb +8 -8
  203. data/spec/unit/fixtures/cookbook_cache/dep_of_bar-1.2.3/recipes/default.rb +8 -8
  204. data/spec/unit/fixtures/cookbook_cache/foo-1.0.0/.kitchen.yml +16 -16
  205. data/spec/unit/fixtures/cookbook_cache/foo-1.0.0/Berksfile +3 -3
  206. data/spec/unit/fixtures/cookbook_cache/foo-1.0.0/README.md +4 -4
  207. data/spec/unit/fixtures/cookbook_cache/foo-1.0.0/chefignore +96 -96
  208. data/spec/unit/fixtures/cookbook_cache/foo-1.0.0/metadata.rb +8 -8
  209. data/spec/unit/fixtures/cookbook_cache/foo-1.0.0/recipes/default.rb +8 -8
  210. data/spec/unit/fixtures/cookbooks_api/pruned_small_universe.json +1321 -1321
  211. data/spec/unit/fixtures/cookbooks_api/small_universe.json +2987 -2987
  212. data/spec/unit/fixtures/cookbooks_api/universe.json +1 -1
  213. data/spec/unit/fixtures/cookbooks_api/update_fixtures.rb +36 -36
  214. data/spec/unit/fixtures/dev_cookbooks/README.md +16 -16
  215. data/spec/unit/fixtures/eg_omnibus_dir/valid/embedded/apps/berkshelf/integration_test +2 -2
  216. data/spec/unit/fixtures/eg_omnibus_dir/valid/embedded/apps/berkshelf/verify_me +5 -5
  217. data/spec/unit/fixtures/eg_omnibus_dir/valid/embedded/apps/chef/verify_me +3 -3
  218. data/spec/unit/fixtures/eg_omnibus_dir/valid/embedded/apps/test-kitchen/verify_me +2 -2
  219. data/spec/unit/fixtures/example_cookbook/.gitignore +17 -17
  220. data/spec/unit/fixtures/example_cookbook/.kitchen.yml +16 -16
  221. data/spec/unit/fixtures/example_cookbook/Berksfile +3 -3
  222. data/spec/unit/fixtures/example_cookbook/README.md +4 -4
  223. data/spec/unit/fixtures/example_cookbook/chefignore +96 -96
  224. data/spec/unit/fixtures/example_cookbook/metadata.rb +8 -8
  225. data/spec/unit/fixtures/example_cookbook/recipes/default.rb +8 -8
  226. data/spec/unit/fixtures/example_cookbook_metadata_json_only/.gitignore +17 -17
  227. data/spec/unit/fixtures/example_cookbook_metadata_json_only/.kitchen.yml +16 -16
  228. data/spec/unit/fixtures/example_cookbook_metadata_json_only/Berksfile +3 -3
  229. data/spec/unit/fixtures/example_cookbook_metadata_json_only/README.md +4 -4
  230. data/spec/unit/fixtures/example_cookbook_metadata_json_only/chefignore +96 -96
  231. data/spec/unit/fixtures/example_cookbook_metadata_json_only/metadata.json +5 -5
  232. data/spec/unit/fixtures/example_cookbook_metadata_json_only/recipes/default.rb +8 -8
  233. data/spec/unit/fixtures/example_cookbook_no_metadata/.gitignore +17 -17
  234. data/spec/unit/fixtures/example_cookbook_no_metadata/.kitchen.yml +16 -16
  235. data/spec/unit/fixtures/example_cookbook_no_metadata/Berksfile +3 -3
  236. data/spec/unit/fixtures/example_cookbook_no_metadata/README.md +4 -4
  237. data/spec/unit/fixtures/example_cookbook_no_metadata/chefignore +96 -96
  238. data/spec/unit/fixtures/example_cookbook_no_metadata/recipes/default.rb +8 -8
  239. data/spec/unit/fixtures/local_path_cookbooks/another-local-cookbook/README.md +4 -4
  240. data/spec/unit/fixtures/local_path_cookbooks/another-local-cookbook/chefignore +96 -96
  241. data/spec/unit/fixtures/local_path_cookbooks/another-local-cookbook/metadata.rb +8 -8
  242. data/spec/unit/fixtures/local_path_cookbooks/another-local-cookbook/recipes/default.rb +8 -8
  243. data/spec/unit/fixtures/local_path_cookbooks/cookbook-with-a-dep/Berksfile +3 -3
  244. data/spec/unit/fixtures/local_path_cookbooks/cookbook-with-a-dep/README.md +4 -4
  245. data/spec/unit/fixtures/local_path_cookbooks/cookbook-with-a-dep/chefignore +96 -96
  246. data/spec/unit/fixtures/local_path_cookbooks/cookbook-with-a-dep/metadata.rb +9 -9
  247. data/spec/unit/fixtures/local_path_cookbooks/cookbook-with-a-dep/recipes/default.rb +8 -8
  248. data/spec/unit/fixtures/local_path_cookbooks/local-cookbook/.kitchen.yml +16 -16
  249. data/spec/unit/fixtures/local_path_cookbooks/local-cookbook/Berksfile +3 -3
  250. data/spec/unit/fixtures/local_path_cookbooks/local-cookbook/README.md +4 -4
  251. data/spec/unit/fixtures/local_path_cookbooks/local-cookbook/chefignore +96 -96
  252. data/spec/unit/fixtures/local_path_cookbooks/local-cookbook/metadata.rb +8 -8
  253. data/spec/unit/fixtures/local_path_cookbooks/local-cookbook/recipes/default.rb +8 -8
  254. data/spec/unit/fixtures/local_path_cookbooks/metadata-missing/README.md +2 -2
  255. data/spec/unit/fixtures/local_path_cookbooks/noignore-f59ee7a5bca6a4e606b67f7f856b768d847c39bb/.kitchen.yml +16 -16
  256. data/spec/unit/fixtures/local_path_cookbooks/noignore-f59ee7a5bca6a4e606b67f7f856b768d847c39bb/README.md +4 -4
  257. data/spec/unit/fixtures/local_path_cookbooks/noignore-f59ee7a5bca6a4e606b67f7f856b768d847c39bb/metadata.rb +8 -8
  258. data/spec/unit/fixtures/local_path_cookbooks/noignore-f59ee7a5bca6a4e606b67f7f856b768d847c39bb/recipes/default.rb +8 -8
  259. data/spec/unit/generator_spec.rb +120 -120
  260. data/spec/unit/helpers_spec.rb +92 -92
  261. data/spec/unit/pager_spec.rb +119 -119
  262. data/spec/unit/policyfile/chef_repo_cookbook_source_spec.rb +66 -66
  263. data/spec/unit/policyfile/chef_server_cookbook_source_spec.rb +34 -34
  264. data/spec/unit/policyfile/community_cookbook_source_spec.rb +51 -51
  265. data/spec/unit/policyfile/comparison_base_spec.rb +343 -343
  266. data/spec/unit/policyfile/cookbook_location_specification_spec.rb +252 -252
  267. data/spec/unit/policyfile/cookbook_locks_spec.rb +529 -529
  268. data/spec/unit/policyfile/differ_spec.rb +687 -687
  269. data/spec/unit/policyfile/lister_spec.rb +272 -272
  270. data/spec/unit/policyfile/null_cookbook_source_spec.rb +35 -35
  271. data/spec/unit/policyfile/read_cookbook_for_compat_mode_upload_spec.rb +92 -92
  272. data/spec/unit/policyfile/reports/install_spec.rb +115 -115
  273. data/spec/unit/policyfile/reports/upload_spec.rb +96 -96
  274. data/spec/unit/policyfile/solution_dependencies_spec.rb +145 -145
  275. data/spec/unit/policyfile/storage_config_spec.rb +172 -172
  276. data/spec/unit/policyfile/undo_record_spec.rb +260 -260
  277. data/spec/unit/policyfile/undo_stack_spec.rb +266 -266
  278. data/spec/unit/policyfile/uploader_spec.rb +410 -410
  279. data/spec/unit/policyfile_demands_spec.rb +876 -876
  280. data/spec/unit/policyfile_evaluation_spec.rb +441 -441
  281. data/spec/unit/policyfile_lock_build_spec.rb +1056 -1056
  282. data/spec/unit/policyfile_lock_install_spec.rb +138 -138
  283. data/spec/unit/policyfile_lock_serialization_spec.rb +425 -425
  284. data/spec/unit/policyfile_lock_validation_spec.rb +611 -611
  285. data/spec/unit/policyfile_services/clean_policies_spec.rb +236 -236
  286. data/spec/unit/policyfile_services/clean_policy_cookbooks_spec.rb +275 -275
  287. data/spec/unit/policyfile_services/export_repo_spec.rb +439 -416
  288. data/spec/unit/policyfile_services/install_spec.rb +191 -191
  289. data/spec/unit/policyfile_services/push_archive_spec.rb +345 -345
  290. data/spec/unit/policyfile_services/push_spec.rb +233 -233
  291. data/spec/unit/policyfile_services/rm_policy_group_spec.rb +241 -241
  292. data/spec/unit/policyfile_services/rm_policy_spec.rb +266 -266
  293. data/spec/unit/policyfile_services/show_policy_spec.rb +889 -889
  294. data/spec/unit/policyfile_services/undelete_spec.rb +304 -304
  295. data/spec/unit/policyfile_services/update_attributes_spec.rb +217 -217
  296. data/spec/unit/service_exception_inspectors/base_spec.rb +43 -43
  297. data/spec/unit/service_exception_inspectors/http_spec.rb +140 -140
  298. data/spec/unit/shell_out_spec.rb +34 -34
  299. metadata +9 -3
@@ -1,453 +1,490 @@
1
- #
2
- # Copyright:: Copyright (c) 2014 Chef Software Inc.
3
- # License:: Apache License, Version 2.0
4
- #
5
- # Licensed under the Apache License, Version 2.0 (the "License");
6
- # you may not use this file except in compliance with the License.
7
- # You may obtain a copy of the License at
8
- #
9
- # http://www.apache.org/licenses/LICENSE-2.0
10
- #
11
- # Unless required by applicable law or agreed to in writing, software
12
- # distributed under the License is distributed on an "AS IS" BASIS,
13
- # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14
- # See the License for the specific language governing permissions and
15
- # limitations under the License.
16
- #
17
-
18
- require 'chef-dk/command/base'
19
- require 'chef-dk/exceptions'
20
- require 'chef-dk/component_test'
21
-
22
- module ChefDK
23
- module Command
24
- class Verify < ChefDK::Command::Base
25
-
26
- include ChefDK::Helpers
27
-
28
- banner "Usage: chef verify [component, ...] [options]"
29
-
30
- option :omnibus_dir,
31
- :long => "--omnibus-dir OMNIBUS_DIR",
32
- :description => "Alternate path to omnibus install (used for testing)"
33
-
34
- option :unit,
35
- :long => "--unit",
36
- :description => "Run bundled app unit tests (only smoke tests run by default)"
37
-
38
- option :integration,
39
- :long => "--integration",
40
- :description => "Run integration tests. Possibly dangerous, for development systems only"
41
-
42
- option :verbose,
43
- :long => "--verbose",
44
- :description => "Display all test output, not just failing tests"
45
-
46
- class << self
47
- def add_component(name, _delete_me=nil)
48
- component = ComponentTest.new(name)
49
- yield component if block_given? #delete this conditional
50
- component_map[name] = component
51
- end
52
-
53
- def component(name)
54
- component_map[name]
55
- end
56
-
57
- def components
58
- component_map.values
59
- end
60
-
61
- def component_map
62
- @component_map ||= {}
63
- end
64
- end
65
-
66
- def components
67
- self.class.components
68
- end
69
-
70
- #
71
- # Components included in Chef Development kit:
72
- # :base_dir => Relative path of the component w.r.t. omnibus_apps_dir
73
- # :test_cmd => Test command to be launched for the component
74
- #
75
- add_component "berkshelf" do |c|
76
- c.base_dir = "berkshelf"
77
- # For berks the real command to run is "bundle exec thor spec:ci"
78
- # We can't run it right now since graphviz specs are included in the
79
- # test suite by default. We will be able to switch to that command when/if
80
- # Graphviz is added to omnibus.
81
- c.unit_test { sh("bundle exec rspec --color --format progress spec/unit --tag ~graphviz") }
82
- c.integration_test { sh("bundle exec cucumber --color --format progress --tags ~@no_run --tags ~@spawn --tags ~@graphviz --strict") }
83
-
84
- c.smoke_test do
85
- tmpdir do |cwd|
86
- FileUtils.touch(File.join(cwd,"Berksfile"))
87
- sh("berks install", cwd: cwd)
88
- end
89
- end
90
- end
91
-
92
- add_component "test-kitchen" do |c|
93
- c.base_dir = "test-kitchen"
94
- c.unit_test { sh("bundle exec rake unit") }
95
- c.integration_test { sh("bundle exec rake features") }
96
-
97
- # NOTE: By default, kitchen tries to be helpful and install a driver
98
- # gem for you. This causes a race condition when running the tests
99
- # concurrently, because rubygems breaks when there are partially
100
- # installed gems in the gem repository. Instructing kitchen to create a
101
- # gemfile instead avoids the gem installation.
102
- c.smoke_test { run_in_tmpdir("kitchen init --create-gemfile") }
103
- end
104
-
105
- add_component "chef-client" do |c|
106
- c.base_dir = "chef"
107
- c.unit_test { sh("bundle exec rspec -fp -t '~volatile_from_verify' spec/unit") }
108
- c.integration_test { sh("bundle exec rspec -fp spec/integration spec/functional") }
109
-
110
- c.smoke_test do
111
- tmpdir do |cwd|
112
- FileUtils.touch(File.join(cwd, "apply.rb"))
113
- sh("chef-apply apply.rb", cwd: cwd)
114
- end
115
- end
116
- end
117
-
118
- add_component "chef-dk" do |c|
119
- c.base_dir = "chef-dk"
120
- c.unit_test { sh("bundle exec rspec") }
121
- c.smoke_test { run_in_tmpdir("chef generate cookbook example") }
122
- end
123
-
124
- # entirely possible this needs to be driven by a utility method in chef-provisioning.
125
- add_component "chef-provisioning" do |c|
126
- c.base_dir = "chef-dk"
127
-
128
- c.smoke_test do
129
- # ------------
130
- # we want to avoid hard-coding driver names, but calling Gem::Specification produces a warning;
131
- # changing $VERBOSE seems to be the best way to silence it.
132
- verbose = $VERBOSE
133
- $VERBOSE = nil
134
-
135
- # construct a hash of { driver_name => [version1, version2, ...]}
136
- driver_versions = {}
137
- Gem::Specification.all.map { |gs| [gs.name, gs.version] }.
138
- select { |n| n[0] =~ /^chef-provisioning-/ }.
139
- each { |gem, version| (driver_versions[gem] ||= []) << version }
140
-
141
- drivers = Gem::Specification.all.map { |gs| gs.name }.
142
- select { |n| n =~ /^chef-provisioning-/ }.
143
- uniq
144
-
145
- versions = Gem::Specification.find_all_by_name("chef-provisioning").map { |s| s.version }
146
- $VERBOSE = verbose
147
- # ------------
148
- failures = []
149
-
150
- # ------------
151
- # fail the verify if we have more than one version of chef-provisioning or any of its drivers.
152
- def format_gem_failure(name, versions)
153
- <<-EOS
154
- #{name} has multiple versions installed:
155
- #{versions.sort.map { |gv| " #{gv.to_s}" }.join("\n")}
156
- EOS
157
- end
158
-
159
- failures << format_gem_failure("chef-provisioning", versions) if versions.size > 1
160
-
161
- driver_versions.keys.sort.each do |driver_name|
162
- v = driver_versions[driver_name]
163
- failures << format_gem_failure(driver_name, v) if v.size > 1
164
- end
165
-
166
- if failures.size > 0
167
- failures << <<-EOS
168
-
169
- Some applications may need or prefer different versions of the chef-provisioning gem or its drivers, so
170
- this multiple-version check can fail if a user has installed new versions of those libraries.
171
- EOS
172
- end
173
-
174
- # ------------
175
- # load the core gem and all of the drivers (ignoring versions).
176
- require "chef/provisioning"
177
- drivers.map { |d| "#{d.gsub('-', '/')}_driver" }.each do |driver_gem|
178
- begin
179
- begin
180
- require driver_gem
181
- rescue LoadError
182
- # anomalously, chef-provisioning-fog does not have a fog_driver.rb. (9/2015)
183
- require "#{driver_gem}/driver.rb"
184
- end
185
- rescue LoadError => ex
186
- puts ex
187
- end
188
- end
189
-
190
- # ------------
191
- # look for version dependency conflicts.
192
- tmpdir do |cwd|
193
- versions.each do |provisioning_version|
194
- gemfile = "chef-provisioning-#{provisioning_version}-chefdk-test.gemfile"
195
-
196
- # write out the gemfile for this chef-provisioning version, and see if Bundler can make it go.
197
- with_file(File.join(cwd, gemfile)) do |f|
198
- f.puts %Q(gem "chef-provisioning", "= #{provisioning_version}")
199
- drivers.each { |d| f.puts %Q(gem "#{d}") }
200
- end
201
-
202
- result = sh("bundle install --local --quiet", cwd: cwd, env: {"BUNDLE_GEMFILE" => gemfile })
203
-
204
- if result.exitstatus != 0
205
- failures << result.stdout
206
- end
207
- end # end provisioning versions.
208
-
209
- failures.each { |fail| puts fail }
210
-
211
- # dubious on Windows.
212
- # this is weird, but we seem to require a Mixlib::ShellOut as the return value. suggestions
213
- # welcome.
214
- sh(failures.size > 0 ? "false" : "true")
215
- end
216
- end
217
- end
218
-
219
- add_component "chefspec" do |c|
220
- c.gem_base_dir = "chefspec"
221
- c.unit_test { sh("rake unit") }
222
- c.smoke_test do
223
- tmpdir do |cwd|
224
- FileUtils.mkdir(File.join(cwd, "spec"))
225
- with_file(File.join(cwd, "spec", "spec_helper.rb")) do |f|
226
- f.write <<-EOF
227
- require 'chefspec'
228
- require 'chefspec/berkshelf'
229
- require 'chefspec/cacher'
230
-
231
- RSpec.configure do |config|
232
- config.expect_with(:rspec) { |c| c.syntax = :expect }
233
- end
234
- EOF
235
- end
236
- FileUtils.touch(File.join(cwd, "Berksfile"))
237
- with_file(File.join(cwd, "spec", "foo_spec.rb")) do |f|
238
- f.write <<-EOF
239
- require 'spec_helper'
240
- EOF
241
- end
242
- sh("rspec", cwd: cwd)
243
- end
244
- end
245
- end
246
-
247
- add_component "rubocop" do |c|
248
- c.gem_base_dir = "rubocop"
249
- c.smoke_test do
250
- tmpdir do |cwd|
251
- with_file(File.join(cwd, 'foo.rb')) do |f|
252
- f.write <<-EOF
253
- def foo
254
- puts 'foo'
255
- end
256
- EOF
257
- end
258
- sh("rubocop foo.rb -l", cwd: cwd)
259
- end
260
- end
261
- end
262
-
263
- add_component "fauxhai" do |c|
264
- c.gem_base_dir = "fauxhai"
265
- c.smoke_test { sh("gem list fauxhai") }
266
- end
267
-
268
- add_component "knife-spork" do |c|
269
- c.gem_base_dir = "knife-spork"
270
- c.smoke_test { sh('knife spork info')}
271
- end
272
-
273
- add_component "kitchen-vagrant" do |c|
274
- c.gem_base_dir = "kitchen-vagrant"
275
- # The build is not passing in travis, so no tests
276
- c.smoke_test { sh("gem list kitchen-vagrant") }
277
- end
278
-
279
- add_component "package installation" do |c|
280
-
281
- c.base_dir = "chef-dk"
282
-
283
- c.smoke_test do
284
-
285
- if File.directory?(usr_bin_prefix)
286
- sh!("#{usr_bin_path("berks")} -v")
287
-
288
- sh!("#{usr_bin_path("chef")} -v")
289
-
290
- sh!("#{usr_bin_path("chef-client")} -v")
291
- sh!("#{usr_bin_path("chef-solo")} -v")
292
-
293
- # In `knife`, `knife -v` follows a different code path that skips
294
- # command/plugin loading; `knife -h` loads commands and plugins, but
295
- # it exits with code 1, which is the same as a load error. Running
296
- # `knife exec` forces command loading to happen and this command
297
- # exits 0, which runs most of the code.
298
- #
299
- # See also: https://github.com/opscode/chef-dk/issues/227
300
- sh!("#{usr_bin_path("knife")} exec -E true")
301
-
302
- tmpdir do |dir|
303
- # Kitchen tries to create a .kitchen dir even when just running
304
- # `kitchen -v`:
305
- sh!("#{usr_bin_path("kitchen")} -v", cwd: dir)
306
- end
307
-
308
- sh!("#{usr_bin_path("ohai")} -v")
309
-
310
- sh!("#{usr_bin_path("foodcritic")} -V")
311
- end
312
-
313
- # Test blocks are expected to return a Mixlib::ShellOut compatible
314
- # object:
315
- ComponentTest::NullTestResult.new
316
- end
317
- end
318
-
319
- add_component "openssl" do |c|
320
- # https://github.com/chef/chef-dk/issues/420
321
- c.base_dir = "chef"
322
-
323
- test = <<-EOF.gsub(/^\s+/, "")
324
- require "net/http"
325
-
326
- uris = %w{https://www.google.com https://chef.io/ https://ec2.amazonaws.com}
327
- uris.each do |uri|
328
- uri = URI(uri)
329
- puts "Fetching \#{uri} for SSL check"
330
- Net::HTTP.get uri
331
- end
332
- EOF
333
-
334
- c.unit_test do
335
- tmpdir do |cwd|
336
- with_file(File.join(cwd, "openssl.rb")) do |f|
337
- f.write test
338
- end
339
- sh!("#{Gem.ruby} openssl.rb", cwd: cwd)
340
- end
341
- end
342
- end
343
-
344
- attr_reader :verification_threads
345
- attr_reader :verification_results
346
- attr_reader :verification_status
347
-
348
- def initialize
349
- super
350
- @verification_threads = [ ]
351
- @verification_results = [ ]
352
- @verification_status = 0
353
- end
354
-
355
- def run(params = [ ])
356
- @components_filter = parse_options(params)
357
-
358
- validate_components!
359
- invoke_tests
360
- wait_for_tests
361
- report_results
362
-
363
- verification_status
364
- end
365
-
366
- def omnibus_root
367
- config[:omnibus_dir] || super
368
- end
369
-
370
- def validate_components!
371
- components.each do |component|
372
- component.omnibus_root = omnibus_root
373
- component.assert_present!
374
- end
375
- end
376
-
377
- def components_to_test
378
- if @components_filter.empty?
379
- components
380
- else
381
- components.select do |component|
382
- @components_filter.include?(component.name.to_s)
383
- end
384
- end
385
- end
386
-
387
- def invoke_tests
388
- components_to_test.each do |component|
389
- # Run the component specs in parallel
390
- verification_threads << Thread.new do
391
-
392
- results = []
393
-
394
- results << component.run_smoke_test
395
-
396
- if config[:unit]
397
- results << component.run_unit_test
398
- end
399
-
400
- if config[:integration]
401
- results << component.run_integration_test
402
- end
403
-
404
- if results.any? {|r| r.exitstatus != 0 }
405
- component_status = 1
406
- @verification_status = 1
407
- else
408
- component_status = 0
409
- end
410
-
411
- {
412
- :component => component,
413
- :results => results,
414
- :component_status => component_status
415
- }
416
- end
417
-
418
- msg("Running verification for component '#{component.name}'")
419
- end
420
- end
421
-
422
- def wait_for_tests
423
- while !verification_threads.empty?
424
- verification_threads.each do |t|
425
- if t.join(1)
426
- verification_threads.delete t
427
- verification_results << t.value
428
- t.value[:results].each do |result|
429
- if config[:verbose] || t.value[:component_status] != 0
430
- msg("")
431
- msg(result.stdout)
432
- msg(result.stderr) if result.stderr
433
- end
434
- end
435
- else
436
- $stdout.write "."
437
- end
438
- end
439
- end
440
- end
441
-
442
- def report_results
443
- msg("")
444
- msg("---------------------------------------------")
445
- verification_results.each do |result|
446
- message = result[:component_status] == 0 ? "succeeded" : "failed"
447
- msg("Verification of component '#{result[:component].name}' #{message}.")
448
- end
449
- end
450
-
451
- end
452
- end
453
- end
1
+ #
2
+ # Copyright:: Copyright (c) 2014 Chef Software Inc.
3
+ # License:: Apache License, Version 2.0
4
+ #
5
+ # Licensed under the Apache License, Version 2.0 (the "License");
6
+ # you may not use this file except in compliance with the License.
7
+ # You may obtain a copy of the License at
8
+ #
9
+ # http://www.apache.org/licenses/LICENSE-2.0
10
+ #
11
+ # Unless required by applicable law or agreed to in writing, software
12
+ # distributed under the License is distributed on an "AS IS" BASIS,
13
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14
+ # See the License for the specific language governing permissions and
15
+ # limitations under the License.
16
+ #
17
+
18
+ require 'chef-dk/command/base'
19
+ require 'chef-dk/exceptions'
20
+ require 'chef-dk/component_test'
21
+
22
+ module ChefDK
23
+ module Command
24
+ class Verify < ChefDK::Command::Base
25
+
26
+ include ChefDK::Helpers
27
+
28
+ banner "Usage: chef verify [component, ...] [options]"
29
+
30
+ option :omnibus_dir,
31
+ :long => "--omnibus-dir OMNIBUS_DIR",
32
+ :description => "Alternate path to omnibus install (used for testing)"
33
+
34
+ option :unit,
35
+ :long => "--unit",
36
+ :description => "Run bundled app unit tests (only smoke tests run by default)"
37
+
38
+ option :integration,
39
+ :long => "--integration",
40
+ :description => "Run integration tests. Possibly dangerous, for development systems only"
41
+
42
+ option :verbose,
43
+ :long => "--verbose",
44
+ :description => "Display all test output, not just failing tests"
45
+
46
+ class << self
47
+ def add_component(name, _delete_me=nil)
48
+ component = ComponentTest.new(name)
49
+ yield component if block_given? #delete this conditional
50
+ component_map[name] = component
51
+ end
52
+
53
+ def component(name)
54
+ component_map[name]
55
+ end
56
+
57
+ def components
58
+ component_map.values
59
+ end
60
+
61
+ def component_map
62
+ @component_map ||= {}
63
+ end
64
+ end
65
+
66
+ def components
67
+ self.class.components
68
+ end
69
+
70
+ #
71
+ # Components included in Chef Development kit:
72
+ # :base_dir => Relative path of the component w.r.t. omnibus_apps_dir
73
+ # :test_cmd => Test command to be launched for the component
74
+ #
75
+ add_component "berkshelf" do |c|
76
+ c.base_dir = "berkshelf"
77
+ # For berks the real command to run is "bundle exec thor spec:ci"
78
+ # We can't run it right now since graphviz specs are included in the
79
+ # test suite by default. We will be able to switch to that command when/if
80
+ # Graphviz is added to omnibus.
81
+ c.unit_test { sh("bundle exec rspec --color --format progress spec/unit --tag ~graphviz") }
82
+ c.integration_test { sh("bundle exec cucumber --color --format progress --tags ~@no_run --tags ~@spawn --tags ~@graphviz --strict") }
83
+
84
+ c.smoke_test do
85
+ tmpdir do |cwd|
86
+ FileUtils.touch(File.join(cwd,"Berksfile"))
87
+ sh("berks install", cwd: cwd)
88
+ end
89
+ end
90
+ end
91
+
92
+ add_component "test-kitchen" do |c|
93
+ c.base_dir = "test-kitchen"
94
+ c.unit_test { sh("bundle exec rake unit") }
95
+ c.integration_test { sh("bundle exec rake features") }
96
+
97
+ # NOTE: By default, kitchen tries to be helpful and install a driver
98
+ # gem for you. This causes a race condition when running the tests
99
+ # concurrently, because rubygems breaks when there are partially
100
+ # installed gems in the gem repository. Instructing kitchen to create a
101
+ # gemfile instead avoids the gem installation.
102
+ c.smoke_test { run_in_tmpdir("kitchen init --create-gemfile") }
103
+ end
104
+
105
+ add_component "tk-policyfile-provisioner" do |c|
106
+
107
+ c.base_dir = "chef-dk"
108
+
109
+ c.smoke_test do
110
+ tmpdir do |cwd|
111
+ File.open(File.join(cwd, ".kitchen.yml"), "w+") do |f|
112
+ f.print(<<-KITCHEN_YML)
113
+ ---
114
+ driver:
115
+ name: dummy
116
+ network:
117
+ - ["forwarded_port", {guest: 80, host: 8080}]
118
+
119
+ provisioner:
120
+ name: policyfile_zero
121
+ require_chef_omnibus: 12.3.0
122
+
123
+ platforms:
124
+ - name: ubuntu-14.04
125
+
126
+ suites:
127
+ - name: default
128
+ run_list:
129
+ - recipe[aar::default]
130
+ attributes:
131
+
132
+ KITCHEN_YML
133
+ end
134
+
135
+ sh("kitchen list", cwd: cwd)
136
+
137
+ end
138
+ end
139
+
140
+ end
141
+
142
+ add_component "chef-client" do |c|
143
+ c.base_dir = "chef"
144
+ c.unit_test { sh("bundle exec rspec -fp -t '~volatile_from_verify' spec/unit") }
145
+ c.integration_test { sh("bundle exec rspec -fp spec/integration spec/functional") }
146
+
147
+ c.smoke_test do
148
+ tmpdir do |cwd|
149
+ FileUtils.touch(File.join(cwd, "apply.rb"))
150
+ sh("chef-apply apply.rb", cwd: cwd)
151
+ end
152
+ end
153
+ end
154
+
155
+ add_component "chef-dk" do |c|
156
+ c.base_dir = "chef-dk"
157
+ c.unit_test { sh("bundle exec rspec") }
158
+ c.smoke_test { run_in_tmpdir("chef generate cookbook example") }
159
+ end
160
+
161
+ # entirely possible this needs to be driven by a utility method in chef-provisioning.
162
+ add_component "chef-provisioning" do |c|
163
+ c.base_dir = "chef-dk"
164
+
165
+ c.smoke_test do
166
+ # ------------
167
+ # we want to avoid hard-coding driver names, but calling Gem::Specification produces a warning;
168
+ # changing $VERBOSE seems to be the best way to silence it.
169
+ verbose = $VERBOSE
170
+ $VERBOSE = nil
171
+
172
+ # construct a hash of { driver_name => [version1, version2, ...]}
173
+ driver_versions = {}
174
+ Gem::Specification.all.map { |gs| [gs.name, gs.version] }.
175
+ select { |n| n[0] =~ /^chef-provisioning-/ }.
176
+ each { |gem, version| (driver_versions[gem] ||= []) << version }
177
+
178
+ drivers = Gem::Specification.all.map { |gs| gs.name }.
179
+ select { |n| n =~ /^chef-provisioning-/ }.
180
+ uniq
181
+
182
+ versions = Gem::Specification.find_all_by_name("chef-provisioning").map { |s| s.version }
183
+ $VERBOSE = verbose
184
+ # ------------
185
+ failures = []
186
+
187
+ # ------------
188
+ # fail the verify if we have more than one version of chef-provisioning or any of its drivers.
189
+ def format_gem_failure(name, versions)
190
+ <<-EOS
191
+ #{name} has multiple versions installed:
192
+ #{versions.sort.map { |gv| " #{gv.to_s}" }.join("\n")}
193
+ EOS
194
+ end
195
+
196
+ failures << format_gem_failure("chef-provisioning", versions) if versions.size > 1
197
+
198
+ driver_versions.keys.sort.each do |driver_name|
199
+ v = driver_versions[driver_name]
200
+ failures << format_gem_failure(driver_name, v) if v.size > 1
201
+ end
202
+
203
+ if failures.size > 0
204
+ failures << <<-EOS
205
+
206
+ Some applications may need or prefer different versions of the chef-provisioning gem or its drivers, so
207
+ this multiple-version check can fail if a user has installed new versions of those libraries.
208
+ EOS
209
+ end
210
+
211
+ # ------------
212
+ # load the core gem and all of the drivers (ignoring versions).
213
+ require "chef/provisioning"
214
+ drivers.map { |d| "#{d.gsub('-', '/')}_driver" }.each do |driver_gem|
215
+ begin
216
+ begin
217
+ require driver_gem
218
+ rescue LoadError
219
+ # anomalously, chef-provisioning-fog does not have a fog_driver.rb. (9/2015)
220
+ require "#{driver_gem}/driver.rb"
221
+ end
222
+ rescue LoadError => ex
223
+ puts ex
224
+ end
225
+ end
226
+
227
+ # ------------
228
+ # look for version dependency conflicts.
229
+ tmpdir do |cwd|
230
+ versions.each do |provisioning_version|
231
+ gemfile = "chef-provisioning-#{provisioning_version}-chefdk-test.gemfile"
232
+
233
+ # write out the gemfile for this chef-provisioning version, and see if Bundler can make it go.
234
+ with_file(File.join(cwd, gemfile)) do |f|
235
+ f.puts %Q(gem "chef-provisioning", "= #{provisioning_version}")
236
+ drivers.each { |d| f.puts %Q(gem "#{d}") }
237
+ end
238
+
239
+ result = sh("bundle install --local --quiet", cwd: cwd, env: {"BUNDLE_GEMFILE" => gemfile })
240
+
241
+ if result.exitstatus != 0
242
+ failures << result.stdout
243
+ end
244
+ end # end provisioning versions.
245
+
246
+ failures.each { |fail| puts fail }
247
+
248
+ # dubious on Windows.
249
+ # this is weird, but we seem to require a Mixlib::ShellOut as the return value. suggestions
250
+ # welcome.
251
+ sh(failures.size > 0 ? "false" : "true")
252
+ end
253
+ end
254
+ end
255
+
256
+ add_component "chefspec" do |c|
257
+ c.gem_base_dir = "chefspec"
258
+ c.unit_test { sh("rake unit") }
259
+ c.smoke_test do
260
+ tmpdir do |cwd|
261
+ FileUtils.mkdir(File.join(cwd, "spec"))
262
+ with_file(File.join(cwd, "spec", "spec_helper.rb")) do |f|
263
+ f.write <<-EOF
264
+ require 'chefspec'
265
+ require 'chefspec/berkshelf'
266
+ require 'chefspec/cacher'
267
+
268
+ RSpec.configure do |config|
269
+ config.expect_with(:rspec) { |c| c.syntax = :expect }
270
+ end
271
+ EOF
272
+ end
273
+ FileUtils.touch(File.join(cwd, "Berksfile"))
274
+ with_file(File.join(cwd, "spec", "foo_spec.rb")) do |f|
275
+ f.write <<-EOF
276
+ require 'spec_helper'
277
+ EOF
278
+ end
279
+ sh("rspec", cwd: cwd)
280
+ end
281
+ end
282
+ end
283
+
284
+ add_component "rubocop" do |c|
285
+ c.gem_base_dir = "rubocop"
286
+ c.smoke_test do
287
+ tmpdir do |cwd|
288
+ with_file(File.join(cwd, 'foo.rb')) do |f|
289
+ f.write <<-EOF
290
+ def foo
291
+ puts 'foo'
292
+ end
293
+ EOF
294
+ end
295
+ sh("rubocop foo.rb -l", cwd: cwd)
296
+ end
297
+ end
298
+ end
299
+
300
+ add_component "fauxhai" do |c|
301
+ c.gem_base_dir = "fauxhai"
302
+ c.smoke_test { sh("gem list fauxhai") }
303
+ end
304
+
305
+ add_component "knife-spork" do |c|
306
+ c.gem_base_dir = "knife-spork"
307
+ c.smoke_test { sh('knife spork info')}
308
+ end
309
+
310
+ add_component "kitchen-vagrant" do |c|
311
+ c.gem_base_dir = "kitchen-vagrant"
312
+ # The build is not passing in travis, so no tests
313
+ c.smoke_test { sh("gem list kitchen-vagrant") }
314
+ end
315
+
316
+ add_component "package installation" do |c|
317
+
318
+ c.base_dir = "chef-dk"
319
+
320
+ c.smoke_test do
321
+
322
+ if File.directory?(usr_bin_prefix)
323
+ sh!("#{usr_bin_path("berks")} -v")
324
+
325
+ sh!("#{usr_bin_path("chef")} -v")
326
+
327
+ sh!("#{usr_bin_path("chef-client")} -v")
328
+ sh!("#{usr_bin_path("chef-solo")} -v")
329
+
330
+ # In `knife`, `knife -v` follows a different code path that skips
331
+ # command/plugin loading; `knife -h` loads commands and plugins, but
332
+ # it exits with code 1, which is the same as a load error. Running
333
+ # `knife exec` forces command loading to happen and this command
334
+ # exits 0, which runs most of the code.
335
+ #
336
+ # See also: https://github.com/opscode/chef-dk/issues/227
337
+ sh!("#{usr_bin_path("knife")} exec -E true")
338
+
339
+ tmpdir do |dir|
340
+ # Kitchen tries to create a .kitchen dir even when just running
341
+ # `kitchen -v`:
342
+ sh!("#{usr_bin_path("kitchen")} -v", cwd: dir)
343
+ end
344
+
345
+ sh!("#{usr_bin_path("ohai")} -v")
346
+
347
+ sh!("#{usr_bin_path("foodcritic")} -V")
348
+ end
349
+
350
+ # Test blocks are expected to return a Mixlib::ShellOut compatible
351
+ # object:
352
+ ComponentTest::NullTestResult.new
353
+ end
354
+ end
355
+
356
+ add_component "openssl" do |c|
357
+ # https://github.com/chef/chef-dk/issues/420
358
+ c.base_dir = "chef"
359
+
360
+ test = <<-EOF.gsub(/^\s+/, "")
361
+ require "net/http"
362
+
363
+ uris = %w{https://www.google.com https://chef.io/ https://ec2.amazonaws.com}
364
+ uris.each do |uri|
365
+ uri = URI(uri)
366
+ puts "Fetching \#{uri} for SSL check"
367
+ Net::HTTP.get uri
368
+ end
369
+ EOF
370
+
371
+ c.unit_test do
372
+ tmpdir do |cwd|
373
+ with_file(File.join(cwd, "openssl.rb")) do |f|
374
+ f.write test
375
+ end
376
+ sh!("#{Gem.ruby} openssl.rb", cwd: cwd)
377
+ end
378
+ end
379
+ end
380
+
381
+ attr_reader :verification_threads
382
+ attr_reader :verification_results
383
+ attr_reader :verification_status
384
+
385
+ def initialize
386
+ super
387
+ @verification_threads = [ ]
388
+ @verification_results = [ ]
389
+ @verification_status = 0
390
+ end
391
+
392
+ def run(params = [ ])
393
+ @components_filter = parse_options(params)
394
+
395
+ validate_components!
396
+ invoke_tests
397
+ wait_for_tests
398
+ report_results
399
+
400
+ verification_status
401
+ end
402
+
403
+ def omnibus_root
404
+ config[:omnibus_dir] || super
405
+ end
406
+
407
+ def validate_components!
408
+ components.each do |component|
409
+ component.omnibus_root = omnibus_root
410
+ component.assert_present!
411
+ end
412
+ end
413
+
414
+ def components_to_test
415
+ if @components_filter.empty?
416
+ components
417
+ else
418
+ components.select do |component|
419
+ @components_filter.include?(component.name.to_s)
420
+ end
421
+ end
422
+ end
423
+
424
+ def invoke_tests
425
+ components_to_test.each do |component|
426
+ # Run the component specs in parallel
427
+ verification_threads << Thread.new do
428
+
429
+ results = []
430
+
431
+ results << component.run_smoke_test
432
+
433
+ if config[:unit]
434
+ results << component.run_unit_test
435
+ end
436
+
437
+ if config[:integration]
438
+ results << component.run_integration_test
439
+ end
440
+
441
+ if results.any? {|r| r.exitstatus != 0 }
442
+ component_status = 1
443
+ @verification_status = 1
444
+ else
445
+ component_status = 0
446
+ end
447
+
448
+ {
449
+ :component => component,
450
+ :results => results,
451
+ :component_status => component_status
452
+ }
453
+ end
454
+
455
+ msg("Running verification for component '#{component.name}'")
456
+ end
457
+ end
458
+
459
+ def wait_for_tests
460
+ while !verification_threads.empty?
461
+ verification_threads.each do |t|
462
+ if t.join(1)
463
+ verification_threads.delete t
464
+ verification_results << t.value
465
+ t.value[:results].each do |result|
466
+ if config[:verbose] || t.value[:component_status] != 0
467
+ msg("")
468
+ msg(result.stdout)
469
+ msg(result.stderr) if result.stderr
470
+ end
471
+ end
472
+ else
473
+ $stdout.write "."
474
+ end
475
+ end
476
+ end
477
+ end
478
+
479
+ def report_results
480
+ msg("")
481
+ msg("---------------------------------------------")
482
+ verification_results.each do |result|
483
+ message = result[:component_status] == 0 ? "succeeded" : "failed"
484
+ msg("Verification of component '#{result[:component].name}' #{message}.")
485
+ end
486
+ end
487
+
488
+ end
489
+ end
490
+ end