chef 11.4.4 → 11.6.0.hotfix.1

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 (504) hide show
  1. data/README.md +1 -1
  2. data/Rakefile +18 -1
  3. data/bin/chef-service-manager +37 -0
  4. data/distro/common/html/chef-client.8.html +4 -4
  5. data/distro/common/html/chef-expander.8.html +4 -4
  6. data/distro/common/html/chef-expanderctl.8.html +4 -4
  7. data/distro/common/html/chef-server-webui.8.html +4 -4
  8. data/distro/common/html/chef-server.8.html +4 -4
  9. data/distro/common/html/chef-shell.1.html +4 -4
  10. data/distro/common/html/chef-solo.8.html +12 -18
  11. data/distro/common/html/chef-solr.8.html +4 -4
  12. data/distro/common/html/knife-bootstrap.1.html +4 -4
  13. data/distro/common/html/knife-client.1.html +4 -4
  14. data/distro/common/html/knife-configure.1.html +4 -4
  15. data/distro/common/html/knife-cookbook-site.1.html +4 -4
  16. data/distro/common/html/knife-cookbook.1.html +7 -10
  17. data/distro/common/html/knife-data-bag.1.html +7 -10
  18. data/distro/common/html/knife-environment.1.html +6 -8
  19. data/distro/common/html/knife-exec.1.html +4 -4
  20. data/distro/common/html/knife-index.1.html +4 -4
  21. data/distro/common/html/knife-node.1.html +4 -4
  22. data/distro/common/html/knife-role.1.html +4 -4
  23. data/distro/common/html/knife-search.1.html +4 -4
  24. data/distro/common/html/knife-ssh.1.html +4 -4
  25. data/distro/common/html/knife-status.1.html +4 -4
  26. data/distro/common/html/knife-tag.1.html +4 -4
  27. data/distro/common/html/knife.1.html +4 -4
  28. data/distro/common/man/man1/chef-shell.1 +1 -1
  29. data/distro/common/man/man1/knife-bootstrap.1 +1 -1
  30. data/distro/common/man/man1/knife-client.1 +1 -1
  31. data/distro/common/man/man1/knife-configure.1 +1 -1
  32. data/distro/common/man/man1/knife-cookbook-site.1 +1 -1
  33. data/distro/common/man/man1/knife-cookbook.1 +2 -15
  34. data/distro/common/man/man1/knife-data-bag.1 +2 -15
  35. data/distro/common/man/man1/knife-environment.1 +2 -12
  36. data/distro/common/man/man1/knife-exec.1 +1 -1
  37. data/distro/common/man/man1/knife-index.1 +1 -1
  38. data/distro/common/man/man1/knife-node.1 +1 -1
  39. data/distro/common/man/man1/knife-role.1 +1 -1
  40. data/distro/common/man/man1/knife-search.1 +1 -1
  41. data/distro/common/man/man1/knife-ssh.1 +1 -1
  42. data/distro/common/man/man1/knife-status.1 +1 -1
  43. data/distro/common/man/man1/knife-tag.1 +1 -1
  44. data/distro/common/man/man1/knife.1 +1 -1
  45. data/distro/common/man/man8/chef-client.8 +1 -1
  46. data/distro/common/man/man8/chef-expander.8 +1 -1
  47. data/distro/common/man/man8/chef-expanderctl.8 +1 -1
  48. data/distro/common/man/man8/chef-server-webui.8 +1 -1
  49. data/distro/common/man/man8/chef-server.8 +1 -1
  50. data/distro/common/man/man8/chef-solo.8 +4 -36
  51. data/distro/common/man/man8/chef-solr.8 +1 -1
  52. data/distro/debian/etc/init.d/chef-client +4 -2
  53. data/distro/windows/service_manager.rb +2 -146
  54. data/lib/chef.rb +1 -1
  55. data/lib/chef/application.rb +5 -12
  56. data/lib/chef/application/apply.rb +2 -0
  57. data/lib/chef/application/client.rb +12 -12
  58. data/lib/chef/application/knife.rb +2 -2
  59. data/lib/chef/application/solo.rb +4 -5
  60. data/lib/chef/application/windows_service.rb +113 -56
  61. data/lib/chef/application/windows_service_manager.rb +179 -0
  62. data/lib/chef/chef_fs.rb +2 -4
  63. data/lib/chef/chef_fs/chef_fs_data_store.rb +371 -0
  64. data/lib/chef/chef_fs/command_line.rb +145 -93
  65. data/lib/chef/chef_fs/config.rb +205 -0
  66. data/lib/chef/chef_fs/data_handler/acl_data_handler.rb +26 -0
  67. data/lib/chef/chef_fs/data_handler/client_data_handler.rb +38 -0
  68. data/lib/chef/chef_fs/data_handler/container_data_handler.rb +29 -0
  69. data/lib/chef/chef_fs/data_handler/cookbook_data_handler.rb +38 -0
  70. data/lib/chef/chef_fs/data_handler/data_bag_item_data_handler.rb +56 -0
  71. data/lib/chef/chef_fs/data_handler/data_handler_base.rb +128 -0
  72. data/lib/chef/chef_fs/data_handler/environment_data_handler.rb +40 -0
  73. data/lib/chef/chef_fs/data_handler/group_data_handler.rb +51 -0
  74. data/lib/chef/chef_fs/data_handler/node_data_handler.rb +36 -0
  75. data/lib/chef/chef_fs/data_handler/role_data_handler.rb +40 -0
  76. data/lib/chef/chef_fs/data_handler/user_data_handler.rb +27 -0
  77. data/lib/chef/chef_fs/file_system.rb +195 -127
  78. data/lib/chef/chef_fs/file_system/acl_dir.rb +64 -0
  79. data/lib/chef/chef_fs/file_system/acl_entry.rb +58 -0
  80. data/lib/chef/chef_fs/file_system/acls_dir.rb +68 -0
  81. data/lib/chef/chef_fs/file_system/already_exists_error.rb +31 -0
  82. data/lib/chef/chef_fs/file_system/base_fs_object.rb +98 -39
  83. data/lib/chef/chef_fs/file_system/chef_repository_file_system_cookbook_dir.rb +85 -0
  84. data/lib/chef/chef_fs/file_system/chef_repository_file_system_cookbook_entry.rb +71 -0
  85. data/lib/chef/chef_fs/file_system/chef_repository_file_system_cookbooks_dir.rb +55 -0
  86. data/lib/chef/chef_fs/file_system/chef_repository_file_system_data_bags_dir.rb +36 -0
  87. data/lib/chef/chef_fs/file_system/chef_repository_file_system_entry.rb +14 -63
  88. data/lib/chef/chef_fs/file_system/chef_repository_file_system_root_dir.rb +93 -3
  89. data/lib/chef/chef_fs/file_system/chef_server_root_dir.rb +35 -9
  90. data/lib/chef/chef_fs/file_system/cookbook_dir.rb +67 -32
  91. data/lib/chef/chef_fs/file_system/cookbook_file.rb +13 -6
  92. data/lib/chef/chef_fs/file_system/cookbook_frozen_error.rb +31 -0
  93. data/lib/chef/chef_fs/file_system/cookbooks_acl_dir.rb +41 -0
  94. data/lib/chef/chef_fs/file_system/cookbooks_dir.rb +102 -21
  95. data/lib/chef/chef_fs/file_system/data_bag_dir.rb +12 -21
  96. data/lib/chef/chef_fs/file_system/data_bags_dir.rb +14 -8
  97. data/lib/chef/chef_fs/file_system/default_environment_cannot_be_modified_error.rb +36 -0
  98. data/lib/chef/chef_fs/file_system/environments_dir.rb +60 -0
  99. data/lib/chef/chef_fs/file_system/file_system_entry.rb +8 -8
  100. data/lib/chef/chef_fs/file_system/file_system_error.rb +3 -1
  101. data/lib/chef/chef_fs/file_system/memory_dir.rb +52 -0
  102. data/lib/chef/chef_fs/file_system/memory_file.rb +17 -0
  103. data/lib/chef/chef_fs/file_system/memory_root.rb +21 -0
  104. data/lib/chef/chef_fs/file_system/multiplexed_dir.rb +48 -0
  105. data/lib/chef/chef_fs/file_system/must_delete_recursively_error.rb +2 -2
  106. data/lib/chef/chef_fs/file_system/nodes_dir.rb +17 -9
  107. data/lib/chef/chef_fs/file_system/nonexistent_fs_object.rb +0 -4
  108. data/lib/chef/chef_fs/file_system/not_found_error.rb +2 -2
  109. data/lib/chef/chef_fs/file_system/operation_failed_error.rb +34 -0
  110. data/lib/chef/chef_fs/file_system/operation_not_allowed_error.rb +48 -0
  111. data/lib/chef/chef_fs/file_system/rest_list_dir.rb +42 -13
  112. data/lib/chef/chef_fs/file_system/rest_list_entry.rb +81 -27
  113. data/lib/chef/chef_fs/knife.rb +68 -29
  114. data/lib/chef/chef_fs/parallelizer.rb +129 -0
  115. data/lib/chef/chef_fs/path_utils.rb +29 -3
  116. data/lib/chef/chef_fs/raw_request.rb +79 -0
  117. data/lib/chef/client.rb +46 -20
  118. data/lib/chef/config.rb +59 -61
  119. data/lib/chef/cookbook/chefignore.rb +2 -1
  120. data/lib/chef/cookbook/synchronizer.rb +8 -6
  121. data/lib/chef/cookbook/syntax_check.rb +17 -2
  122. data/lib/chef/cookbook_uploader.rb +10 -1
  123. data/lib/chef/cookbook_version.rb +0 -109
  124. data/lib/chef/data_bag.rb +15 -6
  125. data/lib/chef/deprecation/mixin/template.rb +49 -0
  126. data/lib/chef/deprecation/provider/cookbook_file.rb +55 -0
  127. data/lib/chef/deprecation/provider/file.rb +197 -0
  128. data/lib/chef/deprecation/provider/remote_file.rb +86 -0
  129. data/lib/chef/deprecation/provider/template.rb +63 -0
  130. data/lib/chef/deprecation/warnings.rb +38 -0
  131. data/lib/chef/encrypted_data_bag_item.rb +153 -61
  132. data/lib/chef/environment.rb +34 -3
  133. data/lib/chef/event_dispatch/base.rb +3 -0
  134. data/lib/chef/exceptions.rb +27 -2
  135. data/lib/chef/file_access_control/unix.rb +64 -7
  136. data/lib/chef/file_access_control/windows.rb +22 -11
  137. data/lib/chef/file_content_management/content_base.rb +56 -0
  138. data/lib/chef/file_content_management/deploy.rb +38 -0
  139. data/lib/chef/file_content_management/deploy/cp.rb +48 -0
  140. data/lib/chef/file_content_management/deploy/mv_unix.rb +77 -0
  141. data/lib/chef/file_content_management/deploy/mv_windows.rb +95 -0
  142. data/lib/chef/file_content_management/tempfile.rb +61 -0
  143. data/lib/chef/formatters/doc.rb +1 -1
  144. data/lib/chef/formatters/error_descriptor.rb +5 -4
  145. data/lib/chef/formatters/error_inspectors/cookbook_resolve_error_inspector.rb +23 -3
  146. data/lib/chef/formatters/error_inspectors/registration_error_inspector.rb +4 -0
  147. data/lib/chef/json_compat.rb +3 -0
  148. data/lib/chef/knife.rb +12 -3
  149. data/lib/chef/knife/bootstrap.rb +46 -2
  150. data/lib/chef/knife/bootstrap/archlinux-gems.erb +3 -3
  151. data/lib/chef/knife/bootstrap/centos5-gems.erb +3 -3
  152. data/lib/chef/knife/bootstrap/chef-full.erb +4 -4
  153. data/lib/chef/knife/bootstrap/fedora13-gems.erb +3 -3
  154. data/lib/chef/knife/bootstrap/ubuntu10.04-apt.erb +3 -3
  155. data/lib/chef/knife/bootstrap/ubuntu10.04-gems.erb +3 -3
  156. data/lib/chef/knife/bootstrap/ubuntu12.04-gems.erb +3 -3
  157. data/lib/chef/knife/client_show.rb +2 -5
  158. data/lib/chef/knife/configure.rb +3 -3
  159. data/lib/chef/knife/cookbook_create.rb +6 -5
  160. data/lib/chef/knife/cookbook_download.rb +13 -5
  161. data/lib/chef/knife/cookbook_site_share.rb +1 -0
  162. data/lib/chef/knife/cookbook_test.rb +1 -0
  163. data/lib/chef/knife/cookbook_upload.rb +4 -9
  164. data/lib/chef/knife/core/bootstrap_context.rb +10 -4
  165. data/lib/chef/knife/core/generic_presenter.rb +16 -0
  166. data/lib/chef/knife/core/node_editor.rb +1 -1
  167. data/lib/chef/knife/core/subcommand_loader.rb +43 -12
  168. data/lib/chef/knife/core/ui.rb +19 -4
  169. data/lib/chef/knife/delete.rb +76 -9
  170. data/lib/chef/knife/deps.rb +139 -0
  171. data/lib/chef/knife/diff.rb +22 -5
  172. data/lib/chef/knife/download.rb +16 -3
  173. data/lib/chef/knife/edit.rb +76 -0
  174. data/lib/chef/knife/environment_show.rb +2 -7
  175. data/lib/chef/knife/list.rb +91 -47
  176. data/lib/chef/knife/node_run_list_set.rb +66 -0
  177. data/lib/chef/knife/node_show.rb +1 -7
  178. data/lib/chef/knife/raw.rb +20 -64
  179. data/lib/chef/knife/role_show.rb +2 -4
  180. data/lib/chef/knife/search.rb +5 -6
  181. data/lib/chef/knife/show.rb +34 -11
  182. data/lib/chef/knife/ssh.rb +8 -0
  183. data/lib/chef/knife/upload.rb +23 -4
  184. data/lib/chef/knife/user_show.rb +2 -5
  185. data/lib/chef/knife/xargs.rb +265 -0
  186. data/lib/chef/log.rb +2 -2
  187. data/lib/chef/mixin/file_class.rb +0 -9
  188. data/lib/chef/mixin/language_include_recipe.rb +1 -1
  189. data/lib/chef/mixin/params_validate.rb +19 -9
  190. data/lib/chef/mixin/template.rb +126 -36
  191. data/lib/chef/mixin/windows_architecture_helper.rb +91 -0
  192. data/lib/chef/monkey_patches/file.rb +26 -0
  193. data/lib/chef/monkey_patches/net-ssh-multi.rb +140 -0
  194. data/lib/chef/monkey_patches/securerandom.rb +44 -0
  195. data/lib/chef/monologger.rb +93 -0
  196. data/lib/chef/node.rb +4 -0
  197. data/lib/chef/platform.rb +4 -490
  198. data/lib/chef/platform/provider_mapping.rb +529 -0
  199. data/lib/chef/{monkey_patches/dir.rb → platform/query_helpers.rb} +25 -19
  200. data/lib/chef/provider.rb +12 -9
  201. data/lib/chef/provider/batch.rb +35 -0
  202. data/lib/chef/provider/cookbook_file.rb +9 -78
  203. data/lib/chef/provider/cookbook_file/content.rb +49 -0
  204. data/lib/chef/provider/deploy.rb +24 -20
  205. data/lib/chef/provider/deploy/revision.rb +27 -0
  206. data/lib/chef/provider/directory.rb +19 -22
  207. data/lib/chef/provider/execute.rb +22 -5
  208. data/lib/chef/provider/file.rb +299 -217
  209. data/lib/chef/provider/file/content.rb +39 -0
  210. data/lib/chef/provider/git.rb +76 -43
  211. data/lib/chef/provider/group/usermod.rb +2 -2
  212. data/lib/chef/provider/ifconfig.rb +25 -35
  213. data/lib/chef/provider/ifconfig/debian.rb +71 -0
  214. data/lib/chef/provider/ifconfig/redhat.rb +47 -0
  215. data/lib/chef/provider/link.rb +10 -3
  216. data/lib/chef/provider/mount.rb +1 -1
  217. data/lib/chef/provider/mount/mount.rb +8 -3
  218. data/lib/chef/provider/mount/windows.rb +4 -1
  219. data/lib/chef/provider/package/portage.rb +9 -4
  220. data/lib/chef/provider/package/rubygems.rb +45 -10
  221. data/lib/chef/provider/package/smartos.rb +47 -36
  222. data/lib/chef/provider/package/yum.rb +19 -12
  223. data/lib/chef/provider/package/zypper.rb +45 -55
  224. data/lib/chef/provider/powershell_script.rb +77 -0
  225. data/lib/chef/provider/remote_directory.rb +5 -6
  226. data/lib/chef/provider/remote_file.rb +12 -108
  227. data/lib/chef/provider/remote_file/cache_control_data.rb +165 -0
  228. data/lib/chef/provider/remote_file/content.rb +75 -0
  229. data/lib/chef/provider/remote_file/fetcher.rb +43 -0
  230. data/lib/chef/provider/remote_file/ftp.rb +183 -0
  231. data/lib/chef/provider/remote_file/http.rb +124 -0
  232. data/lib/chef/provider/remote_file/local_file.rb +47 -0
  233. data/lib/chef/provider/route.rb +6 -2
  234. data/lib/chef/provider/script.rb +14 -2
  235. data/lib/chef/provider/service/macosx.rb +16 -10
  236. data/lib/chef/provider/service/solaris.rb +6 -5
  237. data/lib/chef/provider/template.rb +16 -78
  238. data/lib/chef/provider/template/content.rb +61 -0
  239. data/lib/chef/provider/user/solaris.rb +90 -0
  240. data/lib/chef/provider/user/useradd.rb +76 -63
  241. data/lib/chef/provider/windows_script.rb +73 -0
  242. data/lib/chef/providers.rb +16 -0
  243. data/lib/chef/resource.rb +23 -2
  244. data/lib/chef/resource/batch.rb +31 -0
  245. data/lib/chef/resource/conditional.rb +4 -0
  246. data/lib/chef/resource/conditional_action_not_nothing.rb +48 -0
  247. data/lib/chef/resource/file.rb +31 -3
  248. data/lib/chef/resource/link.rb +17 -0
  249. data/lib/chef/resource/lwrp_base.rb +1 -1
  250. data/lib/chef/resource/mount.rb +29 -2
  251. data/lib/chef/resource/powershell_script.rb +31 -0
  252. data/lib/chef/resource/remote_file.rb +47 -1
  253. data/lib/chef/resource/route.rb +1 -1
  254. data/lib/chef/resource/template.rb +145 -0
  255. data/lib/chef/resource/windows_script.rb +62 -0
  256. data/lib/chef/resource_collection.rb +45 -11
  257. data/lib/chef/resource_reporter.rb +81 -52
  258. data/lib/chef/resources.rb +2 -0
  259. data/lib/chef/rest.rb +13 -4
  260. data/lib/chef/rest/rest_request.rb +5 -1
  261. data/lib/chef/run_context/cookbook_compiler.rb +3 -3
  262. data/lib/chef/run_list/run_list_expansion.rb +1 -1
  263. data/lib/chef/run_lock.rb +7 -1
  264. data/lib/chef/runner.rb +0 -1
  265. data/lib/chef/scan_access_control.rb +6 -1
  266. data/lib/chef/search/query.rb +2 -2
  267. data/lib/chef/shell/shell_session.rb +2 -2
  268. data/lib/chef/util/backup.rb +84 -0
  269. data/lib/chef/util/diff.rb +145 -0
  270. data/lib/chef/util/file_edit.rb +1 -1
  271. data/lib/chef/util/selinux.rb +100 -0
  272. data/lib/chef/util/windows/net_user.rb +14 -1
  273. data/lib/chef/util/windows/volume.rb +2 -2
  274. data/lib/chef/version.rb +1 -1
  275. data/lib/chef/version/platform.rb +42 -0
  276. data/lib/chef/version_class.rb +1 -1
  277. data/lib/chef/version_constraint.rb +6 -5
  278. data/lib/chef/version_constraint/platform.rb +26 -0
  279. data/lib/chef/win32/api/file.rb +8 -2
  280. data/lib/chef/win32/version.rb +25 -8
  281. data/spec/data/apt/chef-integration-test-1.0/debian/changelog +5 -0
  282. data/spec/data/apt/chef-integration-test-1.0/debian/compat +1 -0
  283. data/spec/data/apt/chef-integration-test-1.0/debian/control +13 -0
  284. data/spec/data/apt/chef-integration-test-1.0/debian/copyright +34 -0
  285. data/spec/data/apt/chef-integration-test-1.0/debian/files +1 -0
  286. data/spec/data/apt/chef-integration-test-1.0/debian/rules +13 -0
  287. data/spec/data/apt/chef-integration-test-1.0/debian/source/format +1 -0
  288. data/spec/data/apt/chef-integration-test-1.1/debian/changelog +11 -0
  289. data/spec/data/apt/chef-integration-test-1.1/debian/compat +1 -0
  290. data/spec/data/apt/chef-integration-test-1.1/debian/control +13 -0
  291. data/spec/data/apt/chef-integration-test-1.1/debian/copyright +34 -0
  292. data/spec/data/apt/chef-integration-test-1.1/debian/files +1 -0
  293. data/spec/data/apt/chef-integration-test-1.1/debian/rules +13 -0
  294. data/spec/data/apt/chef-integration-test-1.1/debian/source/format +1 -0
  295. data/spec/data/apt/chef-integration-test_1.0-1_amd64.changes +22 -0
  296. data/spec/data/apt/chef-integration-test_1.0-1_amd64.deb +0 -0
  297. data/spec/data/apt/chef-integration-test_1.0.orig.tar.gz +0 -0
  298. data/spec/data/apt/chef-integration-test_1.1-1_amd64.changes +22 -0
  299. data/spec/data/apt/chef-integration-test_1.1-1_amd64.deb +0 -0
  300. data/spec/data/apt/chef-integration-test_1.1.orig.tar.gz +0 -0
  301. data/spec/data/apt/var/www/apt/conf/distributions +7 -0
  302. data/spec/data/apt/var/www/apt/conf/incoming +4 -0
  303. data/spec/data/apt/var/www/apt/conf/pulls +3 -0
  304. data/spec/data/apt/var/www/apt/db/checksums.db +0 -0
  305. data/spec/data/apt/var/www/apt/db/contents.cache.db +0 -0
  306. data/spec/data/apt/var/www/apt/db/packages.db +0 -0
  307. data/spec/data/apt/var/www/apt/db/references.db +0 -0
  308. data/spec/data/apt/var/www/apt/db/release.caches.db +0 -0
  309. data/spec/data/apt/var/www/apt/db/version +4 -0
  310. data/spec/data/apt/var/www/apt/dists/sid/Release +19 -0
  311. data/spec/data/apt/var/www/apt/dists/sid/main/binary-amd64/Packages +16 -0
  312. data/spec/data/apt/var/www/apt/dists/sid/main/binary-amd64/Packages.gz +0 -0
  313. data/spec/data/apt/var/www/apt/dists/sid/main/binary-amd64/Release +5 -0
  314. data/spec/data/apt/var/www/apt/dists/sid/main/binary-i386/Packages +0 -0
  315. data/spec/data/apt/var/www/apt/pool/main/c/chef-integration-test/chef-integration-test_1.0-1_amd64.deb +0 -0
  316. data/spec/data/apt/var/www/apt/pool/main/c/chef-integration-test/chef-integration-test_1.1-1_amd64.deb +0 -0
  317. data/spec/data/bootstrap/encrypted_data_bag_secret +1 -0
  318. data/spec/data/bootstrap/secret.erb +9 -0
  319. data/spec/data/cookbooks/ignorken/recipes/default.rb +1 -0
  320. data/spec/data/cookbooks/ignorken/recipes/ignoreme.rb +2 -0
  321. data/spec/data/cookbooks/openldap/files/default/.dotfile +1 -0
  322. data/spec/data/cookbooks/openldap/files/default/.ssh/id_rsa +1 -0
  323. data/spec/data/cookbooks/openldap/files/default/remotedir/.a_dotdir/.a_dotfile_in_a_dotdir +1 -0
  324. data/spec/data/cookbooks/openldap/files/default/remotedir/remotesubdir/.a_dotfile +1 -0
  325. data/spec/data/cookbooks/openldap/templates/default/all_windows_line_endings.erb +4 -0
  326. data/spec/data/cookbooks/openldap/templates/default/helper_test.erb +1 -0
  327. data/spec/data/cookbooks/openldap/templates/default/helpers_via_partial_test.erb +1 -0
  328. data/spec/data/cookbooks/openldap/templates/default/no_windows_line_endings.erb +4 -0
  329. data/spec/data/cookbooks/openldap/templates/default/some_windows_line_endings.erb +4 -0
  330. data/spec/data/cookbooks/preseed/files/default/preseed-file.seed +1 -0
  331. data/spec/data/cookbooks/preseed/templates/default/preseed-template.seed +1 -0
  332. data/spec/data/file-providers-method-snapshot-chef-11-4.json +127 -0
  333. data/spec/data/git_bundles/example-repo.gitbundle +0 -0
  334. data/spec/data/knife-home/.chef/plugins/knife/example_home_subcommand.rb +0 -0
  335. data/spec/data/knife_subcommand/test_yourself.rb +8 -0
  336. data/spec/data/null_config.rb +1 -0
  337. data/spec/data/partial_one.erb +1 -1
  338. data/spec/data/remote_file/nyan_cat.png.gz +0 -0
  339. data/spec/functional/file_content_management/deploy_strategies_spec.rb +238 -0
  340. data/spec/functional/knife/exec_spec.rb +2 -2
  341. data/spec/functional/provider/remote_file/cache_control_data_spec.rb +101 -0
  342. data/spec/functional/resource/batch_spec.rb +64 -0
  343. data/spec/functional/resource/cookbook_file_spec.rb +2 -3
  344. data/spec/functional/resource/deploy_revision_spec.rb +180 -0
  345. data/spec/functional/resource/directory_spec.rb +2 -2
  346. data/spec/functional/resource/file_spec.rb +17 -1
  347. data/spec/functional/resource/git_spec.rb +259 -0
  348. data/spec/functional/resource/link_spec.rb +422 -388
  349. data/spec/functional/resource/package_spec.rb +297 -0
  350. data/spec/functional/resource/powershell_spec.rb +188 -0
  351. data/spec/functional/resource/registry_spec.rb +8 -4
  352. data/spec/functional/resource/remote_directory_spec.rb +2 -2
  353. data/spec/functional/resource/remote_file_spec.rb +97 -29
  354. data/spec/functional/resource/template_spec.rb +173 -17
  355. data/spec/functional/resource/user_spec.rb +547 -0
  356. data/spec/functional/run_lock_spec.rb +5 -0
  357. data/spec/functional/shell_spec.rb +2 -1
  358. data/spec/functional/win32/service_manager_spec.rb +269 -0
  359. data/spec/functional/win32/versions_spec.rb +78 -0
  360. data/spec/integration/knife/chef_repo_path_spec.rb +805 -0
  361. data/spec/integration/knife/chef_repository_file_system_spec.rb +276 -0
  362. data/spec/integration/knife/chefignore_spec.rb +271 -0
  363. data/spec/integration/knife/delete_spec.rb +944 -0
  364. data/spec/integration/knife/deps_spec.rb +648 -0
  365. data/spec/integration/knife/diff_spec.rb +536 -0
  366. data/spec/integration/knife/download_spec.rb +962 -0
  367. data/spec/integration/knife/list_spec.rb +633 -0
  368. data/spec/integration/knife/raw_spec.rb +166 -0
  369. data/spec/integration/knife/redirection_spec.rb +57 -0
  370. data/spec/integration/knife/show_spec.rb +158 -0
  371. data/spec/integration/knife/upload_spec.rb +1060 -0
  372. data/spec/integration/solo/solo_spec.rb +41 -0
  373. data/spec/spec_helper.rb +55 -1
  374. data/spec/support/chef_helpers.rb +32 -0
  375. data/spec/support/platform_helpers.rb +40 -0
  376. data/spec/support/platforms/win32/spec_service.rb +59 -0
  377. data/spec/support/shared/functional/directory_resource.rb +43 -16
  378. data/spec/support/shared/functional/file_resource.rb +661 -20
  379. data/spec/support/shared/functional/securable_resource.rb +109 -8
  380. data/spec/support/shared/functional/securable_resource_with_reporting.rb +39 -31
  381. data/spec/support/shared/integration/integration_helper.rb +166 -0
  382. data/spec/support/shared/integration/knife_support.rb +171 -0
  383. data/spec/support/shared/unit/execute_resource.rb +125 -0
  384. data/spec/support/shared/unit/file_system_support.rb +8 -48
  385. data/spec/support/shared/unit/provider/file.rb +609 -0
  386. data/spec/support/shared/unit/provider/useradd_based_user_provider.rb +407 -0
  387. data/spec/support/shared/unit/script_resource.rb +52 -0
  388. data/spec/support/shared/unit/windows_script_resource.rb +48 -0
  389. data/spec/tiny_server.rb +13 -11
  390. data/spec/unit/application/client_spec.rb +39 -1
  391. data/spec/unit/application/knife_spec.rb +12 -0
  392. data/spec/unit/application/solo_spec.rb +1 -1
  393. data/spec/unit/application_spec.rb +57 -2
  394. data/spec/unit/chef_fs/diff_spec.rb +30 -31
  395. data/spec/unit/chef_fs/file_pattern_spec.rb +2 -2
  396. data/spec/unit/chef_fs/file_system_spec.rb +2 -3
  397. data/spec/unit/client_spec.rb +20 -1
  398. data/spec/unit/config_spec.rb +70 -52
  399. data/spec/unit/cookbook/synchronizer_spec.rb +49 -1
  400. data/spec/unit/cookbook/syntax_check_spec.rb +28 -3
  401. data/spec/unit/cookbook_loader_spec.rb +3 -2
  402. data/spec/unit/daemon_spec.rb +7 -7
  403. data/spec/unit/data_bag_spec.rb +7 -0
  404. data/spec/unit/deprecation_spec.rb +86 -0
  405. data/spec/unit/encrypted_data_bag_item_spec.rb +183 -88
  406. data/spec/unit/environment_spec.rb +98 -0
  407. data/spec/unit/exceptions_spec.rb +6 -1
  408. data/spec/unit/file_access_control_spec.rb +21 -1
  409. data/spec/unit/file_content_management/deploy/cp_spec.rb +46 -0
  410. data/spec/unit/file_content_management/deploy/mv_unix_spec.rb +103 -0
  411. data/spec/unit/file_content_management/deploy/mv_windows_spec.rb +179 -0
  412. data/spec/unit/formatters/error_inspectors/cookbook_resolve_error_inspector_spec.rb +38 -2
  413. data/spec/unit/formatters/error_inspectors/resource_failure_inspector_spec.rb +3 -2
  414. data/spec/unit/knife/bootstrap_spec.rb +128 -29
  415. data/spec/unit/knife/configure_spec.rb +42 -26
  416. data/spec/unit/knife/cookbook_download_spec.rb +24 -3
  417. data/spec/unit/knife/cookbook_upload_spec.rb +8 -4
  418. data/spec/unit/knife/core/bootstrap_context_spec.rb +78 -61
  419. data/spec/unit/knife/core/subcommand_loader_spec.rb +20 -0
  420. data/spec/unit/knife/core/ui_spec.rb +41 -0
  421. data/spec/unit/knife/node_run_list_set_spec.rb +140 -0
  422. data/spec/unit/knife_spec.rb +21 -0
  423. data/spec/unit/mixin/enforce_ownership_and_permissions_spec.rb +1 -0
  424. data/spec/unit/mixin/params_validate_spec.rb +35 -0
  425. data/spec/unit/mixin/template_spec.rb +69 -57
  426. data/spec/unit/mixin/windows_architecture_helper_spec.rb +83 -0
  427. data/spec/unit/node_spec.rb +7 -0
  428. data/spec/unit/platform_spec.rb +15 -1
  429. data/spec/unit/provider/cookbook_file/content_spec.rb +40 -0
  430. data/spec/unit/provider/cookbook_file_spec.rb +26 -183
  431. data/spec/unit/provider/cron/solaris_spec.rb +1 -1
  432. data/spec/unit/provider/deploy/revision_spec.rb +19 -11
  433. data/spec/unit/provider/deploy_spec.rb +2 -2
  434. data/spec/unit/provider/directory_spec.rb +23 -23
  435. data/spec/unit/provider/execute_spec.rb +27 -1
  436. data/spec/unit/provider/file/content_spec.rb +101 -0
  437. data/spec/unit/provider/file_spec.rb +25 -484
  438. data/spec/unit/provider/git_spec.rb +224 -28
  439. data/spec/unit/provider/group/usermod_spec.rb +3 -1
  440. data/spec/unit/provider/ifconfig/debian_spec.rb +89 -0
  441. data/spec/unit/provider/ifconfig/redhat_spec.rb +71 -0
  442. data/spec/unit/provider/ifconfig_spec.rb +0 -33
  443. data/spec/unit/provider/mount/mount_spec.rb +33 -2
  444. data/spec/unit/provider/mount/windows_spec.rb +4 -1
  445. data/spec/unit/provider/mount_spec.rb +16 -6
  446. data/spec/unit/provider/package/portage_spec.rb +44 -0
  447. data/spec/unit/provider/package/rubygems_spec.rb +44 -1
  448. data/spec/unit/provider/package/smartos_spec.rb +3 -2
  449. data/spec/unit/provider/package/yum_spec.rb +36 -39
  450. data/spec/unit/provider/package/zypper_spec.rb +84 -22
  451. data/spec/unit/provider/package_spec.rb +0 -4
  452. data/spec/unit/provider/powershell_spec.rb +38 -0
  453. data/spec/unit/provider/remote_directory_spec.rb +0 -4
  454. data/spec/unit/provider/remote_file/cache_control_data_spec.rb +211 -0
  455. data/spec/unit/provider/remote_file/content_spec.rb +230 -0
  456. data/spec/unit/provider/remote_file/fetcher_spec.rb +75 -0
  457. data/spec/unit/provider/remote_file/ftp_spec.rb +224 -0
  458. data/spec/unit/provider/remote_file/http_spec.rb +319 -0
  459. data/spec/unit/provider/remote_file/local_file_spec.rb +60 -0
  460. data/spec/unit/provider/remote_file_spec.rb +33 -295
  461. data/spec/unit/provider/route_spec.rb +25 -9
  462. data/spec/unit/provider/service/macosx_spec.rb +176 -152
  463. data/spec/unit/provider/service/solaris_smf_service_spec.rb +21 -18
  464. data/spec/unit/provider/service/systemd_service_spec.rb +2 -2
  465. data/spec/unit/provider/service/upstart_service_spec.rb +2 -2
  466. data/spec/unit/provider/service_spec.rb +3 -3
  467. data/spec/unit/provider/template/content_spec.rb +78 -0
  468. data/spec/unit/provider/template_spec.rb +52 -184
  469. data/spec/unit/provider/user/solaris_spec.rb +80 -0
  470. data/spec/unit/provider/user/useradd_spec.rb +12 -358
  471. data/spec/unit/resource/batch_spec.rb +48 -0
  472. data/spec/unit/resource/conditional_action_not_nothing_spec.rb +45 -0
  473. data/spec/unit/resource/execute_spec.rb +3 -101
  474. data/spec/unit/resource/file_spec.rb +0 -5
  475. data/spec/unit/resource/group_spec.rb +9 -0
  476. data/spec/unit/resource/ifconfig_spec.rb +60 -1
  477. data/spec/unit/resource/link_spec.rb +1 -0
  478. data/spec/unit/resource/mount_spec.rb +37 -0
  479. data/spec/unit/resource/powershell_spec.rb +48 -0
  480. data/spec/unit/resource/remote_file_spec.rb +44 -4
  481. data/spec/unit/resource/route_spec.rb +1 -1
  482. data/spec/unit/resource/script_spec.rb +13 -36
  483. data/spec/unit/resource/template_spec.rb +111 -8
  484. data/spec/unit/resource/user_spec.rb +7 -0
  485. data/spec/unit/resource_collection_spec.rb +61 -32
  486. data/spec/unit/resource_reporter_spec.rb +115 -102
  487. data/spec/unit/resource_spec.rb +170 -1
  488. data/spec/unit/rest/auth_credentials_spec.rb +2 -2
  489. data/spec/unit/rest_spec.rb +6 -2
  490. data/spec/unit/run_context/cookbook_compiler_spec.rb +9 -0
  491. data/spec/unit/runner_spec.rb +1 -1
  492. data/spec/unit/scan_access_control_spec.rb +4 -2
  493. data/spec/unit/shell/shell_session_spec.rb +15 -2
  494. data/spec/unit/util/backup_spec.rb +149 -0
  495. data/spec/unit/util/diff_spec.rb +596 -0
  496. data/spec/unit/util/selinux_spec.rb +172 -0
  497. data/spec/unit/version/platform_spec.rb +61 -0
  498. data/spec/unit/version_constraint/platform_spec.rb +46 -0
  499. data/spec/unit/version_constraint_spec.rb +5 -0
  500. metadata +233 -10
  501. data/lib/chef/chef_fs/file_system/data_bag_item.rb +0 -59
  502. data/spec/unit/chef_fs/file_system/chef_server_root_dir_spec.rb +0 -237
  503. data/spec/unit/chef_fs/file_system/cookbooks_dir_spec.rb +0 -568
  504. data/spec/unit/chef_fs/file_system/data_bags_dir_spec.rb +0 -220
