puppet 0.18.4 → 0.22.4

Sign up to get free protection for your applications and to get access to all the features.

Potentially problematic release.


This version of puppet might be problematic. Click here for more details.

Files changed (673) hide show
  1. data/CHANGELOG +288 -0
  2. data/README +2 -2
  3. data/Rakefile +78 -5
  4. data/bin/puppet +28 -36
  5. data/bin/puppetca +81 -38
  6. data/bin/puppetd +65 -62
  7. data/bin/puppetdoc +409 -140
  8. data/bin/puppetmasterd +59 -47
  9. data/bin/puppetrun +38 -23
  10. data/conf/freebsd/puppetd +26 -0
  11. data/conf/freebsd/puppetmasterd +26 -0
  12. data/conf/gentoo/conf.d/puppet +5 -0
  13. data/conf/gentoo/conf.d/puppetmaster +12 -0
  14. data/conf/gentoo/init.d/puppet +38 -0
  15. data/conf/gentoo/init.d/puppetmaster +50 -0
  16. data/conf/gentoo/puppet/fileserver.conf +12 -0
  17. data/conf/gentoo/puppet/puppetca.conf +29 -0
  18. data/conf/gentoo/puppet/puppetd.conf +29 -0
  19. data/conf/gentoo/puppet/puppetmasterd.conf +29 -0
  20. data/conf/redhat/client.init +10 -5
  21. data/conf/redhat/client.sysconfig +1 -1
  22. data/conf/redhat/fileserver.conf +2 -2
  23. data/conf/redhat/logrotate +1 -1
  24. data/conf/redhat/no-lockdir.patch +13 -0
  25. data/conf/redhat/puppet.spec +65 -8
  26. data/conf/redhat/puppetd.conf +0 -4
  27. data/conf/redhat/server.init +3 -6
  28. data/conf/solaris/pkginfo +1 -1
  29. data/conf/solaris/smf/svc-puppetd +2 -2
  30. data/conf/suse/client.init +142 -0
  31. data/conf/suse/puppet.spec +221 -0
  32. data/conf/suse/server.init +162 -0
  33. data/examples/code/mac_automount.pp +16 -0
  34. data/examples/root/bin/sleeper +3 -5
  35. data/examples/root/etc/init.d/sleeper +8 -2
  36. data/examples/root/etc/puppet/fileserver.conf +12 -2
  37. data/examples/root/etc/puppet/namespaceauth.conf +20 -0
  38. data/examples/root/etc/puppet/puppetd.conf +4 -0
  39. data/examples/root/etc/puppet/puppetmasterd.conf +6 -9
  40. data/examples/root/etc/puppet/tagmail.conf +1 -0
  41. data/ext/emacs/puppet-mode.el +46 -1
  42. data/ext/logcheck/puppet +15 -0
  43. data/ext/module_puppet +15 -23
  44. data/ext/vim/puppet.vim +4 -2
  45. data/install.rb +2 -1
  46. data/lib/puppet.rb +76 -207
  47. data/lib/puppet/configuration.rb +331 -0
  48. data/lib/puppet/daemon.rb +63 -246
  49. data/lib/puppet/dsl.rb +371 -0
  50. data/lib/puppet/element.rb +8 -26
  51. data/lib/puppet/error.rb +54 -0
  52. data/lib/puppet/event.rb +8 -243
  53. data/lib/puppet/{base64.rb → external/base64.rb} +0 -0
  54. data/lib/puppet/external/event-loop.rb +1 -0
  55. data/lib/puppet/{event-loop → external/event-loop}/better-definers.rb +0 -0
  56. data/lib/puppet/{event-loop → external/event-loop}/event-loop.rb +2 -2
  57. data/lib/puppet/{event-loop → external/event-loop}/signal-system.rb +1 -1
  58. data/lib/puppet/external/gratr.rb +33 -0
  59. data/lib/puppet/external/gratr/adjacency_graph.rb +257 -0
  60. data/lib/puppet/external/gratr/base.rb +34 -0
  61. data/lib/puppet/external/gratr/biconnected.rb +116 -0
  62. data/lib/puppet/external/gratr/chinese_postman.rb +123 -0
  63. data/lib/puppet/external/gratr/common.rb +73 -0
  64. data/lib/puppet/external/gratr/comparability.rb +92 -0
  65. data/lib/puppet/external/gratr/digraph.rb +116 -0
  66. data/lib/puppet/external/gratr/digraph_distance.rb +185 -0
  67. data/lib/puppet/external/gratr/dot.rb +90 -0
  68. data/lib/puppet/external/gratr/edge.rb +145 -0
  69. data/lib/puppet/external/gratr/graph.rb +303 -0
  70. data/lib/puppet/external/gratr/graph_api.rb +83 -0
  71. data/lib/puppet/external/gratr/import.rb +44 -0
  72. data/lib/puppet/external/gratr/labels.rb +90 -0
  73. data/lib/puppet/external/gratr/maximum_flow.rb +64 -0
  74. data/lib/puppet/external/gratr/rdot.rb +327 -0
  75. data/lib/puppet/external/gratr/search.rb +409 -0
  76. data/lib/puppet/external/gratr/strong_components.rb +127 -0
  77. data/lib/puppet/external/gratr/undirected_graph.rb +153 -0
  78. data/lib/puppet/{lock.rb → external/lock.rb} +1 -1
  79. data/lib/puppet/feature/base.rb +20 -0
  80. data/lib/puppet/feature/rails.rb +52 -0
  81. data/lib/puppet/metatype/attributes.rb +719 -0
  82. data/lib/puppet/metatype/closure.rb +111 -0
  83. data/lib/puppet/metatype/container.rb +94 -0
  84. data/lib/puppet/metatype/evaluation.rb +118 -0
  85. data/lib/puppet/metatype/instances.rb +261 -0
  86. data/lib/puppet/metatype/manager.rb +169 -0
  87. data/lib/puppet/metatype/metaparams.rb +409 -0
  88. data/lib/puppet/metatype/providers.rb +260 -0
  89. data/lib/puppet/metatype/relationships.rb +116 -0
  90. data/lib/puppet/metatype/schedules.rb +39 -0
  91. data/lib/puppet/metatype/tags.rb +39 -0
  92. data/lib/puppet/modules.rb +113 -0
  93. data/lib/puppet/network/authconfig.rb +168 -0
  94. data/lib/puppet/network/authorization.rb +84 -0
  95. data/lib/puppet/network/authstore.rb +293 -0
  96. data/lib/puppet/network/client.rb +187 -0
  97. data/lib/puppet/network/client/ca.rb +56 -0
  98. data/lib/puppet/network/client/dipper.rb +81 -0
  99. data/lib/puppet/network/client/file.rb +7 -0
  100. data/lib/puppet/network/client/logger.rb +6 -0
  101. data/lib/puppet/network/client/master.rb +644 -0
  102. data/lib/puppet/{client → network/client}/proxy.rb +3 -3
  103. data/lib/puppet/{client/reporter.rb → network/client/report.rb} +4 -7
  104. data/lib/puppet/{client/pelement.rb → network/client/resource.rb} +6 -19
  105. data/lib/puppet/network/client/runner.rb +13 -0
  106. data/lib/puppet/network/client/status.rb +5 -0
  107. data/lib/puppet/network/client_request.rb +32 -0
  108. data/lib/puppet/network/handler.rb +33 -0
  109. data/lib/puppet/{server → network/handler}/ca.rb +5 -6
  110. data/lib/puppet/network/handler/filebucket.rb +180 -0
  111. data/lib/puppet/{server → network/handler}/fileserver.rb +277 -219
  112. data/lib/puppet/{server → network/handler}/logger.rb +3 -5
  113. data/lib/puppet/{server → network/handler}/master.rb +42 -8
  114. data/lib/puppet/network/handler/report.rb +158 -0
  115. data/lib/puppet/network/handler/resource.rb +190 -0
  116. data/lib/puppet/{server → network/handler}/runner.rb +17 -18
  117. data/lib/puppet/network/handler/status.rb +13 -0
  118. data/lib/puppet/network/rights.rb +74 -0
  119. data/lib/puppet/network/server.rb +5 -0
  120. data/lib/puppet/network/server/mongrel.rb +138 -0
  121. data/lib/puppet/network/server/webrick.rb +153 -0
  122. data/lib/puppet/network/xmlrpc/client.rb +129 -0
  123. data/lib/puppet/network/xmlrpc/processor.rb +91 -0
  124. data/lib/puppet/network/xmlrpc/server.rb +20 -0
  125. data/lib/puppet/network/xmlrpc/webrick_servlet.rb +121 -0
  126. data/lib/puppet/parameter.rb +390 -346
  127. data/lib/puppet/parser/ast.rb +116 -147
  128. data/lib/puppet/parser/ast/astarray.rb +17 -33
  129. data/lib/puppet/parser/ast/branch.rb +2 -0
  130. data/lib/puppet/parser/ast/caseopt.rb +7 -12
  131. data/lib/puppet/parser/ast/casestatement.rb +23 -32
  132. data/lib/puppet/parser/ast/collection.rb +19 -80
  133. data/lib/puppet/parser/ast/collexpr.rb +81 -0
  134. data/lib/puppet/parser/ast/component.rb +160 -89
  135. data/lib/puppet/parser/ast/else.rb +30 -0
  136. data/lib/puppet/parser/ast/function.rb +9 -2
  137. data/lib/puppet/parser/ast/hostclass.rb +47 -131
  138. data/lib/puppet/parser/ast/ifstatement.rb +43 -0
  139. data/lib/puppet/parser/ast/leaf.rb +10 -21
  140. data/lib/puppet/parser/ast/node.rb +32 -79
  141. data/lib/puppet/parser/ast/resourcedef.rb +222 -0
  142. data/lib/puppet/parser/ast/{typedefaults.rb → resourcedefaults.rb} +10 -16
  143. data/lib/puppet/parser/ast/resourceoverride.rb +62 -0
  144. data/lib/puppet/parser/ast/{objectparam.rb → resourceparam.rb} +12 -6
  145. data/lib/puppet/parser/ast/resourceref.rb +44 -0
  146. data/lib/puppet/parser/ast/selector.rb +16 -8
  147. data/lib/puppet/parser/ast/tag.rb +3 -1
  148. data/lib/puppet/parser/ast/vardef.rb +8 -12
  149. data/lib/puppet/parser/collector.rb +181 -0
  150. data/lib/puppet/parser/functions.rb +191 -36
  151. data/lib/puppet/parser/interpreter.rb +802 -380
  152. data/lib/puppet/parser/lexer.rb +86 -19
  153. data/lib/puppet/parser/parser.rb +1123 -960
  154. data/lib/puppet/parser/resource.rb +353 -0
  155. data/lib/puppet/parser/resource/param.rb +57 -0
  156. data/lib/puppet/parser/resource/reference.rb +71 -0
  157. data/lib/puppet/parser/scope.rb +573 -1000
  158. data/lib/puppet/parser/templatewrapper.rb +54 -0
  159. data/lib/puppet/pgraph.rb +208 -0
  160. data/lib/puppet/propertychange.rb +143 -0
  161. data/lib/puppet/provider.rb +302 -0
  162. data/lib/puppet/provider/cron/crontab.rb +187 -0
  163. data/lib/puppet/provider/group/groupadd.rb +29 -0
  164. data/lib/puppet/provider/group/netinfo.rb +12 -0
  165. data/lib/puppet/provider/group/pw.rb +31 -0
  166. data/lib/puppet/provider/host/netinfo.rb +18 -0
  167. data/lib/puppet/provider/host/parsed.rb +73 -0
  168. data/lib/puppet/provider/mount.rb +57 -0
  169. data/lib/puppet/provider/mount/netinfo.rb +38 -0
  170. data/lib/puppet/provider/mount/parsed.rb +37 -0
  171. data/lib/puppet/provider/nameservice.rb +344 -0
  172. data/lib/puppet/provider/nameservice/netinfo.rb +210 -0
  173. data/lib/puppet/provider/nameservice/objectadd.rb +45 -0
  174. data/lib/puppet/provider/nameservice/pw.rb +22 -0
  175. data/lib/puppet/provider/package/apple.rb +53 -0
  176. data/lib/puppet/provider/package/apt.rb +119 -0
  177. data/lib/puppet/provider/package/aptitude.rb +30 -0
  178. data/lib/puppet/provider/package/aptrpm.rb +79 -0
  179. data/lib/puppet/provider/package/blastwave.rb +114 -0
  180. data/lib/puppet/provider/package/darwinport.rb +88 -0
  181. data/lib/puppet/provider/package/dpkg.rb +109 -0
  182. data/lib/puppet/provider/package/freebsd.rb +43 -0
  183. data/lib/puppet/provider/package/gem.rb +104 -0
  184. data/lib/puppet/provider/package/openbsd.rb +93 -0
  185. data/lib/puppet/provider/package/pkgdmg.rb +119 -0
  186. data/lib/puppet/provider/package/portage.rb +112 -0
  187. data/lib/puppet/provider/package/ports.rb +94 -0
  188. data/lib/puppet/provider/package/rpm.rb +125 -0
  189. data/lib/puppet/provider/package/rug.rb +53 -0
  190. data/lib/puppet/provider/package/sun.rb +168 -0
  191. data/lib/puppet/provider/package/sunfreeware.rb +9 -0
  192. data/lib/puppet/provider/package/up2date.rb +45 -0
  193. data/lib/puppet/provider/package/yum.rb +54 -0
  194. data/lib/puppet/provider/parsedfile.rb +342 -0
  195. data/lib/puppet/provider/port/parsed.rb +174 -0
  196. data/lib/puppet/provider/service/base.rb +136 -0
  197. data/lib/puppet/provider/service/debian.rb +32 -0
  198. data/lib/puppet/provider/service/gentoo.rb +49 -0
  199. data/lib/puppet/{type → provider}/service/init.rb +42 -40
  200. data/lib/puppet/provider/service/redhat.rb +59 -0
  201. data/lib/puppet/{type → provider}/service/smf.rb +24 -13
  202. data/lib/puppet/provider/sshkey/parsed.rb +36 -0
  203. data/lib/puppet/provider/user/netinfo.rb +106 -0
  204. data/lib/puppet/provider/user/pw.rb +41 -0
  205. data/lib/puppet/provider/user/useradd.rb +67 -0
  206. data/lib/puppet/provider/zone/solaris.rb +208 -0
  207. data/lib/puppet/rails.rb +102 -66
  208. data/lib/puppet/rails/database/001_add_indexes.rb +38 -0
  209. data/lib/puppet/rails/database/schema.rb +89 -0
  210. data/lib/puppet/rails/external/tagging/acts_as_taggable.rb +62 -0
  211. data/lib/puppet/rails/external/tagging/init.rb +5 -0
  212. data/lib/puppet/rails/external/tagging/tag.rb +50 -0
  213. data/lib/puppet/rails/external/tagging/tagging.rb +12 -0
  214. data/lib/puppet/rails/fact_name.rb +7 -0
  215. data/lib/puppet/rails/fact_value.rb +5 -0
  216. data/lib/puppet/rails/host.rb +95 -46
  217. data/lib/puppet/rails/param_name.rb +28 -0
  218. data/lib/puppet/rails/param_value.rb +5 -0
  219. data/lib/puppet/rails/puppet_class.rb +9 -0
  220. data/lib/puppet/rails/resource.rb +95 -0
  221. data/lib/puppet/rails/source_file.rb +5 -0
  222. data/lib/puppet/relationship.rb +63 -0
  223. data/lib/puppet/reports/log.rb +14 -0
  224. data/lib/puppet/reports/rrdgraph.rb +114 -10
  225. data/lib/puppet/reports/store.rb +64 -0
  226. data/lib/puppet/reports/tagmail.rb +144 -71
  227. data/lib/puppet/sslcertificates.rb +38 -5
  228. data/lib/puppet/sslcertificates/ca.rb +142 -37
  229. data/lib/puppet/sslcertificates/certificate.rb +3 -3
  230. data/lib/puppet/sslcertificates/inventory.rb +53 -0
  231. data/lib/puppet/sslcertificates/support.rb +128 -0
  232. data/lib/puppet/transaction.rb +568 -189
  233. data/lib/puppet/transaction/report.rb +14 -3
  234. data/lib/puppet/transportable.rb +18 -10
  235. data/lib/puppet/type.rb +279 -2299
  236. data/lib/puppet/type/component.rb +63 -63
  237. data/lib/puppet/type/cron.rb +294 -710
  238. data/lib/puppet/type/exec.rb +185 -129
  239. data/lib/puppet/type/group.rb +38 -89
  240. data/lib/puppet/type/host.rb +110 -0
  241. data/lib/puppet/type/mount.rb +189 -0
  242. data/lib/puppet/type/notify.rb +47 -0
  243. data/lib/puppet/type/package.rb +129 -257
  244. data/lib/puppet/type/parsedtype.rb +172 -297
  245. data/lib/puppet/type/pfile.rb +540 -319
  246. data/lib/puppet/type/pfile/checksum.rb +103 -76
  247. data/lib/puppet/type/pfile/content.rb +16 -10
  248. data/lib/puppet/type/pfile/ensure.rb +52 -34
  249. data/lib/puppet/type/pfile/group.rb +25 -18
  250. data/lib/puppet/type/pfile/mode.rb +7 -4
  251. data/lib/puppet/type/pfile/{uid.rb → owner.rb} +21 -17
  252. data/lib/puppet/type/pfile/source.rb +119 -124
  253. data/lib/puppet/type/pfile/target.rb +29 -45
  254. data/lib/puppet/type/pfile/type.rb +2 -2
  255. data/lib/puppet/type/pfilebucket.rb +18 -14
  256. data/lib/puppet/type/port.rb +121 -0
  257. data/lib/puppet/type/property.rb +530 -0
  258. data/lib/puppet/type/resources.rb +150 -0
  259. data/lib/puppet/type/schedule.rb +38 -22
  260. data/lib/puppet/type/service.rb +70 -326
  261. data/lib/puppet/type/sshkey.rb +76 -0
  262. data/lib/puppet/type/tidy.rb +197 -97
  263. data/lib/puppet/type/user.rb +107 -183
  264. data/lib/puppet/type/yumrepo.rb +53 -34
  265. data/lib/puppet/type/zone.rb +55 -208
  266. data/lib/puppet/util.rb +239 -201
  267. data/lib/puppet/util/autoload.rb +107 -0
  268. data/lib/puppet/util/classgen.rb +208 -0
  269. data/lib/puppet/{config.rb → util/config.rb} +102 -54
  270. data/lib/puppet/util/docs.rb +104 -0
  271. data/lib/puppet/util/errors.rb +55 -0
  272. data/lib/puppet/util/execution.rb +22 -0
  273. data/lib/puppet/util/feature.rb +76 -0
  274. data/lib/puppet/util/fileparsing.rb +380 -0
  275. data/lib/puppet/util/filetype.rb +300 -0
  276. data/lib/puppet/util/graph.rb +39 -0
  277. data/lib/puppet/util/inifile.rb +209 -0
  278. data/lib/puppet/util/loadedfile.rb +71 -0
  279. data/lib/puppet/util/log.rb +549 -0
  280. data/lib/puppet/util/logging.rb +20 -0
  281. data/lib/puppet/util/metaid.rb +22 -0
  282. data/lib/puppet/util/methodhelper.rb +37 -0
  283. data/lib/puppet/util/metric.rb +160 -0
  284. data/lib/puppet/util/package.rb +31 -0
  285. data/lib/puppet/util/pidlock.rb +68 -0
  286. data/lib/puppet/util/plist.rb +24 -0
  287. data/lib/puppet/util/plist/generator.rb +226 -0
  288. data/lib/puppet/util/plist/parser.rb +227 -0
  289. data/lib/puppet/util/posix.rb +87 -0
  290. data/lib/puppet/util/provider_features.rb +170 -0
  291. data/lib/puppet/util/rails/collection_merger.rb +42 -0
  292. data/lib/puppet/util/storage.rb +103 -0
  293. data/lib/puppet/util/subclass_loader.rb +83 -0
  294. data/lib/puppet/util/suidmanager.rb +86 -0
  295. data/lib/puppet/util/variables.rb +39 -0
  296. data/lib/puppet/util/warnings.rb +15 -0
  297. data/test/Rakefile +97 -0
  298. data/test/certmgr/ca.rb +81 -0
  299. data/test/certmgr/certmgr.rb +77 -50
  300. data/test/certmgr/inventory.rb +79 -0
  301. data/test/certmgr/support.rb +81 -0
  302. data/test/executables/filebucket.rb +49 -0
  303. data/test/executables/puppetbin.rb +28 -12
  304. data/test/executables/puppetca.rb +75 -54
  305. data/test/executables/puppetd.rb +10 -13
  306. data/test/executables/puppetmasterd.rb +12 -17
  307. data/test/executables/puppetmodule.rb +18 -17
  308. data/test/language/ast.rb +242 -798
  309. data/test/language/ast/casestatement.rb +104 -0
  310. data/test/language/ast/component.rb +133 -0
  311. data/test/language/ast/hostclass.rb +162 -0
  312. data/test/language/ast/selector.rb +62 -0
  313. data/test/language/ast/variable.rb +31 -0
  314. data/test/language/collector.rb +369 -0
  315. data/test/language/functions.rb +305 -18
  316. data/test/language/interpreter.rb +894 -125
  317. data/test/language/lexer.rb +98 -12
  318. data/test/language/node.rb +37 -53
  319. data/test/language/parser.rb +455 -148
  320. data/test/language/resource.rb +535 -0
  321. data/test/language/scope.rb +451 -561
  322. data/test/language/snippets.rb +101 -111
  323. data/test/language/transportable.rb +6 -8
  324. data/test/lib/mocha.rb +19 -0
  325. data/test/lib/mocha/any_instance_method.rb +35 -0
  326. data/test/lib/mocha/auto_verify.rb +113 -0
  327. data/test/lib/mocha/central.rb +35 -0
  328. data/test/lib/mocha/class_method.rb +62 -0
  329. data/test/lib/mocha/expectation.rb +295 -0
  330. data/test/lib/mocha/expectation_error.rb +6 -0
  331. data/test/lib/mocha/infinite_range.rb +27 -0
  332. data/test/lib/mocha/inspect.rb +37 -0
  333. data/test/lib/mocha/instance_method.rb +8 -0
  334. data/test/lib/mocha/metaclass.rb +7 -0
  335. data/test/lib/mocha/mock.rb +20 -0
  336. data/test/lib/mocha/mock_methods.rb +122 -0
  337. data/test/lib/mocha/object.rb +100 -0
  338. data/test/lib/mocha/pretty_parameters.rb +28 -0
  339. data/test/lib/mocha/setup_and_teardown.rb +23 -0
  340. data/test/lib/mocha/standalone.rb +30 -0
  341. data/test/lib/mocha/test_case_adapter.rb +49 -0
  342. data/test/lib/mocha_standalone.rb +2 -0
  343. data/test/lib/puppettest.rb +294 -0
  344. data/test/lib/puppettest/certificates.rb +61 -0
  345. data/test/lib/puppettest/exetest.rb +123 -0
  346. data/test/lib/puppettest/fakes.rb +194 -0
  347. data/test/lib/puppettest/fileparsing.rb +33 -0
  348. data/test/lib/puppettest/filetesting.rb +231 -0
  349. data/test/lib/puppettest/graph.rb +41 -0
  350. data/test/lib/puppettest/parsertesting.rb +392 -0
  351. data/test/lib/puppettest/railstesting.rb +56 -0
  352. data/test/lib/puppettest/reporttesting.rb +19 -0
  353. data/test/lib/puppettest/resourcetesting.rb +73 -0
  354. data/test/lib/puppettest/servertest.rb +72 -0
  355. data/test/lib/puppettest/support.rb +8 -0
  356. data/test/lib/puppettest/support/assertions.rb +101 -0
  357. data/test/lib/puppettest/support/helpers.rb +23 -0
  358. data/test/lib/puppettest/support/resources.rb +37 -0
  359. data/test/lib/puppettest/support/utils.rb +160 -0
  360. data/test/lib/puppettest/testcase.rb +48 -0
  361. data/test/lib/rake/puppet_test_loader.rb +17 -0
  362. data/test/lib/rake/puppet_testtask.rb +17 -0
  363. data/test/lib/spec.rb +8 -0
  364. data/test/lib/spec/callback.rb +11 -0
  365. data/test/lib/spec/callback/callback_container.rb +60 -0
  366. data/test/lib/spec/callback/extensions/module.rb +24 -0
  367. data/test/lib/spec/callback/extensions/object.rb +37 -0
  368. data/test/lib/spec/deprecated.rb +3 -0
  369. data/test/lib/spec/expectations.rb +59 -0
  370. data/test/lib/spec/expectations/differs/default.rb +62 -0
  371. data/test/lib/spec/expectations/errors.rb +6 -0
  372. data/test/lib/spec/expectations/extensions.rb +3 -0
  373. data/test/lib/spec/expectations/extensions/object.rb +109 -0
  374. data/test/lib/spec/expectations/extensions/proc.rb +57 -0
  375. data/test/lib/spec/expectations/extensions/string_and_symbol.rb +17 -0
  376. data/test/lib/spec/expectations/handler.rb +47 -0
  377. data/test/lib/spec/expectations/should.rb +5 -0
  378. data/test/lib/spec/expectations/should/base.rb +64 -0
  379. data/test/lib/spec/expectations/should/change.rb +69 -0
  380. data/test/lib/spec/expectations/should/have.rb +128 -0
  381. data/test/lib/spec/expectations/should/not.rb +74 -0
  382. data/test/lib/spec/expectations/should/should.rb +81 -0
  383. data/test/lib/spec/expectations/sugar.rb +47 -0
  384. data/test/lib/spec/matchers.rb +160 -0
  385. data/test/lib/spec/matchers/be.rb +161 -0
  386. data/test/lib/spec/matchers/be_close.rb +37 -0
  387. data/test/lib/spec/matchers/change.rb +120 -0
  388. data/test/lib/spec/matchers/eql.rb +43 -0
  389. data/test/lib/spec/matchers/equal.rb +43 -0
  390. data/test/lib/spec/matchers/has.rb +44 -0
  391. data/test/lib/spec/matchers/have.rb +140 -0
  392. data/test/lib/spec/matchers/include.rb +50 -0
  393. data/test/lib/spec/matchers/match.rb +41 -0
  394. data/test/lib/spec/matchers/raise_error.rb +100 -0
  395. data/test/lib/spec/matchers/respond_to.rb +35 -0
  396. data/test/lib/spec/matchers/satisfy.rb +47 -0
  397. data/test/lib/spec/matchers/throw_symbol.rb +75 -0
  398. data/test/lib/spec/mocks.rb +232 -0
  399. data/test/lib/spec/mocks/argument_expectation.rb +132 -0
  400. data/test/lib/spec/mocks/error_generator.rb +85 -0
  401. data/test/lib/spec/mocks/errors.rb +10 -0
  402. data/test/lib/spec/mocks/extensions/object.rb +3 -0
  403. data/test/lib/spec/mocks/message_expectation.rb +231 -0
  404. data/test/lib/spec/mocks/methods.rb +40 -0
  405. data/test/lib/spec/mocks/mock.rb +26 -0
  406. data/test/lib/spec/mocks/mock_handler.rb +166 -0
  407. data/test/lib/spec/mocks/order_group.rb +29 -0
  408. data/test/lib/spec/rake/spectask.rb +173 -0
  409. data/test/lib/spec/rake/verify_rcov.rb +47 -0
  410. data/test/lib/spec/runner.rb +132 -0
  411. data/test/lib/spec/runner/backtrace_tweaker.rb +55 -0
  412. data/test/lib/spec/runner/command_line.rb +34 -0
  413. data/test/lib/spec/runner/context.rb +154 -0
  414. data/test/lib/spec/runner/context_eval.rb +142 -0
  415. data/test/lib/spec/runner/context_runner.rb +55 -0
  416. data/test/lib/spec/runner/drb_command_line.rb +21 -0
  417. data/test/lib/spec/runner/execution_context.rb +17 -0
  418. data/test/lib/spec/runner/extensions/kernel.rb +17 -0
  419. data/test/lib/spec/runner/extensions/object.rb +32 -0
  420. data/test/lib/spec/runner/formatter.rb +5 -0
  421. data/test/lib/spec/runner/formatter/base_text_formatter.rb +118 -0
  422. data/test/lib/spec/runner/formatter/html_formatter.rb +219 -0
  423. data/test/lib/spec/runner/formatter/progress_bar_formatter.rb +27 -0
  424. data/test/lib/spec/runner/formatter/rdoc_formatter.rb +22 -0
  425. data/test/lib/spec/runner/formatter/specdoc_formatter.rb +23 -0
  426. data/test/lib/spec/runner/heckle_runner.rb +71 -0
  427. data/test/lib/spec/runner/heckle_runner_win.rb +10 -0
  428. data/test/lib/spec/runner/option_parser.rb +224 -0
  429. data/test/lib/spec/runner/reporter.rb +105 -0
  430. data/test/lib/spec/runner/spec_matcher.rb +25 -0
  431. data/test/lib/spec/runner/spec_parser.rb +41 -0
  432. data/test/lib/spec/runner/spec_should_raise_handler.rb +74 -0
  433. data/test/lib/spec/runner/specification.rb +114 -0
  434. data/test/lib/spec/translator.rb +87 -0
  435. data/test/lib/spec/version.rb +30 -0
  436. data/test/lib/stubba.rb +2 -0
  437. data/test/network/authconfig.rb +72 -0
  438. data/test/network/authorization.rb +138 -0
  439. data/test/network/authstore.rb +450 -0
  440. data/test/network/client/ca.rb +38 -0
  441. data/test/{client → network/client}/client.rb +107 -24
  442. data/test/network/client/dipper.rb +35 -0
  443. data/test/network/client/master.rb +627 -0
  444. data/test/{client/pelement.rb → network/client/resource.rb} +13 -29
  445. data/test/network/client_request.rb +39 -0
  446. data/test/network/daemon.rb +71 -0
  447. data/test/{server → network/handler}/bucket.rb +103 -27
  448. data/test/{server → network/handler}/ca.rb +14 -19
  449. data/test/{server → network/handler}/fileserver.rb +443 -68
  450. data/test/network/handler/handler.rb +64 -0
  451. data/test/{server → network/handler}/logger.rb +26 -26
  452. data/test/network/handler/master.rb +352 -0
  453. data/test/network/handler/report.rb +185 -0
  454. data/test/{server/pelement.rb → network/handler/resource.rb} +25 -38
  455. data/test/{server → network/handler}/runner.rb +17 -16
  456. data/test/network/rights.rb +38 -0
  457. data/test/network/server/webrick.rb +140 -0
  458. data/test/network/xmlrpc/client.rb +68 -0
  459. data/test/network/xmlrpc/processor.rb +80 -0
  460. data/test/network/xmlrpc/server.rb +28 -0
  461. data/test/network/xmlrpc/webrick_servlet.rb +26 -0
  462. data/test/other/dsl.rb +218 -0
  463. data/test/other/events.rb +22 -15
  464. data/test/other/overrides.rb +9 -14
  465. data/test/other/pgraph.rb +289 -0
  466. data/test/other/propertychange.rb +142 -0
  467. data/test/other/provider.rb +162 -0
  468. data/test/other/puppet.rb +63 -10
  469. data/test/other/relationship.rb +74 -0
  470. data/test/other/relationships.rb +199 -123
  471. data/test/other/report.rb +152 -23
  472. data/test/other/transactions.rb +824 -78
  473. data/test/puppet/conffiles.rb +16 -11
  474. data/test/puppet/defaults.rb +7 -10
  475. data/test/puppet/{error.rb → errortest.rb} +5 -8
  476. data/test/puppet/modules.rb +58 -0
  477. data/test/puppet/tc_suidmanager.rb +107 -0
  478. data/test/rails/host.rb +177 -0
  479. data/test/rails/rails.rb +27 -0
  480. data/test/rails/railsparameter.rb +62 -0
  481. data/test/rails/railsresource.rb +100 -0
  482. data/test/ral/manager/attributes.rb +296 -0
  483. data/test/ral/manager/manager.rb +55 -0
  484. data/test/ral/manager/provider.rb +54 -0
  485. data/test/ral/manager/type.rb +837 -0
  486. data/test/ral/providers/cron/crontab.rb +346 -0
  487. data/test/ral/providers/group.rb +252 -0
  488. data/test/ral/providers/host/netinfo.rb +58 -0
  489. data/test/ral/providers/host/parsed.rb +226 -0
  490. data/test/ral/providers/mount/netinfo.rb +80 -0
  491. data/test/ral/providers/mount/parsed.rb +223 -0
  492. data/test/ral/providers/nameservice.rb +33 -0
  493. data/test/ral/providers/package.rb +253 -0
  494. data/test/ral/providers/package/apt.rb +89 -0
  495. data/test/ral/providers/package/aptitude.rb +69 -0
  496. data/test/ral/providers/package/aptrpm.rb +89 -0
  497. data/test/ral/providers/package/dpkg.rb +64 -0
  498. data/test/ral/providers/parsedfile.rb +668 -0
  499. data/test/ral/providers/parsedport.rb +233 -0
  500. data/test/ral/providers/provider.rb +423 -0
  501. data/test/{types → ral/providers}/service.rb +20 -121
  502. data/test/ral/providers/service/base.rb +75 -0
  503. data/test/ral/providers/sshkey/parsed.rb +111 -0
  504. data/test/ral/providers/user.rb +567 -0
  505. data/test/ral/providers/user/useradd.rb +250 -0
  506. data/test/ral/types/basic.rb +90 -0
  507. data/test/ral/types/component.rb +113 -0
  508. data/test/ral/types/cron.rb +480 -0
  509. data/test/{types → ral/types}/exec.rb +278 -82
  510. data/test/ral/types/file.rb +1799 -0
  511. data/test/ral/types/file/target.rb +363 -0
  512. data/test/{types → ral/types}/filebucket.rb +15 -17
  513. data/test/{types → ral/types}/fileignoresource.rb +9 -15
  514. data/test/ral/types/filesources.rb +1046 -0
  515. data/test/ral/types/group.rb +169 -0
  516. data/test/ral/types/host.rb +155 -0
  517. data/test/ral/types/mount.rb +312 -0
  518. data/test/ral/types/package.rb +85 -0
  519. data/test/ral/types/parameter.rb +172 -0
  520. data/test/ral/types/port.rb +148 -0
  521. data/test/ral/types/property.rb +343 -0
  522. data/test/ral/types/resources.rb +221 -0
  523. data/test/{types → ral/types}/schedule.rb +34 -12
  524. data/test/ral/types/service.rb +37 -0
  525. data/test/{types → ral/types}/sshkey.rb +75 -65
  526. data/test/ral/types/tidy.rb +240 -0
  527. data/test/ral/types/user.rb +493 -0
  528. data/test/{types → ral/types}/yumrepo.rb +7 -11
  529. data/test/{types → ral/types}/zone.rb +45 -45
  530. data/test/tagging/tagging.rb +17 -26
  531. data/test/util/autoload.rb +130 -0
  532. data/test/util/classgen.rb +227 -0
  533. data/test/{other → util}/config.rb +373 -113
  534. data/test/util/execution.rb +34 -0
  535. data/test/util/features.rb +94 -0
  536. data/test/util/fileparsing.rb +677 -0
  537. data/test/{other → util}/filetype.rb +9 -12
  538. data/test/util/graph.rb +108 -0
  539. data/test/{other → util}/inifile.rb +24 -11
  540. data/test/util/loadedfile.rb +106 -0
  541. data/test/{other → util}/log.rb +96 -50
  542. data/test/{other → util}/metrics.rb +7 -17
  543. data/test/util/package.rb +27 -0
  544. data/test/util/pidlock.rb +126 -0
  545. data/test/util/posixtest.rb +173 -0
  546. data/test/util/storage.rb +123 -0
  547. data/test/util/subclass_loader.rb +100 -0
  548. data/test/util/utiltest.rb +368 -0
  549. metadata +449 -169
  550. data/examples/code/classing +0 -35
  551. data/examples/code/failers/badclassnoparam +0 -10
  552. data/examples/code/failers/badclassparam +0 -10
  553. data/examples/code/failers/badcompnoparam +0 -9
  554. data/examples/code/failers/badcompparam +0 -9
  555. data/examples/code/failers/badtypeparam +0 -3
  556. data/examples/code/failers/noobjectrvalue +0 -1
  557. data/examples/code/snippets/aliastest.pp +0 -16
  558. data/examples/code/snippets/argumentdefaults +0 -14
  559. data/examples/code/snippets/casestatement.pp +0 -58
  560. data/examples/code/snippets/classheirarchy.pp +0 -15
  561. data/examples/code/snippets/classincludes.pp +0 -17
  562. data/examples/code/snippets/classpathtest +0 -11
  563. data/examples/code/snippets/componentmetaparams.pp +0 -11
  564. data/examples/code/snippets/deepclassheirarchy.pp +0 -23
  565. data/examples/code/snippets/defineoverrides.pp +0 -17
  566. data/examples/code/snippets/dirchmod +0 -19
  567. data/examples/code/snippets/emptyclass.pp +0 -9
  568. data/examples/code/snippets/emptyexec.pp +0 -3
  569. data/examples/code/snippets/failmissingexecpath.pp +0 -13
  570. data/examples/code/snippets/falsevalues.pp +0 -3
  571. data/examples/code/snippets/filecreate +0 -11
  572. data/examples/code/snippets/implicititeration +0 -15
  573. data/examples/code/snippets/multipleinstances +0 -7
  574. data/examples/code/snippets/namevartest +0 -9
  575. data/examples/code/snippets/scopetest +0 -13
  576. data/examples/code/snippets/selectorvalues.pp +0 -42
  577. data/examples/code/snippets/simpledefaults +0 -5
  578. data/examples/code/snippets/simpleselector +0 -38
  579. data/examples/code/snippets/singleary.pp +0 -19
  580. data/examples/code/snippets/singlequote.pp +0 -11
  581. data/examples/code/snippets/singleselector.pp +0 -22
  582. data/examples/code/snippets/tag.pp +0 -9
  583. data/examples/code/snippets/tagged.pp +0 -35
  584. data/lib/puppet/client.rb +0 -177
  585. data/lib/puppet/client/ca.rb +0 -21
  586. data/lib/puppet/client/dipper.rb +0 -76
  587. data/lib/puppet/client/file.rb +0 -20
  588. data/lib/puppet/client/log.rb +0 -17
  589. data/lib/puppet/client/master.rb +0 -531
  590. data/lib/puppet/client/runner.rb +0 -17
  591. data/lib/puppet/client/status.rb +0 -7
  592. data/lib/puppet/event-loop.rb +0 -1
  593. data/lib/puppet/filetype.rb +0 -308
  594. data/lib/puppet/inifile.rb +0 -201
  595. data/lib/puppet/log.rb +0 -524
  596. data/lib/puppet/metric.rb +0 -132
  597. data/lib/puppet/networkclient.rb +0 -175
  598. data/lib/puppet/parsedfile.rb +0 -58
  599. data/lib/puppet/parser/ast/classdef.rb +0 -79
  600. data/lib/puppet/parser/ast/compdef.rb +0 -75
  601. data/lib/puppet/parser/ast/nodedef.rb +0 -73
  602. data/lib/puppet/parser/ast/objectdef.rb +0 -284
  603. data/lib/puppet/parser/ast/objectref.rb +0 -77
  604. data/lib/puppet/rails/database.rb +0 -40
  605. data/lib/puppet/rails/rails_object.rb +0 -42
  606. data/lib/puppet/rails/rails_parameter.rb +0 -5
  607. data/lib/puppet/server.rb +0 -196
  608. data/lib/puppet/server/authconfig.rb +0 -177
  609. data/lib/puppet/server/authstore.rb +0 -226
  610. data/lib/puppet/server/filebucket.rb +0 -155
  611. data/lib/puppet/server/pelement.rb +0 -188
  612. data/lib/puppet/server/report.rb +0 -184
  613. data/lib/puppet/server/rights.rb +0 -78
  614. data/lib/puppet/server/servlet.rb +0 -274
  615. data/lib/puppet/statechange.rb +0 -129
  616. data/lib/puppet/storage.rb +0 -98
  617. data/lib/puppet/type/nameservice.rb +0 -264
  618. data/lib/puppet/type/nameservice/netinfo.rb +0 -232
  619. data/lib/puppet/type/nameservice/objectadd.rb +0 -146
  620. data/lib/puppet/type/nameservice/posix.rb +0 -12
  621. data/lib/puppet/type/nameservice/pw.rb +0 -107
  622. data/lib/puppet/type/package/apple.rb +0 -41
  623. data/lib/puppet/type/package/apt.rb +0 -107
  624. data/lib/puppet/type/package/blastwave.rb +0 -136
  625. data/lib/puppet/type/package/darwinport.rb +0 -97
  626. data/lib/puppet/type/package/dpkg.rb +0 -113
  627. data/lib/puppet/type/package/freebsd.rb +0 -19
  628. data/lib/puppet/type/package/gem.rb +0 -119
  629. data/lib/puppet/type/package/openbsd.rb +0 -112
  630. data/lib/puppet/type/package/ports.rb +0 -103
  631. data/lib/puppet/type/package/rpm.rb +0 -121
  632. data/lib/puppet/type/package/sun.rb +0 -174
  633. data/lib/puppet/type/package/sunfreeware.rb +0 -7
  634. data/lib/puppet/type/package/yum.rb +0 -52
  635. data/lib/puppet/type/parsedtype/host.rb +0 -144
  636. data/lib/puppet/type/parsedtype/mount.rb +0 -271
  637. data/lib/puppet/type/parsedtype/port.rb +0 -261
  638. data/lib/puppet/type/parsedtype/sshkey.rb +0 -123
  639. data/lib/puppet/type/service/base.rb +0 -12
  640. data/lib/puppet/type/service/debian.rb +0 -46
  641. data/lib/puppet/type/service/redhat.rb +0 -38
  642. data/lib/puppet/type/state.rb +0 -393
  643. data/lib/puppet/type/symlink.rb +0 -186
  644. data/test/client/master.rb +0 -207
  645. data/test/language/rails.rb +0 -105
  646. data/test/other/parsedfile.rb +0 -58
  647. data/test/other/storage.rb +0 -100
  648. data/test/puppet/utiltest.rb +0 -299
  649. data/test/puppettest.rb +0 -1170
  650. data/test/server/authconfig.rb +0 -56
  651. data/test/server/authstore.rb +0 -218
  652. data/test/server/master.rb +0 -201
  653. data/test/server/report.rb +0 -93
  654. data/test/server/rights.rb +0 -41
  655. data/test/server/server.rb +0 -152
  656. data/test/test +0 -61
  657. data/test/types/basic.rb +0 -117
  658. data/test/types/component.rb +0 -298
  659. data/test/types/cron.rb +0 -718
  660. data/test/types/file.rb +0 -1314
  661. data/test/types/filesources.rb +0 -590
  662. data/test/types/group.rb +0 -323
  663. data/test/types/host.rb +0 -186
  664. data/test/types/mount.rb +0 -294
  665. data/test/types/package.rb +0 -538
  666. data/test/types/parameter.rb +0 -107
  667. data/test/types/port.rb +0 -201
  668. data/test/types/query.rb +0 -101
  669. data/test/types/state.rb +0 -92
  670. data/test/types/symlink.rb +0 -120
  671. data/test/types/tidy.rb +0 -102
  672. data/test/types/type.rb +0 -469
  673. data/test/types/user.rb +0 -563
