tap 0.11.1 → 0.12.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (103) hide show
  1. data/History +35 -1
  2. data/MIT-LICENSE +1 -1
  3. data/README +16 -15
  4. data/bin/tap +1 -1
  5. data/cmd/console.rb +4 -3
  6. data/cmd/manifest.rb +2 -2
  7. data/cmd/run.rb +12 -15
  8. data/doc/Class Reference +120 -117
  9. data/doc/Command Reference +27 -27
  10. data/doc/Syntax Reference +55 -111
  11. data/doc/Tutorial +69 -26
  12. data/lib/tap.rb +3 -8
  13. data/lib/tap/app.rb +122 -146
  14. data/lib/tap/constants.rb +2 -2
  15. data/lib/tap/env.rb +178 -252
  16. data/lib/tap/exe.rb +67 -30
  17. data/lib/tap/file_task.rb +224 -411
  18. data/lib/tap/generator/arguments.rb +13 -0
  19. data/lib/tap/generator/base.rb +112 -30
  20. data/lib/tap/generator/destroy.rb +36 -13
  21. data/lib/tap/generator/generate.rb +69 -48
  22. data/lib/tap/generator/generators/command/templates/command.erb +3 -3
  23. data/lib/tap/generator/generators/config/config_generator.rb +82 -10
  24. data/lib/tap/generator/generators/generator/generator_generator.rb +16 -6
  25. data/lib/tap/generator/generators/generator/templates/task.erb +2 -2
  26. data/lib/tap/generator/generators/generator/templates/test.erb +26 -0
  27. data/lib/tap/generator/generators/root/root_generator.rb +24 -13
  28. data/lib/tap/generator/generators/root/templates/Rakefile +4 -4
  29. data/lib/tap/generator/generators/root/templates/{tapfile → Rapfile} +6 -6
  30. data/lib/tap/generator/generators/root/templates/gemspec +0 -1
  31. data/lib/tap/generator/generators/task/task_generator.rb +3 -3
  32. data/lib/tap/generator/generators/task/templates/test.erb +1 -1
  33. data/lib/tap/generator/manifest.rb +7 -1
  34. data/lib/tap/generator/preview.rb +76 -0
  35. data/lib/tap/root.rb +222 -156
  36. data/lib/tap/spec.rb +41 -0
  37. data/lib/tap/support/aggregator.rb +25 -28
  38. data/lib/tap/support/audit.rb +278 -357
  39. data/lib/tap/support/constant.rb +2 -1
  40. data/lib/tap/support/constant_manifest.rb +28 -25
  41. data/lib/tap/support/dependency.rb +1 -1
  42. data/lib/tap/support/executable.rb +52 -183
  43. data/lib/tap/support/executable_queue.rb +50 -20
  44. data/lib/tap/support/gems.rb +1 -1
  45. data/lib/tap/support/intern.rb +0 -6
  46. data/lib/tap/support/join.rb +49 -83
  47. data/lib/tap/support/joins.rb +0 -3
  48. data/lib/tap/support/joins/switch.rb +13 -11
  49. data/lib/tap/support/joins/sync_merge.rb +25 -50
  50. data/lib/tap/support/manifest.rb +1 -0
  51. data/lib/tap/support/node.rb +140 -20
  52. data/lib/tap/support/parser.rb +56 -42
  53. data/lib/tap/support/schema.rb +183 -157
  54. data/lib/tap/support/templater.rb +9 -1
  55. data/lib/tap/support/versions.rb +39 -0
  56. data/lib/tap/task.rb +150 -177
  57. data/lib/tap/tasks/dump.rb +4 -4
  58. data/lib/tap/tasks/load.rb +29 -29
  59. data/lib/tap/test.rb +66 -53
  60. data/lib/tap/test/env_vars.rb +3 -3
  61. data/lib/tap/test/extensions.rb +11 -17
  62. data/lib/tap/test/file_test.rb +74 -132
  63. data/lib/tap/test/file_test_class.rb +4 -1
  64. data/lib/tap/test/regexp_escape.rb +2 -2
  65. data/lib/tap/test/script_test.rb +2 -2
  66. data/lib/tap/test/subset_test.rb +6 -6
  67. data/lib/tap/test/tap_test.rb +28 -154
  68. metadata +30 -51
  69. data/bin/rap +0 -118
  70. data/cgi/run.rb +0 -97
  71. data/lib/tap/declarations.rb +0 -229
  72. data/lib/tap/generator/generators/config/templates/doc.erb +0 -12
  73. data/lib/tap/generator/generators/config/templates/nodoc.erb +0 -8
  74. data/lib/tap/generator/generators/file_task/file_task_generator.rb +0 -27
  75. data/lib/tap/generator/generators/file_task/templates/file.txt +0 -11
  76. data/lib/tap/generator/generators/file_task/templates/result.yml +0 -6
  77. data/lib/tap/generator/generators/file_task/templates/task.erb +0 -33
  78. data/lib/tap/generator/generators/file_task/templates/test.erb +0 -29
  79. data/lib/tap/generator/generators/root/templates/test/tap_test_suite.rb +0 -5
  80. data/lib/tap/patches/optparse/summarize.rb +0 -62
  81. data/lib/tap/support/assignments.rb +0 -173
  82. data/lib/tap/support/class_configuration.rb +0 -182
  83. data/lib/tap/support/combinator.rb +0 -125
  84. data/lib/tap/support/configurable.rb +0 -113
  85. data/lib/tap/support/configurable_class.rb +0 -271
  86. data/lib/tap/support/configuration.rb +0 -170
  87. data/lib/tap/support/gems/rake.rb +0 -111
  88. data/lib/tap/support/instance_configuration.rb +0 -173
  89. data/lib/tap/support/joins/fork.rb +0 -19
  90. data/lib/tap/support/joins/merge.rb +0 -22
  91. data/lib/tap/support/joins/sequence.rb +0 -21
  92. data/lib/tap/support/lazy_attributes.rb +0 -45
  93. data/lib/tap/support/lazydoc.rb +0 -386
  94. data/lib/tap/support/lazydoc/comment.rb +0 -503
  95. data/lib/tap/support/lazydoc/config.rb +0 -17
  96. data/lib/tap/support/lazydoc/definition.rb +0 -36
  97. data/lib/tap/support/lazydoc/document.rb +0 -152
  98. data/lib/tap/support/lazydoc/method.rb +0 -24
  99. data/lib/tap/support/tdoc.rb +0 -409
  100. data/lib/tap/support/tdoc/tdoc_html_generator.rb +0 -38
  101. data/lib/tap/support/tdoc/tdoc_html_template.rb +0 -42
  102. data/lib/tap/support/validation.rb +0 -479
  103. data/lib/tap/tasks/rake.rb +0 -57