@@ -112,14 +112,18 @@ describe Chef::Resource::RegistryKey, :windows_only do
112
112
  #Reporting setup
113
113
  before do
114
114
  @node.name("windowsbox")
115
+
115
116
  @rest_client = mock("Chef::REST (mock)")
116
- @rest_client.stub!(:create_url).and_return("reports/nodes/windowsbox/runs/ABC123");
117
+ @rest_client.stub!(:create_url).and_return("reports/nodes/windowsbox/runs/#{@run_id}");
117
118
  @rest_client.stub!(:raw_http_request).and_return({"result"=>"ok"});
118
- @rest_client.stub!(:post_rest).and_return({"uri"=>"https://example.com/reports/nodes/windowsbox/runs/ABC123"});
119
+ @rest_client.stub!(:post_rest).and_return({"uri"=>"https://example.com/reports/nodes/windowsbox/runs/#{@run_id}"});
119
120
 
120
121
  @resource_reporter = Chef::ResourceReporter.new(@rest_client)
121
122
  @events.register(@resource_reporter)
122
- @resource_reporter.node_load_completed(@node, :expanded_run_list, :config)
123
+ @run_id = @resource_reporter.run_id
124
+ @run_status = Chef::RunStatus.new(@node, @events)
125
+
126
+ @resource_reporter.run_started(@run_status)
123
127
 