@@ -5,6 +5,7 @@
5
5
  require 'puppet'
6
6
  require 'puppet/type'
7
7
  require 'puppet/transaction'
8
+ require 'puppet/pgraph'
8
9
 
9
10
  module Puppet
10
11
  newtype(:component) do
@@ -22,42 +23,6 @@ module Puppet
22
23
  defaultto "component"
23
24
  end
24
25
 
25
- # topo sort functions
26
- def self.sort(objects)
27
- list = []
28
- tmplist = {}
29
-
30
- objects.each { |obj|
31
- self.recurse(obj, tmplist, list)
32
- }
33
-
34
- return list.flatten
35
- end
36
-
37
- # FIXME this method assumes that dependencies themselves
38
- # are never components
39
- def self.recurse(obj, inlist, list)
40
- if inlist.include?(obj.object_id)
41
- return
42
- end
43
- inlist[obj.object_id] = true
44
- begin
45
- obj.eachdependency { |req|
46
- self.recurse(req, inlist, list)
47
- }
48
- rescue Puppet::Error => detail
49
- raise Puppet::Error, "%s: %s" % [obj.path, detail]
50
- end
51
-
52
- if obj.is_a? self
53
- obj.each { |child|
54
- self.recurse(child, inlist, list)
55
- }
56
- else
57
- list << obj
58
- end
59
- end
60
-
61
26
  # Remove a child from the component.
