tap 0.9.1 → 0.10.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/History +37 -30
- data/MIT-LICENSE +1 -1
- data/README +92 -44
- data/bin/tap +62 -75
- data/cmd/console.rb +42 -0
- data/cmd/destroy.rb +16 -0
- data/cmd/generate.rb +16 -0
- data/cmd/run.rb +126 -0
- data/doc/Class Reference +362 -0
- data/doc/Command Reference +153 -0
- data/doc/Tutorial +237 -0
- data/lib/tap.rb +6 -45
- data/lib/tap/app.rb +126 -500
- data/lib/tap/constants.rb +2 -29
- data/lib/tap/env.rb +555 -250
- data/lib/tap/file_task.rb +60 -103
- data/lib/tap/generator/base.rb +109 -0
- data/lib/tap/generator/destroy.rb +37 -0
- data/lib/tap/generator/generate.rb +61 -0
- data/lib/tap/generator/generators/command/command_generator.rb +16 -12
- data/lib/tap/generator/generators/command/templates/command.erb +13 -19
- data/lib/tap/generator/generators/config/config_generator.rb +18 -27
- data/lib/tap/generator/generators/config/templates/doc.erb +12 -0
- data/lib/tap/generator/generators/config/templates/nodoc.erb +8 -0
- data/lib/tap/generator/generators/file_task/file_task_generator.rb +16 -11
- data/lib/tap/generator/generators/file_task/templates/file.txt +11 -2
- data/lib/tap/generator/generators/file_task/templates/result.yml +6 -0
- data/lib/tap/generator/generators/file_task/templates/task.erb +24 -31
- data/lib/tap/generator/generators/file_task/templates/test.erb +18 -22
- data/lib/tap/generator/generators/root/root_generator.rb +45 -31
- data/lib/tap/generator/generators/root/templates/Rakefile +64 -41
- data/lib/tap/generator/generators/root/templates/gemspec +27 -0
- data/lib/tap/generator/generators/root/templates/tapfile +8 -0
- data/lib/tap/generator/generators/root/templates/test/tap_test_helper.rb +0 -0
- data/lib/tap/generator/generators/root/templates/test/tap_test_suite.rb +1 -1
- data/lib/tap/generator/generators/root/templates/test/tapfile_test.rb +15 -0
- data/lib/tap/generator/generators/task/task_generator.rb +21 -28
- data/lib/tap/generator/generators/task/templates/task.erb +13 -23
- data/lib/tap/generator/generators/task/templates/test.erb +15 -18
- data/lib/tap/generator/manifest.rb +14 -0
- data/lib/tap/patches/rake/rake_test_loader.rb +0 -0
- data/lib/tap/patches/rake/testtask.rb +0 -0
- data/lib/tap/patches/ruby19/backtrace_filter.rb +0 -0
- data/lib/tap/patches/ruby19/parsedate.rb +0 -0
- data/lib/tap/root.rb +260 -21
- data/lib/tap/support/aggregator.rb +11 -11
- data/lib/tap/support/assignments.rb +172 -0
- data/lib/tap/support/audit.rb +20 -18
- data/lib/tap/support/batchable.rb +21 -10
- data/lib/tap/support/batchable_class.rb +107 -0
- data/lib/tap/support/class_configuration.rb +154 -239
- data/lib/tap/support/command_line.rb +97 -102
- data/lib/tap/support/comment.rb +270 -0
- data/lib/tap/support/configurable.rb +86 -65
- data/lib/tap/support/configurable_class.rb +296 -0
- data/lib/tap/support/configuration.rb +122 -0
- data/lib/tap/support/constant.rb +70 -0
- data/lib/tap/support/constant_utils.rb +127 -0
- data/lib/tap/support/declarations.rb +111 -0
- data/lib/tap/support/executable.rb +30 -17
- data/lib/tap/support/executable_queue.rb +0 -0
- data/lib/tap/support/framework.rb +71 -0
- data/lib/tap/support/framework_class.rb +199 -0
- data/lib/tap/support/instance_configuration.rb +147 -0
- data/lib/tap/support/lazydoc.rb +428 -0
- data/lib/tap/support/manifest.rb +89 -0
- data/lib/tap/support/run_error.rb +0 -0
- data/lib/tap/support/shell_utils.rb +33 -9
- data/lib/tap/support/summary.rb +30 -0
- data/lib/tap/support/tdoc.rb +339 -134
- data/lib/tap/support/tdoc/tdoc_html_generator.rb +0 -0
- data/lib/tap/support/tdoc/tdoc_html_template.rb +0 -0
- data/lib/tap/support/templater.rb +180 -0
- data/lib/tap/support/validation.rb +409 -76
- data/lib/tap/support/versions.rb +5 -3
- data/lib/tap/task.rb +78 -174
- data/lib/tap/tasks/dump.rb +56 -0
- data/lib/tap/tasks/rake.rb +93 -0
- data/lib/tap/test.rb +3 -3
- data/lib/tap/test/env_vars.rb +2 -2
- data/lib/tap/test/file_methods.rb +19 -20
- data/lib/tap/test/script_methods.rb +144 -0
- data/lib/tap/test/subset_methods.rb +1 -1
- data/lib/tap/test/tap_methods.rb +28 -62
- data/lib/tap/workflow.rb +22 -39
- metadata +48 -179
- data/Basic Overview +0 -151
- data/Command Reference +0 -99
- data/Rakefile +0 -127
- data/Tutorial +0 -287
- data/lib/tap/cmd/console.rb +0 -31
- data/lib/tap/cmd/destroy.rb +0 -20
- data/lib/tap/cmd/generate.rb +0 -20
- data/lib/tap/cmd/run.rb +0 -151
- data/lib/tap/dump.rb +0 -57
- data/lib/tap/generator.rb +0 -91
- data/lib/tap/generator/generators/command/USAGE +0 -6
- data/lib/tap/generator/generators/config/USAGE +0 -21
- data/lib/tap/generator/generators/config/templates/config.erb +0 -1
- data/lib/tap/generator/generators/file_task/USAGE +0 -3
- data/lib/tap/generator/generators/file_task/templates/file.yml +0 -3
- data/lib/tap/generator/generators/generator/USAGE +0 -0
- data/lib/tap/generator/generators/generator/generator_generator.rb +0 -21
- data/lib/tap/generator/generators/generator/templates/generator.erb +0 -32
- data/lib/tap/generator/generators/generator/templates/usage.erb +0 -1
- data/lib/tap/generator/generators/root/USAGE +0 -0
- data/lib/tap/generator/generators/root/templates/ReadMe.txt +0 -0
- data/lib/tap/generator/generators/root/templates/tap.yml +0 -80
- data/lib/tap/generator/generators/task/USAGE +0 -3
- data/lib/tap/generator/generators/workflow/USAGE +0 -0
- data/lib/tap/generator/generators/workflow/templates/task.erb +0 -16
- data/lib/tap/generator/generators/workflow/templates/test.erb +0 -7
- data/lib/tap/generator/generators/workflow/workflow_generator.rb +0 -6
- data/lib/tap/generator/options.rb +0 -26
- data/lib/tap/generator/usage.rb +0 -26
- data/lib/tap/support/batchable_methods.rb +0 -34
- data/lib/tap/support/command_line_methods.rb +0 -76
- data/lib/tap/support/configurable_methods.rb +0 -224
- data/lib/tap/support/logger.rb +0 -88
- data/lib/tap/support/rake.rb +0 -43
- data/lib/tap/support/tdoc/config_attr.rb +0 -362
- data/test/app/config/another/task.yml +0 -1
- data/test/app/config/batch.yml +0 -2
- data/test/app/config/empty.yml +0 -0
- data/test/app/config/erb.yml +0 -2
- data/test/app/config/some/task.yml +0 -1
- data/test/app/config/template.yml +0 -2
- data/test/app/config/version-0.1.yml +0 -1
- data/test/app/config/version.yml +0 -1
- data/test/app/lib/app_test_task.rb +0 -3
- data/test/app_test.rb +0 -1849
- data/test/env/test_configure/recurse_a.yml +0 -2
- data/test/env/test_configure/recurse_b.yml +0 -2
- data/test/env/test_configure/tap.yml +0 -23
- data/test/env/test_load_env_config/dir/tap.yml +0 -3
- data/test/env/test_load_env_config/recurse_a.yml +0 -2
- data/test/env/test_load_env_config/recurse_b.yml +0 -2
- data/test/env/test_load_env_config/tap.yml +0 -3
- data/test/env_test.rb +0 -198
- data/test/file_task/config/batch.yml +0 -2
- data/test/file_task/config/configured.yml +0 -1
- data/test/file_task/old_file_one.txt +0 -0
- data/test/file_task/old_file_two.txt +0 -0
- data/test/file_task_test.rb +0 -1291
- data/test/root/alt_lib/alt_module.rb +0 -4
- data/test/root/file.txt +0 -0
- data/test/root/glob/one.txt +0 -0
- data/test/root/glob/two.txt +0 -0
- data/test/root/lib/absolute_alt_filepath.rb +0 -2
- data/test/root/lib/alternative_filepath.rb +0 -2
- data/test/root/lib/another_module.rb +0 -2
- data/test/root/lib/nested/some_module.rb +0 -4
- data/test/root/lib/no_module_included.rb +0 -0
- data/test/root/lib/some/module.rb +0 -4
- data/test/root/lib/some_class.rb +0 -2
- data/test/root/lib/some_module.rb +0 -3
- data/test/root/load_path/load_path_module.rb +0 -2
- data/test/root/load_path/skip_module.rb +0 -2
- data/test/root/mtime/older.txt +0 -0
- data/test/root/unload/full_path.rb +0 -2
- data/test/root/unload/loaded_by_nested.rb +0 -2
- data/test/root/unload/nested/nested_load.rb +0 -6
- data/test/root/unload/nested/nested_with_ext.rb +0 -4
- data/test/root/unload/nested/relative_path.rb +0 -4
- data/test/root/unload/older.rb +0 -2
- data/test/root/unload/unload_base.rb +0 -9
- data/test/root/versions/another.yml +0 -0
- data/test/root/versions/file-0.1.2.yml +0 -0
- data/test/root/versions/file-0.1.yml +0 -0
- data/test/root/versions/file.yml +0 -0
- data/test/root_test.rb +0 -718
- data/test/support/aggregator_test.rb +0 -99
- data/test/support/audit_test.rb +0 -445
- data/test/support/batchable_test.rb +0 -74
- data/test/support/class_configuration_test.rb +0 -331
- data/test/support/command_line_test.rb +0 -58
- data/test/support/configurable/config/configured.yml +0 -2
- data/test/support/configurable_test.rb +0 -295
- data/test/support/executable_queue_test.rb +0 -103
- data/test/support/executable_test.rb +0 -38
- data/test/support/logger_test.rb +0 -31
- data/test/support/rake_test.rb +0 -37
- data/test/support/shell_utils_test.rb +0 -24
- data/test/support/tdoc_test.rb +0 -370
- data/test/support/validation_test.rb +0 -54
- data/test/support/versions_test.rb +0 -103
- data/test/tap_test_helper.rb +0 -57
- data/test/tap_test_suite.rb +0 -7
- data/test/task/config/batch.yml +0 -2
- data/test/task/config/batched.yml +0 -2
- data/test/task/config/configured.yml +0 -1
- data/test/task/config/example.yml +0 -1
- data/test/task_base_test.rb +0 -24
- data/test/task_syntax_test.rb +0 -300
- data/test/task_test.rb +0 -320
- data/test/test/env_vars_test.rb +0 -48
- data/test/test/file_methods/test_assert_files/expected/one.txt +0 -1
- data/test/test/file_methods/test_assert_files/expected/two.txt +0 -1
- data/test/test/file_methods/test_assert_files/input/one.txt +0 -1
- data/test/test/file_methods/test_assert_files/input/two.txt +0 -1
- data/test/test/file_methods/test_assert_files_can_have_no_expected_files_if_specified/input/one.txt +0 -1
- data/test/test/file_methods/test_assert_files_can_have_no_expected_files_if_specified/input/two.txt +0 -1
- data/test/test/file_methods/test_assert_files_fails_for_different_content/expected/one.txt +0 -1
- data/test/test/file_methods/test_assert_files_fails_for_different_content/expected/two.txt +0 -1
- data/test/test/file_methods/test_assert_files_fails_for_different_content/input/one.txt +0 -1
- data/test/test/file_methods/test_assert_files_fails_for_different_content/input/two.txt +0 -1
- data/test/test/file_methods/test_assert_files_fails_for_missing_expected_file/expected/one.txt +0 -1
- data/test/test/file_methods/test_assert_files_fails_for_missing_expected_file/input/one.txt +0 -1
- data/test/test/file_methods/test_assert_files_fails_for_missing_expected_file/input/two.txt +0 -1
- data/test/test/file_methods/test_assert_files_fails_for_missing_output_file/expected/one.txt +0 -1
- data/test/test/file_methods/test_assert_files_fails_for_missing_output_file/expected/two.txt +0 -1
- data/test/test/file_methods/test_assert_files_fails_for_missing_output_file/input/one.txt +0 -1
- data/test/test/file_methods/test_assert_files_fails_for_missing_output_file/input/two.txt +0 -1
- data/test/test/file_methods/test_assert_files_fails_for_no_expected_files/input/one.txt +0 -1
- data/test/test/file_methods/test_assert_files_fails_for_no_expected_files/input/two.txt +0 -1
- data/test/test/file_methods/test_method_glob/expected/file.yml +0 -0
- data/test/test/file_methods/test_method_glob/expected/file_1.txt +0 -0
- data/test/test/file_methods/test_method_glob/expected/file_2.txt +0 -0
- data/test/test/file_methods_doc/test_sub/expected/one.txt +0 -1
- data/test/test/file_methods_doc/test_sub/expected/two.txt +0 -1
- data/test/test/file_methods_doc/test_sub/input/one.txt +0 -1
- data/test/test/file_methods_doc/test_sub/input/two.txt +0 -1
- data/test/test/file_methods_doc_test.rb +0 -29
- data/test/test/file_methods_test.rb +0 -275
- data/test/test/subset_methods_test.rb +0 -171
- data/test/test/tap_methods/test_assert_files/expected/task/name/a.txt +0 -1
- data/test/test/tap_methods/test_assert_files/expected/task/name/b.txt +0 -1
- data/test/test/tap_methods/test_assert_files/input/a.txt +0 -1
- data/test/test/tap_methods/test_assert_files/input/b.txt +0 -1
- data/test/test/tap_methods_test.rb +0 -399
- data/test/workflow_test.rb +0 -120
- data/vendor/rails_generator.rb +0 -56
- data/vendor/rails_generator/base.rb +0 -263
- data/vendor/rails_generator/commands.rb +0 -581
- data/vendor/rails_generator/generated_attribute.rb +0 -42
- data/vendor/rails_generator/lookup.rb +0 -209
- data/vendor/rails_generator/manifest.rb +0 -53
- data/vendor/rails_generator/options.rb +0 -143
- data/vendor/rails_generator/scripts.rb +0 -83
- data/vendor/rails_generator/scripts/destroy.rb +0 -7
- data/vendor/rails_generator/scripts/generate.rb +0 -7
- data/vendor/rails_generator/scripts/update.rb +0 -12
- data/vendor/rails_generator/simple_logger.rb +0 -46
- data/vendor/rails_generator/spec.rb +0 -44
|
@@ -1,279 +1,194 @@
|
|
|
1
|
-
|
|
1
|
+
require 'tap/support/assignments'
|
|
2
|
+
require 'tap/support/instance_configuration'
|
|
3
|
+
require 'tap/support/configuration'
|
|
2
4
|
|
|
3
5
|
module Tap
|
|
4
6
|
module Support
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
#
|
|
8
|
-
# ClassConfiguration holds the class configurations defined in a Tap::Task.
|
|
9
|
-
# The configurations are stored as an array of declarations_array like:
|
|
10
|
-
# [name, default, msg, declaration_class]. In addition, ClassConfiguration
|
|
11
|
-
# collapse the array of declarations_array into a hash, which acts as the default
|
|
12
|
-
# task configuration.
|
|
13
|
-
#
|
|
14
|
-
# Storing metadata about the configurations, such as the declaration_class,
|
|
15
|
-
# allows the creation of more user-friendly configuration files and facilitates
|
|
16
|
-
# incorporation into command-line applications.
|
|
17
|
-
#
|
|
18
|
-
# In general, users will not have to interact with ClassConfigurations directly.
|
|
19
|
-
#
|
|
20
|
-
# === Example
|
|
21
|
-
#
|
|
22
|
-
# class BaseTask < Tap::Configurable
|
|
23
|
-
# class_configurations [:one, 1]
|
|
24
|
-
# end
|
|
25
|
-
#
|
|
26
|
-
# BaseTask.configurations.hash # => {:one => 1}
|
|
27
|
-
#
|
|
28
|
-
# class SubTask < BaseTask
|
|
29
|
-
# class_configurations(
|
|
30
|
-
# [:one, 'one', "the first configuration"],
|
|
31
|
-
# [:two, 'two', "the second configuration"])
|
|
32
|
-
# end
|
|
33
|
-
#
|
|
34
|
-
# SubTask.configurations.hash # => {:one => 'one', :two => 'two'}
|
|
35
|
-
#
|
|
36
|
-
# Now you can see how the comments and declaring classes get used in the
|
|
37
|
-
# configuration files. Note that configuration keys are stringified
|
|
38
|
-
# for clarity (this is ok -- they will be symbolized when loaded by a
|
|
39
|
-
# task).
|
|
40
|
-
#
|
|
41
|
-
# [BaseTask.configurations.format_yaml]
|
|
42
|
-
# # BaseTask configuration
|
|
43
|
-
# one: 1
|
|
44
|
-
#
|
|
45
|
-
# [SubTask.configurations.format_yaml]
|
|
46
|
-
# # BaseTask configuration
|
|
47
|
-
# one: one # the first configuration
|
|
48
|
-
#
|
|
49
|
-
# # SubTask configuration
|
|
50
|
-
# two: two # the second configuration
|
|
51
|
-
#
|
|
52
|
-
#--
|
|
53
|
-
# TODO -
|
|
54
|
-
# Revisit config formatting... right now it's a bit jacked.
|
|
55
|
-
#++
|
|
7
|
+
|
|
8
|
+
# ClassConfiguration tracks and handles the class configurations defined in a
|
|
9
|
+
# Configurable class.
|
|
56
10
|
class ClassConfiguration
|
|
57
11
|
include Enumerable
|
|
58
12
|
|
|
59
|
-
# The class receiving
|
|
13
|
+
# The class receiving new configurations
|
|
60
14
|
attr_reader :receiver
|
|
15
|
+
|
|
16
|
+
# Tracks the assignment of the config keys to receivers
|
|
17
|
+
attr_reader :assignments
|
|
61
18
|
|
|
62
|
-
#
|
|
63
|
-
#
|
|
64
|
-
|
|
65
|
-
attr_reader :declarations_array
|
|
66
|
-
|
|
67
|
-
# An array of configuration keys declared by self
|
|
68
|
-
attr_reader :declarations
|
|
69
|
-
|
|
70
|
-
# A hash of the unprocessed default values
|
|
71
|
-
attr_reader :unprocessed_default
|
|
72
|
-
|
|
73
|
-
# A hash of the processed default values
|
|
74
|
-
attr_reader :default
|
|
75
|
-
|
|
76
|
-
# A hash of the processing blocks
|
|
77
|
-
attr_reader :process_blocks
|
|
19
|
+
# A map of config keys and instance methods used to set a
|
|
20
|
+
# config (ie the reader and writer for a config)
|
|
21
|
+
attr_reader :map
|
|
78
22
|
|
|
79
|
-
# A placeholder to indicate when no value
|
|
80
|
-
# was specified during a call to add.
|
|
81
|
-
NO_VALUE = Object.new
|
|
82
|
-
|
|
83
23
|
def initialize(receiver, parent=nil)
|
|
84
24
|
@receiver = receiver
|
|
85
|
-
@default = parent != nil ? parent.default.dup : {}
|
|
86
|
-
@unprocessed_default = parent != nil ? parent.unprocessed_default.dup : {}
|
|
87
|
-
@process_blocks = parent != nil ? parent.process_blocks.dup : {}
|
|
88
25
|
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
26
|
+
if parent != nil
|
|
27
|
+
@map = parent.map.inject({}) do |hash, (key, config)|
|
|
28
|
+
hash[key] = config.dup
|
|
29
|
+
hash
|
|
30
|
+
end
|
|
31
|
+
@assignments = Assignments.new(parent.assignments)
|
|
32
|
+
else
|
|
33
|
+
@map = {}
|
|
34
|
+
@assignments = Assignments.new
|
|
35
|
+
end
|
|
36
|
+
end
|
|
37
|
+
|
|
38
|
+
# Initializes a Configuration using the inputs and sets it in self
|
|
39
|
+
# using name as a key, overriding the current config by that name,
|
|
40
|
+
# if it exists. Returns the new config.
|
|
41
|
+
def add(name, default=nil, attributes={})
|
|
42
|
+
self[name] = Configuration.new(name.to_sym, default, attributes)
|
|
94
43
|
end
|
|
95
44
|
|
|
96
|
-
#
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
def declared?(key)
|
|
100
|
-
key = key.to_sym
|
|
101
|
-
declarations_array.each do |r,array|
|
|
102
|
-
return true if array.include?(key)
|
|
103
|
-
end
|
|
104
|
-
false
|
|
45
|
+
# Removes the specified configuration.
|
|
46
|
+
def remove(key)
|
|
47
|
+
self[key] = nil
|
|
105
48
|
end
|
|
106
49
|
|
|
107
|
-
#
|
|
108
|
-
|
|
109
|
-
|
|
50
|
+
# Gets the configuration specified by key. The key is symbolized.
|
|
51
|
+
def [](key)
|
|
52
|
+
map[key.to_sym]
|
|
53
|
+
end
|
|
54
|
+
|
|
55
|
+
# Assigns the configuration to key. A nil config unassigns the
|
|
56
|
+
# configuration key. The key is symbolized.
|
|
57
|
+
def []=(key, config)
|
|
110
58
|
key = key.to_sym
|
|
111
|
-
|
|
112
|
-
|
|
59
|
+
|
|
60
|
+
if config == nil
|
|
61
|
+
assignments.unassign(key)
|
|
62
|
+
map.delete(key)
|
|
63
|
+
else
|
|
64
|
+
assignments.assign(receiver, key) unless assignments.assigned?(key)
|
|
65
|
+
map[key] = config
|
|
113
66
|
end
|
|
114
|
-
nil
|
|
115
67
|
end
|
|
116
68
|
|
|
117
|
-
# Returns
|
|
118
|
-
def
|
|
119
|
-
|
|
120
|
-
return array if r == receiver
|
|
121
|
-
end
|
|
122
|
-
nil
|
|
69
|
+
# Returns true if key is a config key.
|
|
70
|
+
def key?(key)
|
|
71
|
+
map.has_key?(key)
|
|
123
72
|
end
|
|
124
73
|
|
|
125
|
-
#
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
# The existing value and process_block for the
|
|
129
|
-
# configuration will not be overwritten unless specified. However,
|
|
130
|
-
# if a configuration is added without specifying a value and no previous
|
|
131
|
-
# default value exists, the default and unprocessed_default for the
|
|
132
|
-
# configuration will be set to nil.
|
|
133
|
-
#
|
|
134
|
-
#--
|
|
135
|
-
# Note -- existing blocks are NOT overwritten unless a new block is provided.
|
|
136
|
-
# This allows overide of the default value in subclasses while preserving the
|
|
137
|
-
# validation/processing code.
|
|
138
|
-
def add(key, value=NO_VALUE, &process_block)
|
|
139
|
-
key = key.to_sym
|
|
140
|
-
value = unprocessed_default[key] if value == NO_VALUE
|
|
141
|
-
|
|
142
|
-
declarations << key unless declared?(key)
|
|
143
|
-
process_blocks[key] = process_block if block_given?
|
|
144
|
-
unprocessed_default[key] = value
|
|
145
|
-
default[key] = process(key, value)
|
|
146
|
-
|
|
147
|
-
self
|
|
74
|
+
# Returns all config keys.
|
|
75
|
+
def keys
|
|
76
|
+
map.keys
|
|
148
77
|
end
|
|
149
78
|
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
process_blocks.delete(key)
|
|
154
|
-
unprocessed_default.delete(key)
|
|
155
|
-
default.delete(key)
|
|
156
|
-
|
|
157
|
-
self
|
|
79
|
+
# Returns config keys in order.
|
|
80
|
+
def ordered_keys
|
|
81
|
+
assignments.values
|
|
158
82
|
end
|
|
159
83
|
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
unless declarations.include?(key)
|
|
177
|
-
declarations << key
|
|
178
|
-
yield(key) if block_given?
|
|
179
|
-
end
|
|
180
|
-
|
|
181
|
-
add(key, another.unprocessed_default[key], &another.process_blocks[key])
|
|
84
|
+
# Returns all mapped configs.
|
|
85
|
+
def values
|
|
86
|
+
map.values
|
|
87
|
+
end
|
|
88
|
+
|
|
89
|
+
# True if map is empty.
|
|
90
|
+
def empty?
|
|
91
|
+
map.empty?
|
|
92
|
+
end
|
|
93
|
+
|
|
94
|
+
# Calls block once for each [receiver, key, config] in self,
|
|
95
|
+
# passing those elements as parameters, in the order in
|
|
96
|
+
# which they were assigned.
|
|
97
|
+
def each
|
|
98
|
+
assignments.each do |receiver, key|
|
|
99
|
+
yield(receiver, key, map[key])
|
|
182
100
|
end
|
|
183
101
|
end
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
102
|
+
|
|
103
|
+
# Calls block once for each [key, config] pair in self,
|
|
104
|
+
# passing those elements as parameters, in the order in
|
|
105
|
+
# which they were assigned.
|
|
106
|
+
def each_pair
|
|
107
|
+
assignments.each do |receiver, key|
|
|
108
|
+
yield(key, map[key])
|
|
188
109
|
end
|
|
189
110
|
end
|
|
190
111
|
|
|
191
|
-
#
|
|
192
|
-
#
|
|
193
|
-
def
|
|
194
|
-
|
|
195
|
-
block ? block.call(value) : value
|
|
112
|
+
# Initializes and returns a new InstanceConfiguration set to self
|
|
113
|
+
# and bound to the receiver, if specified.
|
|
114
|
+
def instance_config(receiver=nil)
|
|
115
|
+
InstanceConfiguration.new(self, receiver)
|
|
196
116
|
end
|
|
197
|
-
|
|
198
|
-
# Nicely formats the configurations into yaml with messages and
|
|
199
|
-
# declaration class divisions.
|
|
200
|
-
def format_yaml
|
|
201
|
-
lines = []
|
|
202
|
-
declarations_array.each do |receiver, keys|
|
|
203
|
-
|
|
204
|
-
# do not consider keys that have been removed
|
|
205
|
-
keys = keys.delete_if {|key| !self.default.has_key?(key) }
|
|
206
|
-
next if keys.empty?
|
|
207
|
-
|
|
208
|
-
lines << "# #{receiver} configuration#{keys.length > 1 ? 's' : ''}"
|
|
209
|
-
|
|
210
|
-
class_doc = Tap::Support::TDoc[receiver]
|
|
211
|
-
configurations = (class_doc == nil ? [] : class_doc.configurations)
|
|
212
|
-
keys.each do |key|
|
|
213
|
-
tdoc_config = configurations.find {|config| config.name == key.to_s }
|
|
214
|
-
|
|
215
|
-
# yaml adds a header and a final newline which should be removed:
|
|
216
|
-
# {'key' => 'value'}.to_yaml # => "--- \nkey: value\n"
|
|
217
|
-
# {'key' => 'value'}.to_yaml[5...-1] # => "key: value"
|
|
218
|
-
yaml = {key.to_s => unprocessed_default[key]}.to_yaml[5...-1]
|
|
219
|
-
message = tdoc_config ? tdoc_config.comment : ""
|
|
220
|
-
|
|
221
|
-
lines << case
|
|
222
|
-
when message == nil || message.empty?
|
|
223
|
-
# if there is no message, simply add the yaml
|
|
224
|
-
yaml
|
|
225
|
-
when yaml !~ /\r?\n/ && message !~ /\r?\n/ && yaml.length < 25 && message.length < 30
|
|
226
|
-
# shorthand ONLY if the config and message can be expressed in a single line
|
|
227
|
-
message = message.gsub(/^#\s*/, "")
|
|
228
|
-
"%-25s # %s" % [yaml, message]
|
|
229
|
-
else
|
|
230
|
-
lines << ""
|
|
231
|
-
# comment out new lines and add the message
|
|
232
|
-
message.split(/\n/).each do |msg|
|
|
233
|
-
lines << "# #{msg.strip.gsub(/^#\s*/, '')}"
|
|
234
|
-
end
|
|
235
|
-
yaml
|
|
236
|
-
end
|
|
237
|
-
end
|
|
238
|
-
|
|
239
|
-
# add a spacer line
|
|
240
|
-
lines << ""
|
|
241
|
-
end
|
|
242
117
|
|
|
243
|
-
|
|
118
|
+
# Returns a hash of the (key, config.default) values in self.
|
|
119
|
+
def to_hash
|
|
120
|
+
hash = {}
|
|
121
|
+
each_pair {|key, config| hash[key] = config.default }
|
|
122
|
+
hash
|
|
244
123
|
end
|
|
245
|
-
|
|
246
|
-
def opt_map(long_option)
|
|
247
|
-
raise ArgumentError.new("not a long option: #{long_option}") unless long_option =~ /^--(.*)$/
|
|
248
|
-
long = $1
|
|
249
124
|
|
|
250
|
-
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
|
|
125
|
+
def code_comments
|
|
126
|
+
code_comments = []
|
|
127
|
+
values.each do |config|
|
|
128
|
+
code_comments << config.desc if config.desc.kind_of?(Comment)
|
|
129
|
+
end
|
|
130
|
+
code_comments
|
|
254
131
|
end
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
:long => key,
|
|
262
|
-
:short => nil,
|
|
263
|
-
:opt_type => GetoptLong::REQUIRED_ARGUMENT,
|
|
264
|
-
:desc => receiver
|
|
265
|
-
}
|
|
266
|
-
|
|
267
|
-
long = attributes[:long]
|
|
268
|
-
attributes[:long] = "--#{long}" unless long =~ /^-{2}/
|
|
269
|
-
|
|
270
|
-
short = attributes[:short].to_s
|
|
271
|
-
attributes[:short] = "-#{short}" unless short.empty? || short =~ /^-/
|
|
132
|
+
|
|
133
|
+
# The path to the :doc template (see format_str)
|
|
134
|
+
DOC_TEMPLATE_PATH = File.expand_path File.dirname(__FILE__) + "/../generator/generators/config/templates/doc.erb"
|
|
135
|
+
|
|
136
|
+
# The path to the :nodoc template (see format_str)
|
|
137
|
+
NODOC_TEMPLATE_PATH = File.expand_path File.dirname(__FILE__) + "/../generator/generators/config/templates/nodoc.erb"
|
|
272
138
|
|
|
273
|
-
|
|
274
|
-
|
|
139
|
+
# Formats the configurations using the specified template. Two default
|
|
140
|
+
# templates are defined, <tt>:doc</tt> and <tt>:nodoc</tt>. These map
|
|
141
|
+
# to the contents of DOC_TEMPLATE_PATH and NODOC_TEMPLATE_PATH and
|
|
142
|
+
# correspond to the documented and undocumented config generator templates.
|
|
143
|
+
#
|
|
144
|
+
# == Custom Templates
|
|
145
|
+
#
|
|
146
|
+
# format_str initializes a Templater which formats each [receiver, configurations]
|
|
147
|
+
# pair in turn, and puts the output to the target using <tt><<</tt>. The
|
|
148
|
+
# templater is assigned the following attributes for use in formatting:
|
|
149
|
+
#
|
|
150
|
+
# receiver:: The receiver
|
|
151
|
+
# class_doc:: The TDoc for the receiver, from Tap::Support::TDoc[receiver]
|
|
152
|
+
# configurations:: An array of configurations and associated comments
|
|
153
|
+
#
|
|
154
|
+
# In the template these can be accessed as any ERB locals, for example:
|
|
155
|
+
#
|
|
156
|
+
# <%= receiver.to_s %>
|
|
157
|
+
# <% configurations.each do |key, config, comment| %>
|
|
158
|
+
# ...
|
|
159
|
+
# <% end %>
|
|
160
|
+
#
|
|
161
|
+
# The input template may be a String or an ERB; either may be used to
|
|
162
|
+
# initialize the templater.
|
|
163
|
+
def format_str(template=:doc, target="")
|
|
164
|
+
Lazydoc.resolve(code_comments)
|
|
165
|
+
|
|
166
|
+
template = case template
|
|
167
|
+
when :doc then File.read(DOC_TEMPLATE_PATH)
|
|
168
|
+
when :nodoc then File.read(NODOC_TEMPLATE_PATH)
|
|
169
|
+
else template
|
|
170
|
+
end
|
|
171
|
+
|
|
172
|
+
templater = Templater.new(template)
|
|
173
|
+
assignments.each_pair do |receiver, keys|
|
|
174
|
+
next if keys.empty?
|
|
175
|
+
|
|
176
|
+
# set the template attributes
|
|
177
|
+
templater.receiver = receiver
|
|
178
|
+
templater.configurations = keys.collect do |key|
|
|
179
|
+
# duplicate config so that any changes to it
|
|
180
|
+
# during templation will not propogate back
|
|
181
|
+
# into self
|
|
182
|
+
[key, map[key].dup]
|
|
183
|
+
end.compact
|
|
184
|
+
|
|
185
|
+
yield(templater) if block_given?
|
|
186
|
+
target << templater.build
|
|
187
|
+
end
|
|
188
|
+
|
|
189
|
+
target
|
|
275
190
|
end
|
|
276
|
-
|
|
277
191
|
end
|
|
278
192
|
end
|
|
279
|
-
end
|
|
193
|
+
end
|
|
194
|
+
|
|
@@ -1,103 +1,98 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
#
|
|
11
|
-
#
|
|
12
|
-
#
|
|
13
|
-
#
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
opt_lines.join("\n")
|
|
99
|
-
end
|
|
100
|
-
|
|
101
|
-
end
|
|
102
|
-
end
|
|
1
|
+
require 'optparse'
|
|
2
|
+
|
|
3
|
+
module Tap
|
|
4
|
+
module Support
|
|
5
|
+
|
|
6
|
+
# Under Construction
|
|
7
|
+
module CommandLine
|
|
8
|
+
module_function
|
|
9
|
+
|
|
10
|
+
# Parses the input string as YAML, if the string matches the YAML document
|
|
11
|
+
# specifier (ie it begins with "---\s*\n"). Otherwise returns the string.
|
|
12
|
+
#
|
|
13
|
+
# str = {'key' => 'value'}.to_yaml # => "--- \nkey: value\n"
|
|
14
|
+
# Tap::Script.parse_yaml(str) # => {'key' => 'value'}
|
|
15
|
+
# Tap::Script.parse_yaml("str") # => "str"
|
|
16
|
+
def parse_yaml(str)
|
|
17
|
+
str =~ /\A---\s*\n/ ? YAML.load(str) : str
|
|
18
|
+
end
|
|
19
|
+
|
|
20
|
+
SPLIT_ARGV_REGEXP = /\A-{2}(\+*)\z/
|
|
21
|
+
|
|
22
|
+
def split(argv)
|
|
23
|
+
current = []
|
|
24
|
+
current_split = []
|
|
25
|
+
splits = [current_split]
|
|
26
|
+
|
|
27
|
+
argv.each do |arg|
|
|
28
|
+
if arg =~ SPLIT_ARGV_REGEXP
|
|
29
|
+
current_split << current unless current.empty?
|
|
30
|
+
current = []
|
|
31
|
+
current_split = (splits[$1.length] ||= [])
|
|
32
|
+
else
|
|
33
|
+
current << arg
|
|
34
|
+
end
|
|
35
|
+
end
|
|
36
|
+
|
|
37
|
+
current_split << current unless current.empty?
|
|
38
|
+
splits.delete_if {|split| split.nil? || split.empty? }
|
|
39
|
+
splits
|
|
40
|
+
end
|
|
41
|
+
|
|
42
|
+
def shift(argv)
|
|
43
|
+
index = nil
|
|
44
|
+
argv.each_with_index do |arg, i|
|
|
45
|
+
if arg !~ /\A-/
|
|
46
|
+
index = i
|
|
47
|
+
break
|
|
48
|
+
end
|
|
49
|
+
end
|
|
50
|
+
index == nil ? nil : argv.delete_at(index)
|
|
51
|
+
end
|
|
52
|
+
|
|
53
|
+
def usage(path, cols=80)
|
|
54
|
+
parse_usage(File.read(path), cols)
|
|
55
|
+
end
|
|
56
|
+
|
|
57
|
+
def parse_usage(str, cols=80)
|
|
58
|
+
scanner = StringScanner.new(str)
|
|
59
|
+
scanner.scan(/^#!.*?$/)
|
|
60
|
+
Comment.parse(scanner, false).wrap(cols, 2).strip
|
|
61
|
+
end
|
|
62
|
+
|
|
63
|
+
def configv(config)
|
|
64
|
+
desc = config.desc
|
|
65
|
+
desc.extend(OptParseComment) if desc.kind_of?(Comment)
|
|
66
|
+
|
|
67
|
+
[config.short, argtype(config), desc].compact
|
|
68
|
+
end
|
|
69
|
+
|
|
70
|
+
def argtype(config)
|
|
71
|
+
case config.arg_type
|
|
72
|
+
when :optional
|
|
73
|
+
"#{config.long} [#{config.arg_name}]"
|
|
74
|
+
when :switch
|
|
75
|
+
config.long(true)
|
|
76
|
+
when :flag
|
|
77
|
+
config.long
|
|
78
|
+
when :list
|
|
79
|
+
"#{config.long} a,b,c"
|
|
80
|
+
when :mandatory, nil
|
|
81
|
+
"#{config.long} #{config.arg_name}"
|
|
82
|
+
else
|
|
83
|
+
raise "unknown arg_type: #{config.arg_type}"
|
|
84
|
+
end
|
|
85
|
+
end
|
|
86
|
+
|
|
87
|
+
module OptParseComment
|
|
88
|
+
def empty?
|
|
89
|
+
to_str.empty?
|
|
90
|
+
end
|
|
91
|
+
|
|
92
|
+
def to_str
|
|
93
|
+
subject.to_s =~ /#(.*)$/ ? $1.strip : ""
|
|
94
|
+
end
|
|
95
|
+
end
|
|
96
|
+
end
|
|
97
|
+
end
|
|
103
98
|
end
|