124
128
  @new_resource.cookbook_name = "monkey"
125
129
  @cookbook_version = mock("Cookbook::Version", :version => "1.2.3")
@@ -537,7 +541,7 @@ describe Chef::Resource::RegistryKey, :windows_only do
537
541
  @report["resources"][0]["type"].should == "registry_key"
538
542
  @report["resources"][0]["name"].should == resource_name
539
543
  @report["resources"][0]["id"].should == reg_parent + '\ReportKey'
540
- #Not testing for before or after values to match since
544
+ #Not testing for before or after values to match since
541
545
  #after -> new_resource.values and
542
546
  #before -> current_resource.values
543
547
  @report["resources"][0]["result"].should == "delete_key"
@@ -22,7 +22,7 @@ describe Chef::Resource::RemoteDirectory do
22
22
  include_context Chef::Resource::Directory
23
23
 
24
24
  let(:directory_base) { "directory_spec" }
25
- let(:default_mode) { "755" }
25
+ let(:default_mode) { ((0100777 - File.umask) & 07777).to_s(8) }
26
26
 
27
27
  def create_resource
28
28
  cookbook_repo = File.expand_path(File.join(CHEF_SPEC_DATA, "cookbooks"))
@@ -48,7 +48,7 @@ describe Chef::Resource::RemoteDirectory do
48
48
  FileUtils.touch(@existing2)