62
27
  def delete(child)
63
28
  if @children.include?(child)
@@ -73,6 +38,16 @@ module Puppet
73
38
  @children.each { |child| yield child }
74
39
  end
75
40
 
41
+ # flatten all children, sort them, and evaluate them in order
42
+ # this is only called on one component over the whole system
43
+ # this also won't work with scheduling, but eh
44
+ def evaluate
45
+ self.finalize unless self.finalized?
46
+ transaction = Puppet::Transaction.new(self)
47
+ transaction.component = self
48
+ return transaction
49
+ end
50
+
76
51
  # Do all of the polishing off, mostly doing autorequires and making
77
52
  # dependencies. This will get run once on the top-level component,
78
53
  # and it will do everything necessary.
@@ -84,14 +59,13 @@ module Puppet
84
59
  self.delve do |object|
85
60
  # Make sure we don't get into loops
86
61
  if started.has_key?(object)
87
- debug "Already finished %s" % object.name
62
+ debug "Already finished %s" % object.title
88
63
  next
89
64
  else
90
65
  started[object] = true
91
66
  end
92
67
  unless finished.has_key?(object)
93
68
  object.finish
94
- object.builddepends
95
69
  finished[object] = true
96
70
  end
97
71
  end
@@ -106,39 +80,43 @@ module Puppet
106
80
  return false