@@ -1,18 +1,14 @@
1
1
  = Command Reference
2
2
 
3
- Tap comes with two executables: tap (a gateway application) and rap (a shortcut for running tasks). The syntax for running tasks via 'tap run' and rap is covered in the {Syntax Reference}[link:files/doc/Syntax%20Reference.html]; this reference covers all of the other tap commands. For help on the command line, type:
3
+ Tap comes the tap executable. For help on the command line, type:
4
4
 
5
5
  % tap --help
6
6
 
7
- === configuration
7
+ == console
8
8
 
9
- Tap sets up the local execution environment from 'tap.yml', if it exists. The config file is, as the extension implies, a YAML file and will be automatically created by the root generator. Naturally, you can create it yourself. See Tap::Env and Tap::Exe for a list of the available configurations.
10
-
11
- In addition, default configurations may be specified in the global configuration file '~/.tap.yml', where '~' is evaluated as Gem.user_home.
12
-
13
- == tap console
14
-
15
- Console opens an irb session after loading the tap environment. Console defines variables 'app' and 'env' referencing Tap::App.instance and Tap::Env.instance, for easy access.
9
+ Console opens an irb session after loading the tap environment. Console
10
+ defines variables 'app' and 'env' referencing Tap::App.instance and
11
+ Tap::Env.instance, for easy access.
16
12
 
17
13
  % tap console
18
14
  irb(main):001:0> app.log(:hello)
@@ -20,13 +16,13 @@ Console opens an irb session after loading the tap environment. Console defines
20
16
  => true
21
17
  irb(main):002:0>
22
18
 
23
- == tap generate/destroy
19
+ == generate/destroy
24
20
 