49
49
  end
50
50
 
51
- let!(:resource) do
51
+ let(:resource) do
52
52
  create_resource
53
53
  end
54
54
 
@@ -20,17 +20,22 @@ require 'spec_helper'
20
20
  require 'tiny_server'
21
21
 
22
22
  describe Chef::Resource::RemoteFile do
23
+
24
+ let(:file_cache_path) { Dir.mktmpdir }
25
+
26
+ before(:each) do
27
+ @old_file_cache = Chef::Config[:file_cache_path]
28
+ Chef::Config[:file_cache_path] = file_cache_path
29
+ end
30
+
31
+ after(:each) do
32
+ Chef::Config[:file_cache_path] = @old_file_cache
33
+ FileUtils.rm_rf(file_cache_path)
34
+ end
35
+
23
36
  include_context Chef::Resource::File
24
37
 
25
38
  let(:file_base) { "remote_file_spec" }
26
- let(:source) { 'http://localhost:9000/nyan_cat.png' }
27
- let(:expected_content) do
28
- content = File.open(File.join(CHEF_SPEC_DATA, 'remote_file', 'nyan_cat.png'), "rb") do |f|
29
- f.read
30
- end
31
- content.force_encoding(Encoding::BINARY) if content.respond_to?(:force_encoding)
32
- content
33
- end
34
39
 