107
81
  end
108
82
  end
109
-
110
- # Return a flattened array containing all of the children
111
- # and all child components' children, sorted in order of dependencies.
112
- def flatten
113
- self.class.sort(@children).flatten
114
- end
115
83
 
116
84
  # Initialize a new component
117
85
  def initialize(args)
118
86
  @children = []
119
87
  super(args)
120
88
  end
121
-
122
- # flatten all children, sort them, and evaluate them in order
123
- # this is only called on one component over the whole system
124
- # this also won't work with scheduling, but eh
125
- def evaluate
126
- self.finalize unless self.finalized?
127
- transaction = Puppet::Transaction.new(self.flatten)
128
- transaction.component = self
129
- return transaction
89
+
90
+ # Component paths are special because they function as containers.
91
+ def pathbuilder
92
+ tmp = []
93
+ if defined? @parent and @parent
94
+ tmp += [@parent.pathbuilder, self.title]
95
+ else
96
+ # The top-level name is always main[top], so we don't bother with
97
+ # that.
98
+ if self.title == "main[top]"
99
+ tmp << "" # This empty field results in "//" in the path
100
+ else
101
+ tmp << self.title
102
+ end
103
+ end
104
+
105
+ tmp
130
106
  end
131
107
 
132
- def name
133
- #return self[:name]
134
- unless defined? @name
135
- if self[:type] == self[:name] or self[:name] =~ /--\d+$/
136
- @name = self[:type]
137
- else
138
- @name = "%s[%s]" % [self[:type],self[:name]]
108
+ # We have a different way of setting the title
109
+ def title
110
+ unless defined? @title
111
+ if self[:type] == self[:name] # this is the case for classes
112
+ @title = self[:type]
113
+ elsif self[:name] =~ /\[.+\]/ # most components already have ref info in the name
114
+ @title = self[:name]
115
+ else # else, set it up
116
+ @title = "%s[%s]" % [self[:type].capitalize, self[:name]]
139
117
  end