25
- Generate and destory launch generator scripts, similar to those in {Rails}[http://www.rubyonrails.org/]. By default Tap provides generators for:
21
+ Generate and destroy launch generator scripts, similar to those in
22
+ {Rails}[http://www.rubyonrails.org/]. By default Tap provides generators for:
26
23
 
27
24
  {command}[link:classes/Tap/Generator/Generators/CommandGenerator.html]:: a new command
28
25
  {config}[link:classes/Tap/Generator/Generators/ConfigGenerator.html]:: a static config file for the specified task
29
- {file_task}[link:classes/Tap/Generator/Generators/FileTaskGenerator.html]:: a file task and test
30
26
  {generator}[link:classes/Tap/Generator/Generators/GeneratorGenerator.html]:: a new generator
31
27
  {root}[link:classes/Tap/Generator/Generators/RootGenerator.html]:: the basic directory structure
32
28
  {task}[link:classes/Tap/Generator/Generators/TaskGenerator.html]:: a task class and test
@@ -36,7 +32,7 @@ For example:
36
32
  % tap generate root .
37
33
  % tap generate task sample_task
38
34
  % tap generate config sample_task
39
-
35
+
40
36
  % tap destroy config sample_task
41
37
  % tap destroy task sample_task
42
38
  % tap destroy root .
@@ -45,10 +41,13 @@ Each generator works a little differently. For help:
45
41
 
46
42
  % tap generate --help
47
43
  % tap generate <generator> --help
48
-
49
- == tap manifest
50
44
 
51
- Manifest prints a list of all resources (commands, tasks, generators, etc) available to tap. Environments are listed in the same order as they are searched, and at the end a tree diagram is printed showing how the environments are nested.
45
+ == manifest
46
+
47
+ Manifest prints a list of all resources (commands, tasks, generators, etc)
48
+ available to tap. Environments are listed in the same order as they are
49
+ searched, and at the end a tree diagram is printed showing how the
50
+ environments are nested.
52
51
 
53
52
  % tap manifest
54
53
  --------------------------------------------------------------------------------
@@ -58,7 +57,6 @@ Manifest prints a list of all resources (commands, tasks, generators, etc) avail
58
57
  generators
59
58
  command (lib/tap/generator/generators/command/command_generator.rb)
60
59
  config (lib/tap/generator/generators/config/config_generator.rb)
61
- file_task (lib/tap/generator/generators/file_task/file_task_generator.rb)
62
60
  generator (lib/tap/generator/generators/generator/generator_generator.rb)
63
61
  root (lib/tap/generator/generators/root/root_generator.rb)
64
62
  task (lib/tap/generator/generators/task/task_generator.rb)
@@ -77,18 +75,25 @@ Manifest prints a list of all resources (commands, tasks, generators, etc) avail
77
75
  Desktop
78
76
  `- tap
79
77
 
80
- == tap run
78
+ == run
81
79
 
82
- Run configures, enqueues, and executes tasks. Run has a rich syntax allowing the specification of any number of tasks with configurations and inputs, but simplifies under most circumstances. The run syntax is detailed in the {Syntax Reference}[link:files/doc/Syntax%20Reference.html], but a couple examples illustrate the key points:
80
+ Run configures, enqueues, and executes tasks. Run has a rich syntax allowing
81
+ the specification of any number of tasks with configurations and inputs, but
82
+ simplifies under most circumstances. The run syntax is detailed in the {Syntax Reference}[link:files/doc/Syntax%20Reference.html], but a couple examples
83
+ illustrate the key points:
83
84
 
84
85
  % tap run sample/task
85
86
  % tap run -- sample/task --key=value input_one -- another/task input_two
86
87
 
87
- The second statement specifies two tasks with inputs, and specifies a configuration for sample/task. As can be seen, run separates tasks using a double-dash, the standard option break. Options for the run command can be specified before the first break.
88
+ The second statement specifies two tasks with inputs, and specifies a
89
+ configuration for sample/task. As can be seen, run separates tasks using a
90
+ double-dash, the standard option break. Options for the run command can be
91
+ specified before the first break.
88
92
 
89
93
  % tap run --debug -- sample/task --key=value
90
94
 
91
- Here run receives the <tt>--debug</tt> option and sample/task receives the <tt>--key=value</tt> option. Inputs work the same way. For example:
95
+ Here run receives the <tt>--debug</tt> option and sample/task receives the
96
+ <tt>--key=value</tt> option. Inputs work the same way. For example:
92
97
 
93
98
  % tap run -- sample/task --key=value one -- another/task two three
94
99
 
@@ -97,9 +102,4 @@ Specifies the following:
97
102
  Sample::Task.new(:key => 'value').enq('one')
98
103
  Another::Task.new.enq('two', 'three')
99
104
 
100
- Any number of tasks, configurations, and inputs may be specified in this way.
101
-
102
- --
103
- == tap server
104
-
105
- An experimental local server for tap tasks.
105
+ Any number of tasks, configurations, and inputs may be specified in this way.
@@ -1,81 +1,11 @@
1
1
  = Syntax Reference
2
2
 
3
- Tap uses several domain-specific languages to declare tasks and workflows. This is a reference for:
3
+ Tap uses several domain-specific languages to declare tasks and workflows.
4
+ This is a reference for:
4
5
 
5
- * task declarations
6
6
  * class definitions
7
7
  * workflows
8
8
 
9
- == Task Declarations
10
-
11
- A task declaration:
12
-
13
- # name:: the name of the task, either alone or as the
14
- # key of a {key => dependencies} hash
15
- # dependencies:: an array of task names (optional)
16
- # arg_names:: an array of argument names (optional)
17
- # configurations:: a hash of {key => default} pairs (optional)
18
-
19
- task({<name> => [<dependencies...>]}, <arg_names...>, {<configs>}) do |task, args|
20
- # arguments are available through args:
21
- args.arg_name
22
-
23
- # configurations are available through task
24
- task.key
25
- end
26
-
27
- A namespace declaration:
28
-
29
- namespace(<name>) { task ... }
30
-
31
- Simple documentation:
32
-
33
- desc "description"
34
- task ...
35
-
36
- Extended documentation:
37
-
38
- # ::desc description
39
- # Extended documentation may span multiple lines, and
40
- # supports
41
- #
42
- # code indentation
43
- # like this.
44
- #
45
- # Lines are justified and wrapped on the command line.
46
- task ...
47
-
48
- Pains were taken to make task declarations for rap work the similar to rake tasks. In both cases (noting that in general, beyond rap, task classes are not limited in these ways):
49
-
50
- * tasks are singleton instances that may be extended across multiple declarations
51
- * tasks do not pass inputs from one task to the next
52
- * tasks only execute once
53
-
54
- A few syntactical differences between rake and rap must to be noted, as they can cause errors if you try to migrate rake tasks to tap. Tap declarations.
55
-
56
- ==== no needs
57
-
58
- Tasks do not support :needs as a way to specify dependencies. For instance, this will declare a ':needs' configuration with the default value ':another', not a task which depends on another:
59
-
60
- Tap.task :name, :needs => :another
61
-
62
- ==== immediate namespace lookup
63
-
64
- Within a namespace, task will look for a literal match to the dependency first. If it doesn't find one, it will declare it within the namespace; one way or the other the dependency is resolved immediately. Hence, in this example the nested task depends on the non-nested task.
65
-
66
- task :outer { print 'non-nested' }
67
- namespace :nest do
68
- task :inner => :outer { puts 'was executed' }
69
- task :outer { print 'nested' }
70
- end
71
-
72
- By contrast, rake waits to resolve dependencies and so will always use a match within a namespace in preference to a literal match. For these tasks rap and rake produce different results:
73
-
74
- % rap nest/inner
75
- non-nested was executed
76
- % rake nest:inner
77
- nested was executed
78
-
79
9
  == Task Classes
80
10
 
81
11
  This is a verbose prototype for Tap::Task subclasses:
@@ -143,14 +73,21 @@ This is a verbose prototype for Tap::Task subclasses:
143
73
 
144
74
  == Workflows
145
75
 
146
- The tap workflow syntax is designed to specify an arbitrary number of tasks, inputs, configurations, and joins. The syntax works both as text and as YAML; 'tap run' and rap both use it to specify which tasks to execute. Basically, the syntax uses double-dash delimiters to separate task vectors and modified delimiters to specify joins for the tasks.
76
+ The tap workflow syntax is designed to specify an arbitrary number of tasks,
77
+ inputs, configurations, and joins. The syntax works both as text and as YAML;
78
+ 'tap run' uses it to specify which tasks to execute. Basically, the syntax
79
+ uses double-dash delimiters to separate task vectors and modified delimiters
80
+ to specify joins for the tasks.
147
81
 
148
82
  These both specify three tasks (x,y,z) joined in a sequence:
149
83
 
150
- % rap x --: y --: z
151
- % rap x -- y -- z --0:1:2
84
+ % tap run -- x --: y --: z
85
+ % tap run -- x -- y -- z --0:1:2
152
86
 
153
- The modified delimiters use numbers to indicate which tasks participate in a join and punctuation to indicate the join type. In the first example, the numbers are implicitly added for the preceding and following task. A variety of joins are supported:
87
+ The modified delimiters use numbers to indicate which tasks participate in a
88
+ join and punctuation to indicate the join type. In the first example, the
89
+ numbers are implicitly added for the preceding and following task. A variety
90
+ of joins are supported:
154
91
 
155
92
  delimiter function syntax example meaning
156
93
  -- delimiter a -- b -- c enques/configures tasks a, b, c
@@ -165,11 +102,11 @@ The modified delimiters use numbers to indicate which tasks participate in a joi
165
102
 
166
103
  Inputs may be specified between delimiters:
167
104
 
168
- % rap x alpha beta --: y gamma --: z delta
105
+ % tap run -- x alpha beta --: y gamma --: z delta
169
106
 
170
107
  As may be configurations, in a variety of formats:
171
108
 
172
- % rap x alpha beta -k --: y gamma --key value --: z delta --key=value
109
+ % tap run -- x alpha beta -k --: y gamma --key value --: z delta --key=value
173
110
 
174
111
  These are the corresponding task vectors:
175
112
 
@@ -191,19 +128,30 @@ This is how it would look as YAML:
191
128
  - --key=value
192
129
  - 0:1:2
193
130
 
194
- The task vectors are converted into a task and an argument vector by first looking up a task class and then calling TaskClass.parse. The parse method returns a configured instance of the task and an argv to be executed by the task. Once the task are instantiated, instances are joined and enqued to Tap::App for execution (see Tap::Support::Schema#build).
131
+ The task vectors are converted into a task and an argument vector by first
132
+ looking up a task class and then calling TaskClass.parse. The parse method
133
+ returns a configured instance of the task and an argv to be executed by the
134
+ task. Once the task are instantiated, instances are joined and enqued to
135
+ Tap::App for execution (see Tap::Support::Schema#build).
195
136
 
196
137
  ==== Class Lookup
197
138
 
198
- Tap looks up classes via Tap::Env. Tap can find tasks from multiple environments; by adding in environments for gems, Tap can find tasks within a gem.
139
+ Tap looks up classes via Tap::Env. Tap can find tasks from multiple
140
+ environments; by adding in environments for gems, Tap can find tasks
141
+ within a gem.
199
142
 
200
- During lookup, classes are treated like filepaths which match from the basename up:
143
+ During lookup, classes are treated like filepaths which match from the
144
+ basename up:
201
145
 
202
146
  class lookup matched by
203
147
  Sample::Task sample/task task, sample/task
204
148
  A::Nested::Task a/nested/task task, nested/task, a/nested/task
205
149
 
206
- In the event of a name conflict, the path of the environment may also be specified. It seems like this could get confusing, but the tap executable produces manifests that specify the minimal path required to uniquely identify a class. Fragments of the minimized paths will be resolved in order from top to bottom within the specified environment. For example:
150
+ In the event of a name conflict, the path of the environment may also be
151
+ specified. It seems like this could get confusing, but the tap executable
152
+ produces manifests that specify the minimal path required to uniquely
153
+ identify a class. Fragments of the minimized paths will be resolved in order
154
+ from top to bottom within the specified environment. For example:
207
155
 
208
156
  % tap run -T
209
157
  one:
@@ -234,57 +182,53 @@ Runs another/task:
234
182
  % tap run -- another/task
235
183
  % tap run -- one:another/task
236
184
 
237
- Notice that the full minimized path ('another/task') is required because simply using 'task' will be matched to sample/task. The order of tasks is obviously not alphabetical -- rather it corresponds to the order in which Tap::Env discovers the tasks.
185
+ Notice that the full minimized path ('another/task') is required because simply
186
+ using 'task' will be matched to sample/task. The order of tasks is obviously
187
+ not alphabetical -- rather it corresponds to the order in which Tap::Env
188
+ discovers the tasks.
238
189
 
239
190
  ==== Dependencies (--*)
240
191
 
241
- Normally each task vector specifies a new instance of a task. This specifies three instance of the 'a' task.
192
+ Normally each task vector specifies a new instance of a task. This specifies
193
+ three instance of the 'a' task.
242
194
 
243
- % rap -- a -- a -- a
195
+ % tap run -- a -- a -- a
244
196
 
245
- When you want to specify a 'singleton' instance of a task, the instance specified by TaskClass.instance, use the dependency delimiter '--*'.
197
+ When you want to specify a 'singleton' instance of a task, the instance
198
+ specified by TaskClass.instance, use the dependency delimiter '--*'.
246
199
 
247
- % rap --* a
200
+ % tap run --* a
248
201
 
249
- The dependency instance will be configured and enqued with the arguments. Dependency instances will be executed first, even if they are specified at the end of a workflow, they cannot participate in workflows, and any single dependency may only be specified once in a workflow. These are equivalent:
202
+ The dependency instance will be configured and enqued with the arguments.
203
+ Dependency instances will be executed first, even if they are specified at the
204
+ end of a workflow, they cannot participate in workflows, and any single
205
+ dependency may only be specified once in a workflow. These are equivalent:
250
206
 
251
- % rap --* a -- b -- c
252
- % rap b -- c --* a
207
+ % tap run --* a -- b -- c
208
+ % tap run b -- c --* a
253
209
 
254
210
  While these raise errors:
255
211
 
256
- % rap --* a --* a
257
- % rap --* a --: b
212
+ % tap run --* a --* a
213
+ % tap run --* a --: b
258
214
 
259
215
  ==== Rounds (--+)
260
216
 
261
- The workflow syntax allows multiple execution rounds to be specified All tasks in a round are run to completion before the next round begins. Rounds are specified by adding '+' characters after the double-dash break.
217
+ The workflow syntax allows multiple execution rounds to be specified All tasks
218
+ in a round are run to completion before the next round begins. Rounds are
219
+ specified by adding '+' characters after the double-dash break.
262
220
 
263
221
  % tap run -- round_one_task --+ round_two_task
264
222
 
265
- Tasks may be added to rounds in any order and may use the shorthand for multiple tasks. These are equivalents:
223
+ Tasks may be added to rounds in any order and may use the shorthand for multiple
224
+ tasks. These are equivalents:
266
225
 
267
226
  % tap run -- a --+ b --+ c --++ d
268
227
  % tap run --+ b --++ d -- a --+ c
269
228
  % tap run -- a -- b -- c -- d --+1[1,2] --+2[3]
270
229
 
271
- Rounds are particularly useful for dump tasks; add a dump task as a final round to capture all results from previous rounds:
230
+ Rounds are particularly useful for dump tasks; add a dump task as a final round
231
+ to capture all results from previous rounds:
272
232
 
273
233
  % tap run -- task -- task --+ dump
274
234
 
275
- ==== Notes for rap
276
-
277
- Specifying tasks for rap is no different than 'tap run'. The only exception occurs when the task can't be found. Unknown tasks are implicitly run as a Tap::Tasks::Rake task, which causes the task to be run as if by rake. These are the same:
278
-
279
- Run a rake task with inputs and an ENV config:
280
-
281
- % rake task_name[1,2,3] key=value
282
-
283
- Explicitly run a Tap::Tasks::Rake task using the same inputs:
284
-
285
- % rap rake task_name[1,2,3] key=value
286
-
287
- Implicitly run the Tap::Tasks::Rake task:
288
-
289
- % rap task_name[1,2,3] key=value
290
-
@@ -1,16 +1,26 @@
1
1
  = Tap (Task Application)
2
2
 
3
- Tap is a framework for creating configurable, distributable tasks and workflows. Although scalable for complex workflows, at it simplest tap works like a supercharged rake. Using the rap executable, you can declare tasks using a syntax almost identical to rake, but with added support for configurations and documentation.
3
+ Tap is a framework for creating configurable, distributable tasks and workflows.
4
+ Although scalable for complex workflows, at it simplest tap works like a
5
+ supercharged rake. Using the rap executable, you can declare tasks using a
6
+ syntax almost identical to rake, but with added support for configurations and
7
+ documentation.
8
+
9
+ Note: this tutorial spans several modules in the {Tap-Suite}[http://tap.rubyforge.org/tap-suite].
10
+ Be sure to install both tap and rap (or the full suite) beforehand.
11
+
12
+ % gem install tap-suite
4
13
 
5
14
  == Quickstart
6
15
 
7
- If you've used rake, tap will be easy to pick up. To get started, make a Tapfile with a simple task declaration:
16
+ If you've used rake, tap will be easy to pick up. To get started, make a
17
+ Rapfile with a simple task declaration:
8
18
 
9
- [Tapfile]
19
+ [Rapfile]
10
20
 
11
21
  # ::desc your basic goodnight moon task
12
22
  # Says goodnight with a configurable message.
13
- Tap.task(:goodnight, :obj, :message => 'goodnight') do |task, args|
23
+ Rap.task(:goodnight, :obj, :message => 'goodnight') do |task, args|
14
24
  puts "#{task.message} #{args.obj}\n"
15
25
  end
16
26
 
@@ -37,15 +47,18 @@ Now from the command line:
37
47
  --name NAME Specify a name
38
48
  --use FILE Loads inputs from file
39
49
 
40
- Just like that you have a command-line application with inputs, configuration, and documentation.
50
+ Just like that you have a command-line application with inputs, configuration,
51
+ and documentation.
41
52
 
42
- The declaration syntax is obviously similar to rake; configurations are new but the task-block style is the same, as are inputs. Other rake constructs are available. Here is a similar goodnight task using dependencies, rake-style.
53
+ The declaration syntax is obviously similar to rake; configurations are new but
54
+ the task-block style is the same, as are inputs. Other rake constructs are
55
+ available. Here is a similar goodnight task using dependencies, rake-style.
43
56
 
44
- [Tapfile]
57
+ [Rapfile]
45
58
 
46
59
  # make the declarations available everywhere
47
60
  # (normally they're accessed via Tap, as above)
48
- include Tap::Declarations
61
+ include Rap::Declarations
49
62
 
50
63
  namespace :example do
51
64
  task(:say, :message) do |task, args|
@@ -53,7 +66,7 @@ The declaration syntax is obviously similar to rake; configurations are new but
53
66
  end
54
67
 
55
68
  desc "your basic goodnight moon task"
56
- task({:goodnight => :say}, :obj) do |task, args|
69
+ task({:goodnight => 'example:say'}, :obj) do |task, args|
57
70
  puts " #{args.obj}\n"
58
71
  end
59
72
  end
@@ -66,21 +79,30 @@ And now from the command line:
66
79
  % rap goodnight world --* say hello
67
80
  hello world
68
81
 
69
- Unlike rake, rap inputs are written out individually and tasks are delimited by a modified double-dash. Aside from that, you can see rap is basically a supercharged rake. Furthermore, rap runs rake. Directly substitute rap for rake on the command line and your tasks should run as normal (see the {Syntax Reference}[link:files/doc/Syntax%20Reference.html] for more details).
82
+ Unlike rake, rap inputs are written out individually and tasks are delimited
83
+ by a modified double-dash. Aside from that, you can see rap is basically a
84
+ supercharged rake. Furthermore, rap runs rake. Directly substitute rap for
85
+ rake on the command line and your tasks should run as normal (see the Rap
86
+ {Syntax Reference}[http://tap.rubyforge.org/rap/files/doc/Syntax%20Reference.html]
87
+ for more details).
70
88
 
71
- However, supercharging rake isn't the point of Tap. Declarations bridge the gap between rake and tap, but tap itself is a more general framework. To get at other features like imperative workflows, testing, and distribution, we have to go beyond rap and take a look at what declarations do.
89
+ However, supercharging rake isn't the point of Tap. Declarations bridge the
90
+ gap between rake and tap, but tap itself is a more general framework. To get
91
+ at other features like imperative workflows, testing, and distribution, we
92
+ have to go beyond rap and take a look at what declarations do.
72
93
 
73
94
  Spoiler: declarations make subclasses of Tap::Task.
74
95
 
75
96
  == Beyond Rap
76
97
 
77
- Going back to the first example, lets take a look at how a task declaration maps to a class definition:
98
+ Going back to the first example, lets take a look at how a task declaration
99
+ maps to a class definition:
78
100
 
79
- [Tapfile]
101
+ [Rapfile]
80
102
 
81
103
  # ::desc your basic goodnight moon task
82
104
  # Says goodnight with a configurable message.
83
- Tap.task(:goodnight, :obj, :message => 'goodnight') do
105
+ Rap.task(:goodnight, :obj, :message => 'goodnight') do
84
106
  puts "#{task.message} #{args.obj}\n"
85
107
  end
86
108
 
@@ -96,10 +118,11 @@ Here is a corresponding class:
96
118
  end
97
119
  end
98
120
 
99
- Simple enough; the name corresponds to the class, configurations (and dependencies, although they aren't show) are written out individually, and the block corresponds to process. There are a few differences, especially relating to process, but for the moment lets gloss over them and see how Goodnight works.
121
+ Simple enough; the name corresponds to the class, configurations (and
122
+ dependencies, although they aren't show) are written out individually, and the
123
+ block corresponds to process. There are a few differences, especially relating
124
+ to process, but for the moment lets gloss over them and see how Goodnight works.
100
125
 
101
- Goodnight.configurations.to_hash # => {:message => 'goodnight'}
102
-
103
126
  goodnight = Goodnight.new
104
127
  goodnight.message # => 'goodnight'
105
128
  goodnight.process('moon') # => 'goodnight moon'
@@ -108,7 +131,14 @@ Simple enough; the name corresponds to the class, configurations (and dependenci
108
131
  hello.message # => 'hello'
109
132
  hello.process('world') # => 'hello world'
110
133
 
111
- Totally straightforward. Goodnight stores the default configurations, each instance has accessors to the configurations, and the defaults may be overridden during initialization, or later. Class definitions allow validation/transformation blocks to be specified for configurations. These blocks process inputs (ex the string inputs from the command line), quite literally defining the writer for a configuration accessor. A set of standard blocks are available through +c+, an alias for the Tap::Support::Validation module.
134
+ Totally straightforward. Goodnight stores the default configurations, each
135
+ instance has accessors to the configurations, and the defaults may be overridden
136
+ during initialization, or later. Class definitions allow validation/transformation
137
+ blocks to be specified for configurations. These blocks process inputs (ex the
138
+ string inputs from the command line), quite literally defining the writer for a
139
+ configuration accessor. A set of standard blocks are available through +c+, an
140
+ alias for the {Configurable::Validation}[http://tap.rubyforge.org/configurable/classes/Configurable/Validation.html]
141
+ module.
112
142
 
113
143
  [lib/goodnight.rb]
114
144
 
@@ -166,9 +196,15 @@ Now from the command line:
166
196
  --name NAME Specify a name
167
197
  --use FILE Loads inputs from file
168
198
 
169
- Take a quick look at the documentation. Class definitions can also map documentation and, in some cases, metadata to the command line; the configurations now have comments and reverse is a switch! Rich mapping allows tasks to act as an script interface, not unlike {OptionParser}[http://www.ruby-doc.org/stdlib/libdoc/optparse/rdoc/classes/OptionParser.html] (surprise, tap uses OptionParser).
199
+ Take a quick look at the documentation. Class definitions map documentation
200
+ and, in some cases, metadata to the command line; the configurations now have
201
+ comments and reverse is a switch! Rich mapping allows tasks to act as an
202
+ script interface, not unlike {OptionParser}[http://www.ruby-doc.org/stdlib/libdoc/optparse/rdoc/classes/OptionParser.html]
203
+ (check out the {Configurable}[http://tap.rubyforge.org/configurable/] gem and
204
+ specifically {ConfigParser}[http://tap.rubyforge.org/configurable/classes/ConfigParser.html]
205
+ for more details).
170
206
 
171
- For example this is a stand-alone goodnight script:
207
+ This is a stand-alone goodnight script:
172
208
 
173
209
  [goodnight]
174
210
 
@@ -198,17 +234,23 @@ Now, from the command line:
198
234
  % ./goodnight --help
199
235
  ...
200
236
 
201
- As simple as it is to take a task to the command line, it's nice to note that tasks may be subclassed, tested, and distributed as usual. No magic, just convenience.
237
+ As simple as it is to take a task to the command line, it's nice to note that
238
+ tasks may be subclassed, tested, and distributed as usual. No magic, just
239
+ convenience.
202
240
 
203
241
  == Tap
204
242
 
205
- Tap comes with two executables, rap and tap. The tap executable is more verbose than rap for running tasks, but it is more configurable, scalable, and logically pure. Tap comes with a number of {commands}[link:files/doc/Command%20Reference.html] but we'll focus on generate to make, test, and package a task library. Begin by creating a tap directory structure and a task:
243
+ Tap comes with two executables, rap and tap. The tap executable is more
244
+ verbose than rap for running tasks, but it is more configurable, scalable, and
245
+ logically pure. Tap comes with a number of {commands}[link:/files/doc/Command%20Reference.html]
246
+ but we'll focus on generate to make, test, and package a task library. Begin
247
+ by creating a tap directory structure and a task:
206
248
 
207
249
  % tap generate root sample
208
250
  % cd sample
209
251
  % tap generate task goodnight
210
252
 
211
- Take a look at the task files an you find something like this:
253
+ Take a look at the task files and you find something like this:
212
254
 
213
255
  [lib/goodnight.rb]
214
256
 
@@ -247,7 +289,7 @@ Take a look at the task files an you find something like this:
247
289
  app.run
248
290
 
249
291
  assert_equal ["goodnight moon"], app.results(task)
250
- assert_audit_equal ExpAudit[[nil, "moon"], [task, "goodnight moon"]], app._results(task)[0]
292
+ assert_audit_equal [[nil, "moon"], [task, "goodnight moon"]], app._results(task)[0]
251
293
  end
252
294
  end
253
295
 
@@ -272,7 +314,8 @@ Ok, lets share it. Print the current gemspec manifest:
272
314
  true test/tap_test_helper.rb
273
315
  true test/tap_test_suite.rb
274
316
 
275
- As you can see, this needs an update to include the task file. Open up sample.gemspec and fix the manifest.
317
+ As you can see, this needs an update to include the task file. Open up
318
+ sample.gemspec and fix the manifest.
276
319
 
277
320
  [sample.gemspec]
278
321
 
@@ -282,7 +325,7 @@ As you can see, this needs an update to include the task file. Open up sample.g
282
325
  s.platform = Gem::Platform::RUBY
283
326
  s.summary = "sample"
284
327
  s.require_path = "lib"
285
- s.add_dependency("tap", ">= 0.11")
328
+ s.add_dependency("tap")
286
329
  s.files = %W{
287
330
  lib/goodnight.rb
288
331
  tap.yml