35
40
  def create_resource
36
41
  node = Chef::Node.new
@@ -41,28 +46,14 @@ describe Chef::Resource::RemoteFile do
41
46
  resource
42
47
  end
43
48
 
44
- let!(:resource) do
49
+ let(:resource) do
45
50
  create_resource
46
51
  end
47
52
 
48
- let(:default_mode) do
49
- # TODO: Lots of ugly here :(
50
- # RemoteFile uses FileUtils.cp. FileUtils does a copy by opening the
51
- # destination file and writing to it. Before 1.9.3, it does not preserve
52
- # the mode of the copied file. In 1.9.3 and after, it does. So we have to
53
- # figure out what the default mode ought to be via heuristic.
54
-
55
- t = Tempfile.new("get-the-mode")
56
- path = t.path
57
- path_2 = t.path + "fileutils-mode-test"
58
- FileUtils.cp(path, path_2)
59
- t.close
60
- m = File.stat(path_2).mode
61
- (07777 & m).to_s(8)
62
- end
53
+ let(:default_mode) { ((0100666 - File.umask) & 07777).to_s(8) }
63
54
 
64
- before(:all) do
65
- @server = TinyServer::Manager.new
55
+ def start_tiny_server(server_opts={})
56
+ @server = TinyServer::Manager.new(server_opts)
66
57
  @server.start
67
58
  @api = TinyServer::API.instance
68
59
  @api.clear
@@ -71,13 +62,90 @@ describe Chef::Resource::RemoteFile do
71
62
  f.read
72
63
  end
73
64
  }
65
+ @api.get("/nyan_cat.png.gz", 200, nil, { 'Content-Type' => 'application/gzip', 'Content-Encoding' => 'gzip' } ) {
66
+ File.open(File.join(CHEF_SPEC_DATA, 'remote_file', 'nyan_cat.png.gz'), "rb") do |f|
67
+ f.read
68
+ end
69
+ }
74
70
  end
75
71
 
76
- after(:all) do
72
+ def stop_tiny_server
77
73
  @server.stop
74
+ @server = @api = nil
78
75
  end
79
76
 
80
- it_behaves_like "a file resource"
77
+ context "when fetching files over HTTP" do
78
+ before(:all) do
79
+ start_tiny_server
80
+ end
81
+
82
+ after(:all) do
83
+ stop_tiny_server
84
+ end
85
+
86
+ context "when using normal encoding" do
87
+ let(:source) { 'http://localhost:9000/nyan_cat.png' }
88
+ let(:expected_content) do
89
+ content = File.open(File.join(CHEF_SPEC_DATA, 'remote_file', 'nyan_cat.png'), "rb") do |f|
90
+ f.read
91
+ end
92
+ content.force_encoding(Encoding::BINARY) if content.respond_to?(:force_encoding)
93
+ content
94
+ end
95
+
96
+ it_behaves_like "a file resource"
97
+
98
+ it_behaves_like "a securable resource with reporting"
99
+ end
100
+
101
+ context "when using gzip encoding" do
102
+ let(:source) { 'http://localhost:9000/nyan_cat.png.gz' }
103
+ let(:expected_content) do
104
+ content = File.open(File.join(CHEF_SPEC_DATA, 'remote_file', 'nyan_cat.png.gz'), "rb") do |f|
105
+ f.read
106
+ end
107
+ content.force_encoding(Encoding::BINARY) if content.respond_to?(:force_encoding)
108
+ content
109
+ end
110
+
111
+ it_behaves_like "a file resource"
112
+
113
+ it_behaves_like "a securable resource with reporting"
114
+ end
115
+ end
116
+
117
+ context "when fetching files over HTTPS" do
118
+
119
+ before(:all) do
120
+ cert_text = File.read(File.expand_path("ssl/chef-rspec.cert", CHEF_SPEC_DATA))
121
+ cert = OpenSSL::X509::Certificate.new(cert_text)
122
+ key_text = File.read(File.expand_path("ssl/chef-rspec.key", CHEF_SPEC_DATA))
123
+ key = OpenSSL::PKey::RSA.new(key_text)
124
+
125
+ server_opts = { :SSLEnable => true,
126
+ :SSLVerifyClient => OpenSSL::SSL::VERIFY_NONE,
127
+ :SSLCertificate => cert,
128
+ :SSLPrivateKey => key }
129
+
130
+ start_tiny_server(server_opts)
131
+ end
132
+
133
+ after(:all) do
134
+ stop_tiny_server
135
+ end
136
+
137
+ let(:source) { 'https://localhost:9000/nyan_cat.png' }
138
+
139
+ let(:expected_content) do
140
+ content = File.open(File.join(CHEF_SPEC_DATA, 'remote_file', 'nyan_cat.png'), "rb") do |f|
141
+ f.read
142
+ end
143
+ content.force_encoding(Encoding::BINARY) if content.respond_to?(:force_encoding)
144
+ content
145
+ end
146
+
147
+ it_behaves_like "a file resource"
148
+
149
+ end
81
150
 