140
118
  end
141
- return @name
119
+ return @title
142
120
  end
143
121
 
144
122
  def refresh
@@ -149,11 +127,33 @@ module Puppet
149
127
  end
150
128
  }
151
129
  end
130
+
131
+ # Convert to a graph object with all of the container info.
132
+ def to_graph
133
+ graph = Puppet::PGraph.new
134
+
135
+ delver = proc do |obj|
136
+ obj.each do |child|
137
+ if child.is_a?(Puppet::Type)
138
+ graph.add_edge!(obj, child)
139
+ delver.call(child)
140
+ end
141
+ end
142
+ end
143
+
144
+ delver.call(self)
145
+
146
+ return graph
147
+ end
152
148
 
153
149
  def to_s
154
- return "component(%s)" % self.name
150
+ if self.title =~ /\[/
151
+ return self.title
152
+ else
153
+ return "component(%s)" % self.title
154
+ end
155
155
  end
156
156
  end
157
157
  end
158
158
 
159
- # $Id: component.rb 1246 2006-06-08 20:38:44Z luke $
159
+ # $Id: component.rb 2052 2007-01-05 17:09:04Z luke $
@@ -1,813 +1,397 @@
1
1
  require 'etc'
2
2
  require 'facter'
3
- require 'puppet/type/state'
4
- require 'puppet/filetype'
3
+ require 'puppet/type/property'
4
+ require 'puppet/util/filetype'
5
5
  require 'puppet/type/parsedtype'
6
6
 
7
- module Puppet
8
- # Model the actual cron jobs. Supports all of the normal cron job fields
9
- # as parameters, with the 'command' as the single state. Also requires a
10
- # completely symbolic 'name' paremeter, which gets written to the file
11
- # and is used to manage the job.
12
- newtype(:cron) do
13
-
14
- # A base class for all of the Cron parameters, since they all have
15
- # similar argument checking going on. We're stealing the base class
16
- # from parsedtype, and we should probably subclass Cron from there,
17
- # but it was just too annoying to do.
18
- class CronParam < Puppet::State::ParsedParam
19
- class << self
20
- attr_accessor :boundaries, :default
21
- end
22
-
23
- # We have to override the parent method, because we consume the entire
24
- # "should" array
25
- def insync?
26
- if defined? @should and @should
27
- self.is_to_s == self.should_to_s
28
- else
29
- true
30
- end
31
- end
7
+ Puppet::Type.newtype(:cron) do
8
+ @doc = "Installs and manages cron jobs. All fields except the command
9
+ and the user are optional, although specifying no periodic
10
+ fields would result in the command being executed every
11
+ minute. While the name of the cron job is not part of the actual
12
+ job, it is used by Puppet to store and retrieve it.
13
+
14
+ If you specify a cron job that matches an existing job in every way
15
+ except name, then the jobs will be considered equivalent and the
16
+ new name will be permanently associated with that job. Once this
17
+ association is made and synced to disk, you can then manage the job
18
+ normally (e.g., change the schedule of the job).
19
+
20
+ Example::
21
+
22
+ cron { logrotate:
23
+ command => \"/usr/sbin/logrotate\",
24
+ user => root,
25
+ hour => 2,
26
+ minute => 0
27
+ }
28
+ "
29
+ ensurable
30
+
31
+ # A base class for all of the Cron parameters, since they all have
32
+ # similar argument checking going on. We're stealing the base class
33
+ # from parsedtype, and we should probably subclass Cron from there,
34
+ # but it was just too annoying to do.
35
+ class CronParam < Puppet::Property
36
+ class << self
37
+ attr_accessor :boundaries, :default
38
+ end
32
39
 
33
- # A method used to do parameter input handling. Converts integers
34
- # in string form to actual integers, and returns the value if it's
35
- # an integer or false if it's just a normal string.
36
- def numfix(num)
37
- if num =~ /^\d+$/
38
- return num.to_i
39
- elsif num.is_a?(Integer)
40
- return num
41
- else
42
- return false
43
- end
40
+ # We have to override the parent method, because we consume the entire
41
+ # "should" array
42
+ def insync?
43
+ if defined? @should and @should
44
+ self.is_to_s == self.should_to_s
45
+ else
46
+ true
44
47
  end
48
+ end
45
49
 
46
- # Verify that a number is within the specified limits. Return the
47
- # number if it is, or false if it is not.
48
- def limitcheck(num, lower, upper)
49
- if num >= lower and num <= upper
50
- return num
51
- else
52
- return false
53
- end
50
+ # A method used to do parameter input handling. Converts integers
51
+ # in string form to actual integers, and returns the value if it's
52
+ # an integer or false if it's just a normal string.
53
+ def numfix(num)
54
+ if num =~ /^\d+$/
55
+ return num.to_i
56
+ elsif num.is_a?(Integer)
57
+ return num
58
+ else
59
+ return false
54
60
  end
61
+ end
55
62
 
56
- # Verify that a value falls within the specified array. Does case
57
- # insensitive matching, and supports matching either the entire word
58
- # or the first three letters of the word.
59
- def alphacheck(value, ary)
60
- tmp = value.downcase
61
-
62
- # If they specified a shortened version of the name, then see
63
- # if we can lengthen it (e.g., mon => monday).
64
- if tmp.length == 3
65
- ary.each_with_index { |name, index|
66
- if name =~ /#{tmp}/i
67
- return index
68
- end
69
- }
70
- else
71
- if ary.include?(tmp)
72
- return ary.index(tmp)
73
- end
74
- end
75
-
63
+ # Verify that a number is within the specified limits. Return the
64
+ # number if it is, or false if it is not.
65
+ def limitcheck(num, lower, upper)
66
+ if num >= lower and num <= upper
67
+ return num
68
+ else
76
69
  return false
77
70
  end
71
+ end
78
72
 
79
- def should_to_s
80
- if @should
81
- unless @should.is_a?(Array)
82
- fail "wtf?"
83
- end
84
-
85
- if self.name == :command or @should[0].is_a? Symbol
86
- @should[0]
87
- else
88
- @should.join(",")
73
+ # Verify that a value falls within the specified array. Does case
74
+ # insensitive matching, and supports matching either the entire word
75
+ # or the first three letters of the word.
76
+ def alphacheck(value, ary)
77
+ tmp = value.downcase
78
+
79
+ # If they specified a shortened version of the name, then see
80
+ # if we can lengthen it (e.g., mon => monday).
81
+ if tmp.length == 3
82
+ ary.each_with_index { |name, index|
83
+ if name =~ /#{tmp}/i
84
+ return index
89
85
  end
90
- else
91
- nil
86
+ }
87
+ else
88
+ if ary.include?(tmp)
89
+ return ary.index(tmp)
92
90
  end
93
91
  end
94
92
 
95
- def is_to_s
96
- if @is
97
- unless @is.is_a?(Array)
98
- return @is
99
- end
93
+ return false
94
+ end
100
95
 
101
- if self.name == :command or @is[0].is_a? Symbol
102
- @is[0]
103
- else
104
- @is.join(",")
105
- end
96
+ def should_to_s
97
+ if @should
98
+ if self.name == :command or @should[0].is_a? Symbol
99
+ @should[0]
106
100
  else
107
- nil
101
+ @should.join(",")
108
102
  end
103
+ else
104
+ nil
109
105
  end
106
+ end
110
107
 
111
- # The method that does all of the actual parameter value
112
- # checking; called by all of the +param<name>=+ methods.
113
- # Requires the value, type, and bounds, and optionally supports
114
- # a boolean of whether to do alpha checking, and if so requires
115
- # the ary against which to do the checking.
116
- munge do |value|
117
- # Support 'absent' as a value, so that they can remove
118
- # a value
119
- if value == "absent" or value == :absent
120
- return :absent
121
- end
122
-
123
- # Allow the */2 syntax
124
- if value =~ /^\*\/[0-9]+$/
125
- return value
126
- end
127
-
128
- # Allow ranges
129
- if value =~ /^[0-9]+-[0-9]+$/
130
- return value
131
- end
132
-
133
- if value == "*"
134
- return value
135
- end
136
-
137
- return value unless self.class.boundaries
138
- lower, upper = self.class.boundaries
139
- retval = nil
140
- if num = numfix(value)
141
- retval = limitcheck(num, lower, upper)
142
- elsif respond_to?(:alpha)
143
- # If it has an alpha method defined, then we check
144
- # to see if our value is in that list and if so we turn
145
- # it into a number
146
- retval = alphacheck(value, alpha())
147
- end
148
-
149
- if retval
150
- return retval.to_s
151
- else
152
- self.fail "%s is not a valid %s" %
153
- [value, self.class.name]
154
- end
108
+ def is=(val)
109
+ if val.is_a?(Array)
110
+ @is = val
111
+ else
112
+ @is = [val]
155
113
  end
156
114
  end
157
115
 
116
+ def is_to_s
117
+ if @is
118
+ unless @is.is_a?(Array)
119
+ return @is
120
+ end
158
121
 
159
- # Override 'newstate' so that all states default to having the
160
- # correct parent type
161
- def self.newstate(name, parent = nil, &block)
162
- parent ||= Puppet::State::CronParam
163
- super(name, parent, &block)
164
- end
165
-
166
- # Somewhat uniquely, this state does not actually change anything -- it
167
- # just calls +@parent.sync+, which writes out the whole cron tab for
168
- # the user in question. There is no real way to change individual cron
169
- # jobs without rewriting the entire cron file.
170
- #
171
- # Note that this means that managing many cron jobs for a given user
172
- # could currently result in multiple write sessions for that user.
173
- newstate(:command, CronParam) do
174
- desc "The command to execute in the cron job. The environment
175
- provided to the command varies by local system rules, and it is
176
- best to always provide a fully qualified command. The user's
177
- profile is not sourced when the command is run, so if the
178
- user's environment is desired it should be sourced manually.
179
-
180
- All cron parameters support ``absent`` as a value; this will
181
- remove any existing values for that field."
182
-
183
- def should
184
- if @should
185
- if @should.is_a? Array
186
- @should[0]
187
- else
188
- devfail "command is not an array"
189
- end
122
+ if self.name == :command or @is[0].is_a? Symbol
123
+ @is[0]
190
124
  else
191
- nil
125
+ @is.join(",")
192
126
  end
127
+ else
128
+ nil
193
129
  end
194
130
  end
195
131
 
196
- newstate(:special, Puppet::State::ParsedParam) do
197
- desc "Special schedules only supported on FreeBSD."
198
-
199
- def specials
200
- %w{reboot yearly annually monthly weekly daily midnight hourly}
201
- end
202
-
203
- validate do |value|
204
- unless specials().include?(value)
205
- raise ArgumentError, "Invalid special schedule %s" %
206
- value.inspect
207
- end
132
+ def should
133
+ if @should and @should[0] == :absent
134
+ :absent
135
+ else
136
+ @should
208
137
  end
209
138
  end
210
139
 
211
- newstate(:minute, CronParam) do
212
- self.boundaries = [0, 59]
213
- desc "The minute at which to run the cron job.
214
- Optional; if specified, must be between 0 and 59, inclusive."
215
- end
216
-
217
- newstate(:hour, CronParam) do
218
- self.boundaries = [0, 23]
219
- desc "The hour at which to run the cron job. Optional;
220
- if specified, must be between 0 and 23, inclusive."
140
+ def should=(ary)
141
+ super
142
+ @should.flatten!
221
143
  end
222
144
 
223
- newstate(:weekday, CronParam) do
224
- def alpha
225
- %w{sunday monday tuesday wednesday thursday friday saturday}
145
+ # The method that does all of the actual parameter value
146
+ # checking; called by all of the +param<name>=+ methods.
147
+ # Requires the value, type, and bounds, and optionally supports
148
+ # a boolean of whether to do alpha checking, and if so requires
149
+ # the ary against which to do the checking.
150
+ munge do |value|
151
+ # Support 'absent' as a value, so that they can remove
152
+ # a value
153
+ if value == "absent" or value == :absent
154
+ return :absent
226
155
  end
227
- self.boundaries = [0, 6]
228
- desc "The weekday on which to run the command.
229
- Optional; if specified, must be between 0 and 6, inclusive, with
230
- 0 being Sunday, or must be the name of the day (e.g., Tuesday)."
231
- end
232
156
 
233
- newstate(:month, CronParam) do
234
- def alpha
235
- %w{january february march april may june july
236
- august september october november december}
157
+ # Allow the */2 syntax
158
+ if value =~ /^\*\/[0-9]+$/
159
+ return value
237
160
  end
238
- self.boundaries = [1, 12]
239
- desc "The month of the year. Optional; if specified
240
- must be between 1 and 12 or the month name (e.g., December)."
241
- end
242
-
243
- newstate(:monthday, CronParam) do
244
- self.boundaries = [1, 31]
245
- desc "The day of the month on which to run the
246
- command. Optional; if specified, must be between 1 and 31."
247
- end
248
161
 
249
- newstate(:environment, Puppet::State::ParsedParam) do
250
- desc "Any environment settings associated with this cron job. They
251
- will be stored between the header and the job in the crontab. There
252
- can be no guarantees that other, earlier settings will not also
253
- affect a given cron job.
254
-
255
- Also, Puppet cannot automatically determine whether an existing,
256
- unmanaged environment setting is associated with a given cron
257
- job. If you already have cron jobs with environment settings,
258
- then Puppet will keep those settings in the same place in the file,
259
- but will not associate them with a specific job."
260
-
261
- validate do |value|
262
- unless value =~ /^\s*(\w+)\s*=\s*(.+)\s*$/
263
- raise ArgumentError, "Invalid environment setting %s" %
264
- value.inspect
265
- end
162
+ # Allow ranges
163
+ if value =~ /^[0-9]+-[0-9]+$/
164
+ return value
266
165
  end
267
166
 
268
- def insync?
269
- if @is.is_a? Array
270
- return @is.sort == @should.sort
271
- else
272
- return @is == @should[0]
273
- end
167
+ if value == "*"
168
+ return value
274
169
  end
275
170
 
276
- def should
277
- @should
171
+ return value unless self.class.boundaries
172
+ lower, upper = self.class.boundaries
173
+ retval = nil
174
+ if num = numfix(value)
175
+ retval = limitcheck(num, lower, upper)
176
+ elsif respond_to?(:alpha)
177
+ # If it has an alpha method defined, then we check
178
+ # to see if our value is in that list and if so we turn
179
+ # it into a number
180
+ retval = alphacheck(value, alpha())
278
181
  end
279
- end
280
182
 
281
- newparam(:name) do
282
- desc "The symbolic name of the cron job. This name
283
- is used for human reference only and is generated automatically
284
- for cron jobs found on the system. This generally won't
285
- matter, as Puppet will do its best to match existing cron jobs
286
- against specified jobs (and Puppet adds a comment to cron jobs it
287
- adds), but it is at least possible that converting from
288
- unmanaged jobs to managed jobs might require manual
289
- intervention.
290
-
291
- The names can only have alphanumeric characters plus the '-'
292
- character."
293
-
294
- isnamevar
295
-
296
- validate do |value|
297
- unless value =~ /^[-\w]+$/
298
- raise ArgumentError, "Invalid name format '%s'" % value
299
- end
183
+ if retval
184
+ return retval.to_s
185
+ else
186
+ self.fail "%s is not a valid %s" %
187
+ [value, self.class.name]
300
188
  end
301
189
  end
190
+ end
302
191
 
303
- newparam(:user) do
304
- desc "The user to run the command as. This user must
305
- be allowed to run cron jobs, which is not currently checked by
306
- Puppet.
307
-
308
- The user defaults to whomever Puppet is running as."
309
-
310
- defaultto { ENV["USER"] }
311
-
312
- def value=(value)
313
- super
192
+ # Somewhat uniquely, this property does not actually change anything -- it
193
+ # just calls +@parent.sync+, which writes out the whole cron tab for
194
+ # the user in question. There is no real way to change individual cron
195
+ # jobs without rewriting the entire cron file.
196
+ #
197
+ # Note that this means that managing many cron jobs for a given user
198
+ # could currently result in multiple write sessions for that user.
199
+ newproperty(:command, :parent => CronParam) do
200
+ desc "The command to execute in the cron job. The environment
201
+ provided to the command varies by local system rules, and it is
202
+ best to always provide a fully qualified command. The user's
203
+ profile is not sourced when the command is run, so if the
204
+ user's environment is desired it should be sourced manually.
205
+
206
+ All cron parameters support ``absent`` as a value; this will
207
+ remove any existing values for that field."
314
208
 
315
- # Make sure the user is not an array
316
- if @value.is_a? Array
317
- @value = @value[0]
318
- end
209
+ def is
210
+ if @is
211
+ @is[0]
212
+ else
213
+ nil
319
214
  end
320
215
  end
321
216
 
322
- @doc = "Installs and manages cron jobs. All fields except the command
323
- and the user are optional, although specifying no periodic
324
- fields would result in the command being executed every
325
- minute. While the name of the cron job is not part of the actual
326
- job, it is used by Puppet to store and retrieve it.
327
-
328
- If you specify a cron job that matches an existing job in every way
329
- except name, then the jobs will be considered equivalent and the
330
- new name will be permanently associated with that job. Once this
331
- association is made and synced to disk, you can then manage the job
332
- normally (e.g., change the schedule of the job).
333
-
334
- Example:
335
-
336
- cron { logrotate:
337
- command => \"/usr/sbin/logrotate\",
338
- user => root,
339
- hour => 2,
340
- minute => 0
341
- }
342
- "
343
-
344
- @instances = {}
345
- @tabs = {}
346
-
347
- class << self
348
- attr_accessor :filetype
349
-
350
- def cronobj(name)
351
- if defined? @tabs
352
- return @tabs[name]
217
+ def should
218
+ if @should
219
+ if @should.is_a? Array
220
+ @should[0]
353
221
  else
354
- return nil
222
+ devfail "command is not an array"
355
223
  end
356
- end
357
- end
358
-
359
- attr_accessor :uid
360
-
361
- # In addition to removing the instances in @objects, Cron has to remove
362
- # per-user cron tab information.
363
- def self.clear
364
- @instances = {}
365
- @tabs = {}
366
- super
367
- end
368
-
369
- def self.defaulttype
370
- case Facter["operatingsystem"].value
371
- when "Solaris":
372
- return Puppet::FileType.filetype(:suntab)
373
224
  else
374
- return Puppet::FileType.filetype(:crontab)
225
+ nil
375
226
  end
376
227
  end
228
+ end
377
229
 
378
- self.filetype = self.defaulttype()
379
-
380
- # Override the default Puppet::Type method, because instances
381
- # also need to be deleted from the @instances hash
382
- def self.delete(child)
383
- if @instances.include?(child[:user])
384
- if @instances[child[:user]].include?(child)
385
- @instances[child[:user]].delete(child)
386
- end
387
- end
388
- super
389
- end
230
+ newproperty(:special) do
231
+ desc "Special schedules only supported on FreeBSD."
390
232
 
391
- # Return the fields found in the cron tab.
392
- def self.fields
393
- return [:minute, :hour, :monthday, :month, :weekday, :command]
233
+ def specials
234
+ %w{reboot yearly annually monthly weekly daily midnight hourly}
394
235
  end
395
236
 
396
- # Convert our hash to an object
397
- def self.hash2obj(hash)
398
- obj = nil
399
- namevar = self.namevar
400
- unless hash.include?(namevar) and hash[namevar]
401
- Puppet.info "Autogenerating name for %s" % hash[:command]
402
- hash[:name] = "autocron-%s" % hash.object_id
237
+ validate do |value|
238
+ unless specials().include?(value)
239
+ raise ArgumentError, "Invalid special schedule %s" %
240
+ value.inspect
403
241
  end
404
-
405
- unless hash.include?(:command)
406
- raise Puppet::DevError, "No command for %s" % name
407
- end
408
- # if the cron already exists with that name...
409
- if obj = (self[hash[:name]] || match(hash))
410
- # Mark the cron job as present
411
- obj.is = [:ensure, :present]
412
-
413
- # Mark all of the values appropriately
414
- hash.each { |param, value|
415
- if state = obj.state(param)
416
- state.is = value
417
- elsif val = obj[param]
418
- obj[param] = val
419
- else
420
- # There is a value on disk, but it should go away
421
- obj.is = [param, value]
422
- obj[param] = :absent
423
- end
424
- }
425
- else
426
- # create a new cron job, since no existing one
427
- # seems to match
428
- obj = self.create(
429
- :name => hash[namevar]
430
- )
431
-
432
- obj.is = [:ensure, :present]
433
-
434
- obj.notice "created"
435
-
436
- hash.delete(namevar)
437
- hash.each { |param, value|
438
- obj.is = [param, value]
439
- }
440
- end
441
-
442
- instance(obj)
443
242
  end
243
+ end
444
244
 
445
- # Return the header placed at the top of each generated file, warning
446
- # users that modifying this file manually is probably a bad idea.
447
- def self.header
448
- %{# HEADER This file was autogenerated at #{Time.now} by puppet. While it
449
- # HEADER can still be managed manually, it is definitely not recommended.
450
- # HEADER Note particularly that the comments starting with 'Puppet Name' should
451
- # HEADER not be deleted, as doing so could cause duplicate cron jobs.\n}
452
- end
245
+ newproperty(:minute, :parent => CronParam) do
246
+ self.boundaries = [0, 59]
247
+ desc "The minute at which to run the cron job.
248
+ Optional; if specified, must be between 0 and 59, inclusive."
249
+ end
453
250
 
454
- def self.instance(obj)
455
- user = obj[:user]
456
- unless @instances.include?(user)
457
- @instances[user] = []
458
- end
251
+ newproperty(:hour, :parent => CronParam) do
252
+ self.boundaries = [0, 23]
253
+ desc "The hour at which to run the cron job. Optional;
254
+ if specified, must be between 0 and 23, inclusive."
255
+ end
459
256
 
460
- @instances[user] << obj
257
+ newproperty(:weekday, :parent => CronParam) do
258
+ def alpha
259
+ %w{sunday monday tuesday wednesday thursday friday saturday}
461
260
  end
261
+ self.boundaries = [0, 6]
262
+ desc "The weekday on which to run the command.
263
+ Optional; if specified, must be between 0 and 6, inclusive, with
264
+ 0 being Sunday, or must be the name of the day (e.g., Tuesday)."
265
+ end
462
266
 
463
- def self.list
464
- # Look for cron jobs for each user
465
- Puppet::Type.type(:user).list.each { |user|
466
- self.retrieve(user.name)
467
- }
468
-
469
- self.collect { |c| c }
267
+ newproperty(:month, :parent => CronParam) do
268
+ def alpha
269
+ %w{january february march april may june july
270
+ august september october november december}
470
271
  end
272
+ self.boundaries = [1, 12]
273
+ desc "The month of the year. Optional; if specified
274
+ must be between 1 and 12 or the month name (e.g., December)."
275
+ end
471
276
 
472
- # See if we can match the hash against an existing cron job.
473
- def self.match(hash)
474
- self.find_all { |obj|
475
- obj[:user] == hash[:user] and obj.value(:command) == hash[:command][0]
476
- }.each do |obj|
477
- # we now have a cron job whose command exactly matches
478
- # let's see if the other fields match
479
-
480
- # First check the @special stuff
481
- if hash[:special]
482
- next unless obj.value(:special) == hash[:special]
483
- end
484
-
485
- # Then the normal fields.
486
- matched = true
487
- fields().each do |field|
488
- next if field == :command
489
- if hash[field] and ! obj.value(field)
490
- #Puppet.info "Cron is missing %s: %s and %s" %
491
- # [field, hash[field].inspect, obj.value(field).inspect]
492
- matched = false
493
- break
494
- end
277
+ newproperty(:monthday, :parent => CronParam) do
278
+ self.boundaries = [1, 31]
279
+ desc "The day of the month on which to run the
280
+ command. Optional; if specified, must be between 1 and 31."
281
+ end
495
282
 
496
- if ! hash[field] and obj.value(field)
497
- #Puppet.info "Hash is missing %s: %s and %s" %
498
- # [field, obj.value(field).inspect, hash[field].inspect]
499
- matched = false
500
- break
501
- end
283
+ newproperty(:environment) do
284
+ desc "Any environment settings associated with this cron job. They
285
+ will be stored between the header and the job in the crontab. There
286
+ can be no guarantees that other, earlier settings will not also
287
+ affect a given cron job.
288
+
289
+ Also, Puppet cannot automatically determine whether an existing,
290
+ unmanaged environment setting is associated with a given cron
291
+ job. If you already have cron jobs with environment settings,
292
+ then Puppet will keep those settings in the same place in the file,
293
+ but will not associate them with a specific job.
294
+
295
+ Settings should be specified exactly as they should appear in
296
+ the crontab, e.g., ``PATH=/bin:/usr/bin:/usr/sbin``."
502
297
 
503
- # FIXME It'd be great if I could somehow reuse how the
504
- # fields are turned into text, but....
505
- next if (hash[field] == [:absent] and obj.value(field) == "*")
506
- next if (hash[field].join(",") == obj.value(field))
507
- #Puppet.info "Did not match %s: %s vs %s" %
508
- # [field, obj.value(field).inspect, hash[field].inspect]
509
- matched = false
510
- break
511
- end
512
- next unless matched
513
- return obj
298
+ validate do |value|
299
+ unless value =~ /^\s*(\w+)\s*=\s*(.+)\s*$/
300
+ raise ArgumentError, "Invalid environment setting %s" %
301
+ value.inspect
514
302
  end
515
-
516
- return false
517
303
  end
518
304
 
519
- # Parse a user's cron job into individual cron objects.
520
- #
521
- # Autogenerates names for any jobs that don't already have one; these
522
- # names will get written back to the file.
523
- #
524
- # This method also stores existing comments, and it stores all cron
525
- # jobs in order, mostly so that comments are retained in the order
526
- # they were written and in proximity to the same jobs.
527
- def self.parse(user, text)
528
- count = 0
529
- hash = {}
530
-
531
- envs = []
532
- text.chomp.split("\n").each { |line|
533
- case line
534
- when /^# Puppet Name: (.+)$/
535
- hash[:name] = $1
536
- next
537
- when /^#/:
538
- # add other comments to the list as they are
539
- @instances[user] << line
540
- next
541
- when /^\s*(\w+)\s*=\s*(.+)\s*$/:
542
- # Match env settings.
543
- if hash[:name]
544
- envs << line
545
- else
546
- @instances[user] << line
547
- end
548
- next
549
- when /^@(\w+)\s+(.+)/ # FreeBSD special cron crap
550
- fields().each do |field|
551
- next if field == :command
552
- hash[field] = :absent
553
- end
554
- hash[:special] = $1
555
- hash[:command] = $2
556
- else
557
- if match = /^(\S+) (\S+) (\S+) (\S+) (\S+) (.+)$/.match(line)
558
- fields().zip(match.captures).each { |param, value|
559
- if value == "*"
560
- hash[param] = [:absent]
561
- else
562
- if param == :command
563
- hash[param] = [value]
564
- else
565
- # We always want the 'is' value to be an
566
- # array
567
- hash[param] = value.split(",")
568
- end
569
- end
570
- }
571
- else
572
- # Don't fail on unmatched lines, just warn on them
573
- # and skip them.
574
- Puppet.warning "Could not match '%s'" % line
575
- next
576
- end
577
- end
578
-
579
- unless envs.empty?
580
- hash[:environment] = envs
581
- end
582
-
583
- hash[:user] = user
584
-
585
- # Now convert our hash to an object.
586
- hash2obj(hash)
587
-
588
- hash = {}
589
- envs.clear
590
- count += 1
591
- }
592
- end
593
-
594
- # Retrieve a given user's cron job, using the @filetype's +retrieve+
595
- # method. Returns nil if there was no cron job; else, returns the
596
- # number of cron instances found.
597
- def self.retrieve(user)
598
- # First make sure the user exists
599
- begin
600
- Puppet::Util.uid(user)
601
- rescue ArgumentError
602
- raise Puppet::Error, "User %s not found" % user
603
- end
604
-
605
- @tabs[user] ||= @filetype.new(user)
606
- text = @tabs[user].read
607
- if $? != 0
608
- # there is no cron file
609
- return nil
305
+ def insync?
306
+ if @is.is_a? Array
307
+ return @is.sort == @should.sort
610
308
  else
611
- # Preemptively mark everything absent, so that retrieving it
612
- # can mark it present again.
613
- self.find_all { |obj|
614
- obj[:user] == user
615
- }.each { |obj|
616
- obj.is = [:ensure, :absent]
617
- }
618
-
619
- # Get rid of the old instances, so we don't get duplicates
620
- if @instances.include?(user)
621
- @instances[user].clear
622
- else
623
- @instances[user] = []
624
- end
625
-
626
- self.parse(user, text)
309
+ return @is == @should
627
310
  end
628
311
  end
629
312
 
630
- # Remove a user's cron tab.
631
- def self.remove(user)
632
- @tabs[user] ||= @filetype.new(user)
633
- @tabs[user].remove
313
+ def should
314
+ @should
634
315
  end
316
+ end
635
317
 
636
- # Store the user's cron tab. Collects the text of the new tab and
637
- # sends it to the +@filetype+ module's +write+ function. Also adds
638
- # header, warning users not to modify the file directly.
639
- def self.store(user)
640
- unless @instances.include?(user) or @objects.find do |n,o|
641
- o[:user] == user
642
- end
643
- Puppet.notice "No cron instances for %s" % user
644
- return
645
- end
646
-
647
- @tabs[user] ||= @filetype.new(user)
648
-
649
- self.each do |inst|
650
- unless (@instances[user] and @instances[user].include? inst)
651
- @instances[user] ||= []
652
- @instances[user] << inst
653
- end
654
- end
655
- @tabs[user].write(self.tab(user))
656
- end
318
+ newparam(:name) do
319
+ desc "The symbolic name of the cron job. This name
320
+ is used for human reference only and is generated automatically
321
+ for cron jobs found on the system. This generally won't
322
+ matter, as Puppet will do its best to match existing cron jobs
323
+ against specified jobs (and Puppet adds a comment to cron jobs it
324
+ adds), but it is at least possible that converting from
325
+ unmanaged jobs to managed jobs might require manual
326
+ intervention."
327
+
328
+ isnamevar
329
+ end
657
330
 
658
- # Collect all Cron instances for a given user and convert them
659
- # into literal text.
660
- def self.tab(user)
661
- Puppet.info "Writing cron tab for %s" % user
662
- if @instances.include?(user)
663
- return self.header() + @instances[user].reject { |obj|
664
- if obj.is_a?(self) and obj.should(:ensure) == :absent
665
- true
666
- else
667
- false
668
- end
669
- }.collect { |obj|
670
- if obj.is_a? self
671
- obj.to_record
672
- else
673
- obj.to_s
674
- end
675
- }.join("\n") + "\n"
331
+ newproperty(:user) do
332
+ desc "The user to run the command as. This user must
333
+ be allowed to run cron jobs, which is not currently checked by
334
+ Puppet.
335
+
336
+ The user defaults to whomever Puppet is running as."
676
337
 
677
- else
678
- Puppet.notice "No cron instances for %s" % user
679
- end
680
- end
338
+ defaultto { ENV["USER"] || "root" }
339
+ end
681
340
 
682
- # Return the tab object itself. Pretty much just used for testing.
683
- def self.tabobj(user)
684
- @tabs[user]
685
- end
341
+ newproperty(:target) do
342
+ desc "Where the cron job should be stored. For crontab-style
343
+ entries this is the same as the user and defaults that way.
344
+ Other providers default accordingly."
686
345
 
687
- # Return the last time a given user's cron tab was loaded. Could
688
- # be used for reducing writes, but currently is not.
689
- def self.loaded?(user)
690
- if @tabs.include?(user)
691
- return @loaded[user].loaded
346
+ defaultto {
347
+ if provider.is_a?(@parent.class.provider(:crontab))
348
+ if val = @parent.should(:user)
349
+ val
350
+ else
351
+ raise ArgumentError,
352
+ "You must provide a user with crontab entries"
353
+ end
354
+ elsif provider.class.ancestors.include?(Puppet::Provider::ParsedFile)
355
+ provider.class.default_target
692
356
  else
693
- return nil
357
+ nil
694
358
  end
695
- end
359
+ }
360
+ end
696
361
 
697
- def create
698
- # nothing
699
- self.store
700
- end
362
+ # We have to reorder things so that :provide is before :target
701
363
 
702
- def destroy
703
- # nothing, since the 'Cron.tab' method just doesn't write out
704
- # crons whose 'ensure' states are set to 'absent'.
705
- self.store
706
- end
364
+ attr_accessor :uid
707
365
 
708
- def exists?
709
- @states.include?(:ensure) and @states[:ensure].is == :present
710
- end
366
+ def value(name)
367
+ name = symbolize(name)
368
+ ret = nil
369
+ if obj = @parameters[name]
370
+ ret = obj.should
711
371
 
712
- # Override the default Puppet::Type method because we need to call
713
- # the +@filetype+ retrieve method.
714
- def retrieve
715
- unless @parameters.include?(:user)
716
- self.fail "You must specify the cron user"
372
+ if ret.nil?
373
+ ret = obj.is
717
374
  end
718
375
 
719
- self.class.retrieve(self[:user])
720
- if withtab = self.class["testwithtab"]
721
- Puppet.info withtab.is(:ensure).inspect
376
+ if ret == :absent
377
+ ret = nil
722
378
  end
723
- self.eachstate { |st|
724
- st.retrieve
725
- }
726
- if withtab = self.class["testwithtab"]
727
- Puppet.info withtab.is(:ensure).inspect
728
- end
729
- end
730
-
731
- # Write the entire user's cron tab out.
732
- def store
733
- self.class.store(self[:user])
734
379
  end
735
380
 
736
- # Convert the current object a cron-style string. Adds the cron name
737
- # as a comment above the cron job, in the form '# Puppet Name: <name>'.
738
- def to_record
739
- hash = {}
740
-
741
- # Collect all of the values that we have
742
- self.class.fields().each { |param|
743
- hash[param] = self.value(param)
744
-
745
- unless hash[param]
746
- devfail "Got no value for %s" % param
747
- end
748
- }
749
-
750
- str = ""
751
-
752
- str = "# Puppet Name: %s\n" % self.name
753
-
754
- if @states.include?(:environment) and
755
- @states[:environment].should != :absent
756
- envs = @states[:environment].should
757
- unless envs.is_a? Array
758
- envs = [envs]
759
- end
760
-
761
- envs.each do |line| str += (line + "\n") end
762
- end
763
-
764
- line = nil
765
- if special = self.value(:special)
766
- line = str + "@%s %s" %
767
- [special, self.value(:command)]
381
+ unless ret
382
+ case name
383
+ when :command
384
+ devfail "No command, somehow"
385
+ when :special
386
+ # nothing
768
387
  else
769
- line = str + self.class.fields.collect { |f|
770
- if hash[f] and hash[f] != :absent
771
- hash[f]
772
- else
773
- "*"
774
- end
775
- }.join(" ")
388
+ #ret = (self.class.validproperty?(name).default || "*").to_s
389
+ ret = "*"
776
390
  end
777
-
778
- return line
779
391
  end
780
392
 
781
- def value(name)
782
- name = name.intern if name.is_a? String
783
- ret = nil
784
- if @states.include?(name)
785
- ret = @states[name].should_to_s
786
-
787
- if ret == :absent or ret.nil?
788
- ret = @states[name].is_to_s
789
- end
790
-
791
- if ret == :absent
792
- ret = nil
793
- end
794
- end
795
-
796
- unless ret
797
- case name
798
- when :command
799
- devfail "No command, somehow"
800
- when :special
801
- # nothing
802
- else
803
- #ret = (self.class.validstate?(name).default || "*").to_s
804
- ret = "*"
805
- end
806
- end
807
-
808
- ret
809
- end
393
+ ret
810
394
  end
811
395
  end
812
396
 
813
- # $Id: cron.rb 1402 2006-07-18 15:35:15Z luke $
397
+ # $Id: cron.rb 2408 2007-04-24 02:41:16Z luke $