82
- it_behaves_like "a securable resource with reporting"
83
151
  end
@@ -20,6 +20,10 @@ require 'spec_helper'
20
20
 
21
21
  describe Chef::Resource::Template do
22
22
 
23
+ def binread(file)
24
+ File.open(file,"rb") {|f| f.read }
25
+ end
26
+
23
27
  include_context Chef::Resource::File
24
28
 
25
29
  let(:file_base) { "template_spec" }
@@ -42,29 +46,19 @@ describe Chef::Resource::Template do
42
46
  resource = Chef::Resource::Template.new(path, run_context)
43
47
  resource.source('openldap_stuff.conf.erb')
44
48
  resource.cookbook('openldap')
49
+
50
+ # NOTE: partials rely on `cookbook_name` getting set by chef internals and
51
+ # ignore the user-set `cookbook` attribute.
52
+ resource.cookbook_name = "openldap"
53
+
45
54
  resource
46
55
  end
47
56
 
48
- let!(:resource) do
57
+ let(:resource) do
49
58
  create_resource
50
59
  end
51
60
 
52
- let(:default_mode) do
53
- # TODO: Lots of ugly here :(
54
- # RemoteFile uses FileUtils.cp. FileUtils does a copy by opening the
55
- # destination file and writing to it. Before 1.9.3, it does not preserve
56
- # the mode of the copied file. In 1.9.3 and after, it does. So we have to
57
- # figure out what the default mode ought to be via heuristic.
58
-
59
- t = Tempfile.new("get-the-mode")
60
- path = t.path
61
- path_2 = t.path + "fileutils-mode-test"
62
- FileUtils.cp(path, path_2)
63
- t.close
64
- m = File.stat(path_2).mode
65
- (07777 & m).to_s(8)
66
- end
67
-
61
+ let(:default_mode) { ((0100666 - File.umask) & 07777).to_s(8) }
68
62
 
69
63
  it_behaves_like "a file resource"
70
64
 
@@ -86,4 +80,166 @@ describe Chef::Resource::Template do
86
80
  IO.read(path).should == expected_content
87
81
  end
88
82
  end
83
+
84
+ describe "when the template resource defines helper methods" do
85
+
86
+ include_context "diff disabled"
87
+
88
+ let(:resource) do
89
+ r = create_resource
90
+ r.source "helper_test.erb"
91
+ r
92
+ end
93
+
94
+ let(:expected_content) { "value from helper method" }
95
+
96
+ shared_examples "a template with helpers" do
97
+ it "generates expected content by calling helper methods" do
98
+ resource.run_action(:create)
99
+ binread(path).strip.should == expected_content
100
+ end
101
+ end
102
+
103
+ context "using single helper syntax" do
104
+ before do
105
+ resource.helper(:helper_method) { "value from helper method" }
106
+ end
107
+
108
+ it_behaves_like "a template with helpers"
109
+ end
110
+
111
+ context "using single helper syntax referencing @node" do
112
+ before do
113
+ node.set[:helper_test_attr] = "value from helper method"
114
+ resource.helper(:helper_method) { "#{@node[:helper_test_attr]}" }
115
+ end
116
+
117
+ it_behaves_like "a template with helpers"
118
+ end
119
+
120
+ context "using an inline block to define helpers" do
121
+ before do
122
+ resource.helpers do
123
+ def helper_method
124
+ "value from helper method"
125
+ end
126
+ end
127
+ end
128
+
129
+ it_behaves_like "a template with helpers"
130
+ end
131
+
132
+ context "using an inline block referencing @node" do
133
+ before do
134
+ node.set[:helper_test_attr] = "value from helper method"
135
+
136
+ resource.helpers do
137
+ def helper_method
138
+ @node[:helper_test_attr]
139
+ end
140
+ end
141
+ end
142
+
143
+ it_behaves_like "a template with helpers"
144
+
145
+ end
146
+
147
+ context "using a module from a library" do
148
+
149
+ module ExampleModule
150
+ def helper_method
151
+ "value from helper method"
152
+ end
153
+ end
154
+
155
+ before do
156
+ resource.helpers(ExampleModule)
157
+ end
158
+
159
+ it_behaves_like "a template with helpers"
160
+
161
+ end
162
+ context "using a module from a library referencing @node" do
163
+
164
+ module ExampleModuleReferencingATNode
165
+ def helper_method
166
+ @node[:helper_test_attr]
167
+ end
168
+ end
169
+
170
+ before do
171
+ node.set[:helper_test_attr] = "value from helper method"
172
+
173
+ resource.helpers(ExampleModuleReferencingATNode)
174
+ end
175
+
176
+ it_behaves_like "a template with helpers"
177
+
178
+ end
179
+
180
+ context "using helpers with partial templates" do
181
+ before do
182
+ resource.source("helpers_via_partial_test.erb")
183
+ resource.helper(:helper_method) { "value from helper method" }
184
+ end
185
+
186
+ it_behaves_like "a template with helpers"
187
+
188
+ end
189
+ end
190
+
191
+ describe "when template source contains windows style line endings" do
192
+
193
+ include_context "diff disabled"
194
+
195
+ let(:expected_content) {
196
+ "Template rendering libraries\r\nshould support\r\ndifferent line endings\r\n\r\n"
197
+ }
198
+
199
+ context "for all lines" do
200
+ let(:resource) do
201
+ r = create_resource
202
+ r.source "all_windows_line_endings.erb"
203
+ r
204
+ end
205
+
206
+ it "output should contain windows line endings" do
207
+ resource.run_action(:create)
208
+ binread(path).each_line do |line|
209
+ line.should end_with("\r\n")
210
+ end
211
+ end
212
+ end
213
+
214
+ context "for some lines" do
215
+ let(:resource) do
216
+ r = create_resource
217
+ r.source "some_windows_line_endings.erb"
218
+ r
219
+ end
220
+
221
+ it "output should contain windows line endings" do
222
+ resource.run_action(:create)
223
+ binread(path).each_line do |line|
224
+ line.should end_with("\r\n")
225
+ end
226
+ end
227
+ end
228
+
229
+ context "for no lines" do
230
+ let(:resource) do
231
+ r = create_resource
232
+ r.source "no_windows_line_endings.erb"
233
+ r
234
+ end
235
+
236
+ it "output should not contain windows line endings" do
237
+ resource.run_action(:create)
238
+ IO.read(path).each_line do |line|
239
+ line.should_not end_with("\r\n")
240
+ end
241
+ end
242
+ end
243
+ end
244
+
89
245
  end
@@ -0,0 +1,547 @@
1
+ # encoding: UTF-8
2
+ #
3
+ # Author:: Daniel DeLeo (<dan@opscode.com>)
4
+ # Copyright:: Copyright (c) 2013 Opscode, Inc.
5
+ # License:: Apache License, Version 2.0
6
+ #
7
+ # Licensed under the Apache License, Version 2.0 (the "License");
8
+ # you may not use this file except in compliance with the License.
9
+ # You may obtain a copy of the License at
10
+ #
11
+ # http://www.apache.org/licenses/LICENSE-2.0
12
+ #
13
+ # Unless required by applicable law or agreed to in writing, software
14
+ # distributed under the License is distributed on an "AS IS" BASIS,
15
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16
+ # See the License for the specific language governing permissions and
17
+ # limitations under the License.
18
+ #
19
+
20
+ require 'spec_helper'
21
+ require 'chef/mixin/shell_out'
22
+
23
+ metadata = { :unix_only => true,
24
+ :requires_root => true,
25
+ :provider => {:user => Chef::Provider::User::Useradd}
26
+ }
27
+
28
+ describe Chef::Resource::User, metadata do
29
+
30
+ include Chef::Mixin::ShellOut
31
+
32
+
33
+ # Utility code for /etc/passwd interaction, avoid any caching of user records:
34
+ PwEntry = Struct.new(:name, :passwd, :uid, :gid, :gecos, :home, :shell)
35
+
36
+ class UserNotFound < StandardError; end
37
+
38
+ def pw_entry
39
+ passwd_file = File.open("/etc/passwd", "rb") {|f| f.read}
40
+ matcher = /^#{Regexp.escape(username)}.+$/
41
+ if passwd_entry = passwd_file.scan(matcher).first
42
+ PwEntry.new(*passwd_entry.split(':'))
43
+ else
44
+ raise UserNotFound, "no entry matching #{matcher.inspect} found in /etc/passwd"
45
+ end
46
+ end
47
+
48
+ def etc_shadow
49
+ File.open("/etc/shadow") {|f| f.read }
50
+ end
51
+
52
+ def supports_quote_in_username?
53
+ OHAI_SYSTEM["platform_family"] == "debian"
54
+ end
55
+
56
+ before do
57
+ # Silence shell_out live stream
58
+ Chef::Log.level = :warn
59
+ end
60
+
61
+ after do
62
+ begin
63
+ pw_entry # will raise if the user doesn't exist
64
+ shell_out!("userdel", "-f", "-r", username, :returns => [0,12])
65
+ rescue UserNotFound
66
+ # nothing to remove
67
+ end
68
+ end
69
+
70
+ let(:node) do
71
+ n = Chef::Node.new
72
+ n.consume_external_attrs(OHAI_SYSTEM.data.dup, {})
73
+ n
74
+ end
75
+
76
+ let(:events) do
77
+ Chef::EventDispatch::Dispatcher.new
78
+ end
79
+
80
+ let(:run_context) do
81
+ Chef::RunContext.new(node, {}, events)
82
+ end
83
+
84
+ let(:username) do
85
+ "chef-functional-test"
86
+ end
87
+
88
+ let(:uid) { nil }
89
+ let(:home) { nil }
90
+ let(:manage_home) { false }
91
+ let(:password) { nil }
92
+ let(:system) { false }
93
+ let(:comment) { nil }
94
+
95
+ let(:user_resource) do
96
+ r = Chef::Resource::User.new("TEST USER RESOURCE", run_context)
97
+ r.username(username)
98
+ r.uid(uid)
99
+ r.home(home)
100
+ r.comment(comment)
101
+ r.manage_home(manage_home)
102
+ r.password(password)
103
+ r.system(system)
104
+ r
105
+ end
106
+
107
+ let(:skip) { false }
108
+
109
+ describe "action :create" do
110
+
111
+ context "when the user does not exist beforehand" do
112
+ before do
113
+ if reason = skip
114
+ pending(reason)
115
+ end
116
+ user_resource.run_action(:create)
117
+ user_resource.should be_updated_by_last_action
118
+ end
119
+
120
+
121
+ it "ensures the user exists" do
122
+ pw_entry.name.should == username
123
+ end
124
+
125
+ # On Debian, the only constraints are that usernames must neither start
126
+ # with a dash ('-') nor plus ('+') nor tilde ('~') nor contain a colon
127
+ # (':'), a comma (','), or a whitespace (space: ' ', end of line: '\n',
128
+ # tabulation: '\t', etc.). Note that using a slash ('/') may break the
129
+ # default algorithm for the definition of the user's home directory.
130
+
131
+ context "and the username contains a single quote" do
132
+ let(:skip) do
133
+ if supports_quote_in_username?
134
+ false
135
+ else
136
+ "Platform #{OHAI_SYSTEM["platform"]} not expected to support username w/ quote"
137
+ end
138
+ end
139
+
140
+ let(:username) { "t'bilisi" }
141
+
142
+ it "ensures the user exists" do
143
+ pw_entry.name.should == username
144
+ end
145
+ end
146
+
147
+
148
+ context "when uid is set" do
149
+ # Should verify uid not in use...
150
+ let(:uid) { 1999 }
151
+
152
+ it "ensures the user has the given uid" do
153
+ pw_entry.uid.should == "1999"
154
+ end
155
+ end
156
+
157
+ context "when comment is set" do
158
+ let(:comment) { "hello this is dog" }
159
+
160
+ it "ensures the comment is set" do
161
+ pw_entry.gecos.should == "hello this is dog"
162
+ end
163
+
164
+ context "in standard gecos format" do
165
+ let(:comment) { "Bobo T. Clown,some building,555-555-5555,@boboclown" }
166
+
167
+ it "ensures the comment is set" do
168
+ pw_entry.gecos.should == comment
169
+ end
170
+ end
171
+
172
+ context "to a string containing multibyte characters" do
173
+ let(:comment) { "(╯°□°)╯︵ ┻━┻" }
174
+
175
+ it "ensures the comment is set" do
176
+ actual = pw_entry.gecos
177
+ actual.force_encoding(Encoding::UTF_8) if "".respond_to?(:force_encoding)
178
+ actual.should == comment
179
+ end
180
+ end
181
+
182
+ context "to a string containing an apostrophe `'`" do
183
+ let(:comment) { "don't go" }
184
+
185
+ it "ensures the comment is set" do
186
+ pw_entry.gecos.should == comment
187
+ end
188
+ end
189
+ end
190
+
191
+ context "when home is set" do
192
+ let(:home) { "/home/#{username}" }
193
+
194
+ it "ensures the user's home is set to the given path" do
195
+ pw_entry.home.should == "/home/#{username}"
196
+ end
197
+
198
+ if OHAI_SYSTEM["platform_family"] == "rhel"
199
+ # Inconsistent behavior. See: CHEF-2205
200
+ it "creates the home dir when not explicitly asked to on RHEL (XXX)" do
201
+ File.should exist("/home/#{username}")
202
+ end
203
+ else
204
+ it "does not create the home dir without `manage_home'" do
205
+ File.should_not exist("/home/#{username}")
206
+ end
207
+ end
208
+
209
+ context "and manage_home is enabled" do
210
+ let(:manage_home) { true }
211
+
212
+ it "ensures the user's home directory exists" do
213
+ File.should exist("/home/#{username}")
214
+ end
215
+ end
216
+ end
217
+
218
+ context "when a password is specified" do
219
+ # openssl passwd -1 "secretpassword"
220
+ let(:password) { "$1$RRa/wMM/$XltKfoX5ffnexVF4dHZZf/" }
221
+ it "sets the user's shadow password" do
222
+ pw_entry.passwd.should == "x"
223
+ expected_shadow = "chef-functional-test:$1$RRa/wMM/$XltKfoX5ffnexVF4dHZZf/"
224
+ etc_shadow.should include(expected_shadow)
225
+ end
226
+ end
227
+
228
+ context "when a system user is specified" do
229
+ let(:system) { true }
230
+ let(:uid_min) do
231
+ # from `man useradd`, login user means uid will be between
232
+ # UID_SYS_MIN and UID_SYS_MAX defined in /etc/login.defs. On my
233
+ # Ubuntu 13.04 system, these are commented out, so we'll look at
234
+ # UID_MIN to find the lower limit of the non-system-user range, and
235
+ # use that value in our assertions.
236
+ login_defs = File.open("/etc/login.defs", "rb") {|f| f.read }
237
+ uid_min_scan = /^UID_MIN\s+(\d+)/
238
+ login_defs.match(uid_min_scan)[1]
239
+ end
240
+
241
+ it "ensures the user has the properties of a system user" do
242
+ pw_entry.uid.to_i.should be < uid_min.to_i
243
+ end
244
+ end
245
+ end # when the user does not exist beforehand
246
+
247
+ context "when the user already exists" do
248
+
249
+ let(:expect_updated?) { true }
250
+
251
+ let(:existing_uid) { nil }
252
+ let(:existing_home) { nil }
253
+ let(:existing_manage_home) { false }
254
+ let(:existing_password) { nil }
255
+ let(:existing_system) { false }
256
+ let(:existing_comment) { nil }
257
+
258
+ let(:existing_user) do
259
+ r = Chef::Resource::User.new("TEST USER RESOURCE", run_context)
260
+ # username is identity attr, must match.
261
+ r.username(username)
262
+ r.uid(existing_uid)
263
+ r.home(existing_home)
264
+ r.comment(existing_comment)
265
+ r.manage_home(existing_manage_home)
266
+ r.password(existing_password)
267
+ r.system(existing_system)
268
+ r
269
+ end
270
+
271
+ before do
272
+ if reason = skip
273
+ pending(reason)
274
+ end
275
+ existing_user.run_action(:create)
276
+ existing_user.should be_updated_by_last_action
277
+ user_resource.run_action(:create)
278
+ user_resource.updated_by_last_action?.should == expect_updated?
279
+ end
280
+
281
+ context "and all properties are in the desired state" do
282
+ let(:uid) { 1999 }
283
+ let(:home) { "/home/bobo" }
284
+ let(:manage_home) { true }
285
+ # openssl passwd -1 "secretpassword"
286
+ let(:password) { "$1$RRa/wMM/$XltKfoX5ffnexVF4dHZZf/" }
287
+ let(:system) { false }
288
+ let(:comment) { "hello this is dog" }
289
+
290
+ let(:existing_uid) { uid }
291
+ let(:existing_home) { home }
292
+ let(:existing_manage_home) { manage_home }
293
+ let(:existing_password) { password }
294
+ let(:existing_system) { false }
295
+ let(:existing_comment) { comment }
296
+
297
+ let(:expect_updated?) { false }
298
+
299
+ it "does not update the user" do
300
+ user_resource.should_not be_updated
301
+ end
302
+ end
303
+
304
+ context "and the uid is updated" do
305
+ let(:uid) { 1999 }
306
+ let(:existing_uid) { 1998 }
307
+
308
+ it "ensures the uid is set to the desired value" do
309
+ pw_entry.uid.should == "1999"
310
+ end
311
+ end
312
+
313
+ context "and the comment is updated" do
314
+ let(:comment) { "hello this is dog" }
315
+ let(:existing_comment) { "woof" }
316
+
317
+ it "ensures the comment field is set to the desired value" do
318
+ pw_entry.gecos.should == "hello this is dog"
319
+ end
320
+ end
321
+
322
+ context "and home directory is updated" do
323
+ let(:existing_home) { "/home/foo" }
324
+ let(:home) { "/home/bar" }
325
+ it "ensures the home directory is set to the desired value" do
326
+ pw_entry.home.should == "/home/bar"
327
+ end
328
+
329
+ context "and manage_home is enabled" do
330
+ let(:existing_manage_home) { true }
331
+ let(:manage_home) { true }
332
+ it "moves the home directory to the new location" do
333
+ File.should_not exist("/home/foo")
334
+ File.should exist("/home/bar")
335
+ end
336
+ end
337
+
338
+ context "and manage_home wasn't enabled but is now" do
339
+ let(:existing_manage_home) { false }
340
+ let(:manage_home) { true }
341
+
342
+ if OHAI_SYSTEM["platform_family"] == "rhel"
343
+ # Inconsistent behavior. See: CHEF-2205
344
+ it "created the home dir b/c of CHEF-2205 so it still exists" do
345
+ # This behavior seems contrary to expectation and non-convergent.
346
+ File.should_not exist("/home/foo")
347
+ File.should exist("/home/bar")
348
+ end
349
+ else
350
+ it "does not create the home dir in the desired location (XXX)" do
351
+ # This behavior seems contrary to expectation and non-convergent.
352
+ File.should_not exist("/home/foo")
353
+ File.should_not exist("/home/bar")
354
+ end
355
+ end
356
+ end
357
+
358
+ context "and manage_home was enabled but is not now" do
359
+ let(:existing_manage_home) { true }
360
+ let(:manage_home) { false }
361
+
362
+ it "leaves the old home directory around (XXX)" do
363
+ # Would it be better to remove the old home?
364
+ File.should exist("/home/foo")
365
+ File.should_not exist("/home/bar")
366
+ end
367
+ end
368
+ end
369
+
370
+ context "and a password is added" do
371
+ # openssl passwd -1 "secretpassword"
372
+ let(:password) { "$1$RRa/wMM/$XltKfoX5ffnexVF4dHZZf/" }
373
+
374
+ it "ensures the password is set" do
375
+ pw_entry.passwd.should == "x"
376
+ expected_shadow = "chef-functional-test:$1$RRa/wMM/$XltKfoX5ffnexVF4dHZZf/"
377
+ etc_shadow.should include(expected_shadow)
378
+ end
379
+
380
+ end
381
+
382
+ context "and the password is updated" do
383
+ # openssl passwd -1 "OLDpassword"
384
+ let(:existing_password) { "$1$1dVmwm4z$CftsFn8eBDjDRUytYKkXB." }
385
+ # openssl passwd -1 "secretpassword"
386
+ let(:password) { "$1$RRa/wMM/$XltKfoX5ffnexVF4dHZZf/" }
387
+
388
+ it "ensures the password is set to the desired value" do
389
+ pw_entry.passwd.should == "x"
390
+ expected_shadow = "chef-functional-test:$1$RRa/wMM/$XltKfoX5ffnexVF4dHZZf/"
391
+ etc_shadow.should include(expected_shadow)
392
+ end
393
+ end
394
+
395
+ context "and the user is changed from not-system to system" do
396
+ let(:existing_system) { false }
397
+ let(:system) { true }
398
+
399
+ let(:expect_updated?) { false }
400
+
401
+ it "does not modify the user at all" do
402
+ end
403
+ end
404
+
405
+ context "and the user is changed from system to not-system" do
406
+ let(:existing_system) { true }
407
+ let(:system) { false }
408
+
409
+ let(:expect_updated?) { false }
410
+
411
+ it "does not modify the user at all" do
412
+ end
413
+ end
414
+
415
+ end # when the user already exists
416
+ end # action :create
417
+
418
+ shared_context "user exists for lock/unlock" do
419
+ let(:user_locked_context?) { false }
420
+
421
+ def shadow_entry
422
+ etc_shadow.lines.select {|l| l.include?(username) }.first
423
+ end
424
+
425
+ def shadow_password
426
+ shadow_entry.split(':')[1]
427
+ end
428
+
429
+ before do
430
+ # create user and setup locked/unlocked state
431
+ user_resource.dup.run_action(:create)
432
+
433
+ if user_locked_context?
434
+ shell_out!("usermod -L #{username}")
435
+ shadow_password.should include("!")
436
+ elsif password
437
+ shadow_password.should_not include("!")
438
+ end
439
+ end
440
+ end
441
+
442
+ describe "action :lock" do
443
+ context "when the user does not exist" do
444
+ it "raises a sensible error" do
445
+ expect { user_resource.run_action(:lock) }.to raise_error(Chef::Exceptions::User)
446
+ end
447
+ end
448
+
449
+ context "when the user exists" do
450
+
451
+ include_context "user exists for lock/unlock"
452
+
453
+ before do
454
+ user_resource.run_action(:lock)
455
+ end
456
+
457
+ context "and the user is not locked" do
458
+ # user will be locked if it has no password
459
+ let(:password) { "$1$RRa/wMM/$XltKfoX5ffnexVF4dHZZf/" }
460
+
461
+ it "locks the user's password" do
462
+ shadow_password.should include("!")
463
+ end
464
+ end
465
+
466
+ context "and the user is locked" do
467
+ # user will be locked if it has no password
468
+ let(:password) { "$1$RRa/wMM/$XltKfoX5ffnexVF4dHZZf/" }
469
+ let(:user_locked_context?) { true }
470
+ it "does not update the user" do
471
+ user_resource.should_not be_updated_by_last_action
472
+ end
473
+ end
474
+ end
475
+ end # action :lock
476
+
477
+ describe "action :unlock" do
478
+ context "when the user does not exist" do
479
+ it "raises a sensible error" do
480
+ expect { user_resource.run_action(:unlock) }.to raise_error(Chef::Exceptions::User)
481
+ end
482
+ end
483
+
484
+ context "when the user exists" do
485
+
486
+ include_context "user exists for lock/unlock"
487
+
488
+ before do
489
+ begin
490
+ user_resource.run_action(:unlock)
491
+ @error = nil
492
+ rescue Exception => e
493
+ @error = e
494
+ end
495
+ end
496
+
497
+ context "and has no password" do
498
+
499
+ # TODO: platform_family should be setup in spec_helper w/ tags
500
+ if OHAI_SYSTEM["platform_family"] == "suse"
501
+ # suse gets this right:
502
+ it "errors out trying to unlock the user" do
503
+ @error.should be_a(Mixlib::ShellOut::ShellCommandFailed)
504
+ @error.message.should include("Cannot unlock the password")
505
+ end
506
+ else
507
+
508
+ # borked on all other platforms:
509
+ it "is marked as updated but doesn't modify the user (XXX)" do
510
+ # This should be an error instead; note that usermod still exits 0
511
+ # (which is probably why this case silently fails):
512
+ #
513
+ # DEBUG: ---- Begin output of usermod -U chef-functional-test ----
514
+ # DEBUG: STDOUT:
515
+ # DEBUG: STDERR: usermod: unlocking the user's password would result in a passwordless account.
516
+ # You should set a password with usermod -p to unlock this user's password.
517
+ # DEBUG: ---- End output of usermod -U chef-functional-test ----
518
+ # DEBUG: Ran usermod -U chef-functional-test returned 0
519
+ @error.should be_nil
520
+ pw_entry.passwd.should == 'x'
521
+ shadow_password.should == "!"
522
+ end
523
+ end
524
+ end
525
+
526
+ context "and has a password" do
527
+ let(:password) { "$1$RRa/wMM/$XltKfoX5ffnexVF4dHZZf/" }
528
+ context "and the user is not locked" do
529
+ it "does not update the user" do
530
+ user_resource.should_not be_updated_by_last_action
531
+ end
532
+ end
533
+
534
+ context "and the user is locked" do
535
+ let(:user_locked_context?) { true }
536
+
537
+ it "unlocks the user's password" do
538
+ shadow_entry = etc_shadow.lines.select {|l| l.include?(username) }.first
539
+ shadow_password = shadow_entry.split(':')[1]
540
+ shadow_password.should_not include("!")
541
+ end
542
+ end
543
+ end
544
+ end
545
+ end # action :unlock
546
+
547
+ end