ratch 0.2.3 → 0.3.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/bin/ratch +60 -47
- data/bin/ratch-find +21 -0
- data/demo/{README → XR} +0 -0
- data/demo/task/stats +0 -2
- data/doc/images/clipboard.jpg +0 -0
- data/doc/images/clipboard2.png +0 -0
- data/doc/images/milles-tn.jpg +0 -0
- data/doc/images/mints.png +0 -0
- data/doc/images/ratch2.png +0 -0
- data/doc/images/ruby-sm.png +0 -0
- data/doc/images/silver.gif +0 -0
- data/doc/images/toolbox.jpg +0 -0
- data/doc/index.html +181 -0
- data/doc/notes/original.rb +308 -0
- data/doc/rdoc/classes/Array.html +194 -0
- data/doc/rdoc/classes/Dir.html +317 -0
- data/doc/rdoc/classes/Hash.html +217 -0
- data/doc/rdoc/classes/Ratch.html +201 -0
- data/doc/rdoc/classes/Ratch/ArgvUtils.html +173 -0
- data/doc/rdoc/classes/Ratch/ArgvUtils/Ext.html +285 -0
- data/doc/rdoc/classes/Ratch/BatchFile.html +207 -0
- data/doc/rdoc/classes/Ratch/BatchManager.html +250 -0
- data/doc/rdoc/classes/Ratch/BatchScript.html +127 -0
- data/doc/rdoc/classes/Ratch/Batchable.html +373 -0
- data/doc/rdoc/classes/Ratch/Build.html +321 -0
- data/doc/rdoc/classes/Ratch/BuildManager.html +319 -0
- data/doc/rdoc/classes/Ratch/Buildable.html +202 -0
- data/doc/rdoc/classes/Ratch/ConfigUtils.html +281 -0
- data/doc/rdoc/classes/Ratch/ConsoleUtils.html +189 -0
- data/doc/rdoc/classes/Ratch/EmailUtils.html +209 -0
- data/doc/rdoc/classes/Ratch/FileUtils.html +674 -0
- data/doc/rdoc/classes/Ratch/GeneralOptions.html +430 -0
- data/doc/rdoc/classes/Ratch/Task.html +201 -0
- data/doc/rdoc/classes/Ratch/TaskManager.html +330 -0
- data/doc/rdoc/classes/Ratch/Taskable.html +231 -0
- data/doc/rdoc/classes/Ratch/UploadUtils.html +566 -0
- data/doc/rdoc/created.rid +1 -0
- data/doc/rdoc/files/COPYING.html +1003 -0
- data/{demo/doc → doc}/rdoc/files/README.html +36 -5
- data/doc/rdoc/files/lib/ratch/argvutils_rb.html +131 -0
- data/doc/rdoc/files/lib/ratch/batch_rb.html +155 -0
- data/doc/rdoc/files/lib/ratch/batchable_rb.html +131 -0
- data/doc/rdoc/files/lib/ratch/batchfile_rb.html +148 -0
- data/doc/rdoc/files/lib/ratch/buildable_rb.html +131 -0
- data/doc/rdoc/files/lib/ratch/consoleutils_rb.html +131 -0
- data/{demo/doc/rdoc/files/lib/foo/foo_rb.html → doc/rdoc/files/lib/ratch/emailutils_rb.html} +35 -41
- data/doc/rdoc/files/lib/ratch/facets/multiglob_rb.html +137 -0
- data/doc/rdoc/files/lib/ratch/fileutils_rb.html +139 -0
- data/doc/rdoc/files/lib/ratch/options_rb.html +131 -0
- data/doc/rdoc/files/lib/ratch/taskable_rb.html +131 -0
- data/doc/rdoc/files/lib/ratch/uploadutils_rb.html +150 -0
- data/doc/rdoc/fr_class_index.html +48 -0
- data/doc/rdoc/fr_file_index.html +41 -0
- data/doc/rdoc/fr_method_index.html +133 -0
- data/{demo/doc → doc}/rdoc/index.html +1 -1
- data/{demo/doc → doc}/rdoc/rdoc-style.css +0 -0
- data/doc/scrap/flexihead-flip.jpg +0 -0
- data/doc/scrap/flexihead.jpg +0 -0
- data/doc/scrap/head1.jpg +0 -0
- data/doc/scrap/ratch.jpg +0 -0
- data/doc/scrap/ratch1.png +0 -0
- data/doc/scrap/ratch2.jpg +0 -0
- data/doc/scrap/ratch3.png +0 -0
- data/doc/scrap/red-ratch.jpg +0 -0
- data/doc/scrap/redratchet.jpg +0 -0
- data/doc/scrap/ruby-kit/ruby.png +0 -0
- data/doc/scrap/scrap.red +256 -0
- data/doc/sitemap.yaml +10 -0
- data/doc/siteparts/index.red +100 -0
- data/doc/siteparts/layout.rhtml +56 -0
- data/doc/siteparts/tutorial.red +578 -0
- data/doc/style.css +112 -0
- data/doc/tutorial.html +722 -0
- data/lib/ratch/batch.rb +417 -30
- data/lib/ratch/{argvutils.rb → batch/argvutils.rb} +27 -19
- data/lib/ratch/batch/build.rb +95 -0
- data/lib/ratch/{consoleutils.rb → batch/consoleutils.rb} +0 -0
- data/lib/ratch/{emailutils.rb → batch/emailutils.rb} +0 -0
- data/lib/ratch/{fileutils.rb → batch/fileutils.rb} +32 -32
- data/lib/ratch/{options.rb → batch/options.rb} +0 -0
- data/lib/ratch/batch/task.rb +43 -0
- data/lib/ratch/manager.rb +34 -0
- data/lib/ratch/project/information.rb +257 -0
- data/lib/ratch/project/package.rb +82 -0
- data/lib/ratch/project/project.rb +531 -0
- data/lib/ratch/project/release.rb +112 -0
- data/lib/ratch/support/filetest.rb +29 -0
- data/lib/ratch/support/setuputils.rb +124 -0
- data/lib/ratch/support/signiture.rb +252 -0
- data/lib/ratch/support/stage.rb +292 -0
- data/lib/ratch/toolset/ruby/pack/gem +85 -0
- data/lib/ratch/toolset/ruby/pack/tgz +85 -0
- data/lib/ratch/toolset/ruby/{crosstest → test/crosstest} +0 -0
- data/lib/ratch/toolset/ruby/{extest → test/extest} +0 -0
- data/lib/ratch/toolset/ruby/{isotest → test/isotest} +0 -0
- data/lib/ratch/toolset/ruby/{load → test/load} +0 -0
- data/lib/ratch/toolset/ruby/{loadtest → test/loadtest} +0 -0
- data/lib/ratch/toolset/ruby/{syntax → test/syntax} +0 -0
- data/lib/ratch/toolset/ruby/{test → test/test} +0 -0
- data/log/{history.rd → history} +6 -0
- data/log/{todo.rd → todo} +0 -0
- data/meta/MANIFEST +52 -36
- data/meta/ROLLRC +2 -0
- data/meta/icli.yaml +16 -0
- data/meta/{ratch-0.2.3.roll → project.yaml} +1 -7
- data/task/release +12 -0
- data/{lib/ratch → work/old}/batchfile.rb +0 -0
- data/work/project-old.rb +67 -0
- data/work/scrap/install +89 -0
- data/work/scrap/install.0 +49 -0
- data/work/scrap/install.1 +63 -0
- data/work/scrap/ludo +25 -0
- data/work/scrap/oldtaskable.rb +573 -0
- data/work/scrap/ratch.man +39 -0
- data/work/scrap/taskable-simple.rb +42 -0
- data/work/scrap/taskable.rb +120 -0
- metadata +170 -72
- data/demo/doc/rdoc/created.rid +0 -1
- data/demo/doc/rdoc/fr_class_index.html +0 -26
- data/demo/doc/rdoc/fr_file_index.html +0 -28
- data/demo/doc/rdoc/fr_method_index.html +0 -27
- data/demo/task/config.yaml +0 -2
- data/lib/ratch/batchable.rb +0 -169
- data/lib/ratch/buildable.rb +0 -182
- data/lib/ratch/configutils.rb +0 -132
- data/lib/ratch/facets/multiglob.rb +0 -160
- data/lib/ratch/taskable.rb +0 -152
- data/log/recent.rd +0 -8
- data/task/config.yaml +0 -10
|
@@ -31,28 +31,35 @@ module Ratch
|
|
|
31
31
|
module ArgvUtils
|
|
32
32
|
|
|
33
33
|
def commandline
|
|
34
|
-
@commandline ||= (ARGV
|
|
34
|
+
@commandline ||= ArgVector.new(ARGV)
|
|
35
35
|
end
|
|
36
36
|
alias_method :argument_vector, :commandline
|
|
37
37
|
|
|
38
|
-
|
|
38
|
+
#
|
|
39
|
+
|
|
40
|
+
class ArgVector
|
|
41
|
+
attr :argv
|
|
42
|
+
|
|
43
|
+
def initialize(argv)
|
|
44
|
+
@argv = argv.dup
|
|
45
|
+
end
|
|
39
46
|
|
|
40
47
|
def arguments
|
|
41
|
-
@arguments ||= select{ |e| e !~ /^-/ && e !~ /=/ }
|
|
48
|
+
@arguments ||= argv.select{ |e| e !~ /^-/ && e !~ /=/ }
|
|
42
49
|
end
|
|
43
50
|
|
|
44
51
|
def options
|
|
45
52
|
@options ||= (
|
|
46
53
|
pms = {}
|
|
47
|
-
select{ |e|
|
|
48
|
-
pms.store(*split('='))
|
|
54
|
+
argv.select{ |e| /[=]/ =~ e }.each do |e|
|
|
55
|
+
pms.store(*e.split('='))
|
|
49
56
|
end
|
|
50
57
|
pms
|
|
51
58
|
)
|
|
52
59
|
end
|
|
53
60
|
|
|
54
61
|
def flags
|
|
55
|
-
@flags ||= select{ |e| e =~ /^-/ || e !~ /=/ }
|
|
62
|
+
@flags ||= argv.select{ |e| e =~ /^-/ || e !~ /=/ }
|
|
56
63
|
end
|
|
57
64
|
|
|
58
65
|
# Have specific flag?
|
|
@@ -61,6 +68,16 @@ module Ratch
|
|
|
61
68
|
flags.include?(flag)
|
|
62
69
|
end
|
|
63
70
|
|
|
71
|
+
#
|
|
72
|
+
def [](x)
|
|
73
|
+
case x
|
|
74
|
+
when Integer
|
|
75
|
+
arguments[x]
|
|
76
|
+
else
|
|
77
|
+
options[x.to_s]
|
|
78
|
+
end
|
|
79
|
+
end
|
|
80
|
+
|
|
64
81
|
# You can use this if you want to use parameterized
|
|
65
82
|
# flags w/o the '=', however be aware that the
|
|
66
83
|
# parameter value will also be listed amoung the
|
|
@@ -71,29 +88,20 @@ module Ratch
|
|
|
71
88
|
# argv.value('--say') #=> "hello"
|
|
72
89
|
# argv.arguments #=> ["tom", "hello"]
|
|
73
90
|
#
|
|
91
|
+
|
|
74
92
|
def value(flag)
|
|
75
|
-
fetch(index(flag)+1)
|
|
93
|
+
argv.fetch(index(flag)+1)
|
|
76
94
|
end
|
|
77
95
|
|
|
78
96
|
#
|
|
79
97
|
def value!(flag)
|
|
80
98
|
@values ||= {}
|
|
81
99
|
@values[flag] ||= (
|
|
82
|
-
delete(index(flag))
|
|
83
|
-
delete(index(flag))
|
|
100
|
+
argv.delete(index(flag))
|
|
101
|
+
argv.delete(index(flag))
|
|
84
102
|
)
|
|
85
103
|
end
|
|
86
104
|
|
|
87
|
-
# #
|
|
88
|
-
# def [](x)
|
|
89
|
-
# case x
|
|
90
|
-
# when Integer
|
|
91
|
-
# super(x)
|
|
92
|
-
# else
|
|
93
|
-
# value(x.to_s)
|
|
94
|
-
# end
|
|
95
|
-
# end
|
|
96
|
-
|
|
97
105
|
end
|
|
98
106
|
end
|
|
99
107
|
end
|
|
@@ -0,0 +1,95 @@
|
|
|
1
|
+
# TITLE:
|
|
2
|
+
#
|
|
3
|
+
# Build
|
|
4
|
+
#
|
|
5
|
+
# COPYING:
|
|
6
|
+
#
|
|
7
|
+
# Copyright (c) 2007 Psi T Corp.
|
|
8
|
+
#
|
|
9
|
+
# This file is part of the ProUtils' Ratch program.
|
|
10
|
+
#
|
|
11
|
+
# Ratch is free software: you can redistribute it and/or modify
|
|
12
|
+
# it under the terms of the GNU General Public License as published by
|
|
13
|
+
# the Free Software Foundation, either version 3 of the License, or
|
|
14
|
+
# (at your option) any later version.
|
|
15
|
+
#
|
|
16
|
+
# Ratch is distributed in the hope that it will be useful,
|
|
17
|
+
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
18
|
+
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
19
|
+
# GNU General Public License for more details.
|
|
20
|
+
#
|
|
21
|
+
# You should have received a copy of the GNU General Public License
|
|
22
|
+
# along with Ratch. If not, see <http://www.gnu.org/licenses/>.
|
|
23
|
+
|
|
24
|
+
module Ratch
|
|
25
|
+
|
|
26
|
+
# = Build class
|
|
27
|
+
|
|
28
|
+
class Build
|
|
29
|
+
|
|
30
|
+
attr :match
|
|
31
|
+
attr :needs
|
|
32
|
+
attr :action
|
|
33
|
+
|
|
34
|
+
alias_method :name, :match
|
|
35
|
+
|
|
36
|
+
# Create a new build definition.
|
|
37
|
+
|
|
38
|
+
def initialize(match, *needs, &action)
|
|
39
|
+
@match = match
|
|
40
|
+
@needs = needs
|
|
41
|
+
@action = action
|
|
42
|
+
end
|
|
43
|
+
|
|
44
|
+
# Call this build process for the given path.
|
|
45
|
+
|
|
46
|
+
def call(path)
|
|
47
|
+
if needs.empty?
|
|
48
|
+
dated = true
|
|
49
|
+
elsif File.exist?(path)
|
|
50
|
+
mtime = File.mtime(path)
|
|
51
|
+
dated = needs.find do |file|
|
|
52
|
+
!File.exist?(file) || File.mtime(file) > mtime
|
|
53
|
+
end
|
|
54
|
+
else
|
|
55
|
+
dated = true
|
|
56
|
+
end
|
|
57
|
+
action.call(path) if dated
|
|
58
|
+
end
|
|
59
|
+
|
|
60
|
+
# Does a file match this build definition?
|
|
61
|
+
|
|
62
|
+
def match?(path)
|
|
63
|
+
case match
|
|
64
|
+
when String
|
|
65
|
+
File.fnmatch(match, path)
|
|
66
|
+
when Regexp
|
|
67
|
+
match =~ path
|
|
68
|
+
else
|
|
69
|
+
false # ???
|
|
70
|
+
end
|
|
71
|
+
end
|
|
72
|
+
|
|
73
|
+
# Is this build needed to update/create path?
|
|
74
|
+
|
|
75
|
+
def needed_for?(path)
|
|
76
|
+
return true unless File.exist?(path)
|
|
77
|
+
return true if needed_paths.empty? # TODO: if there are no prereqs then the file is always considered needed. Correct?
|
|
78
|
+
mtimes = needed_paths.collect do |f|
|
|
79
|
+
File.exist?(f) ? File.mtime(f) : Time.now
|
|
80
|
+
end
|
|
81
|
+
mtimes.max > File.mtime(path)
|
|
82
|
+
end
|
|
83
|
+
|
|
84
|
+
# Glob expanded needs.
|
|
85
|
+
|
|
86
|
+
def needed_paths
|
|
87
|
+
#exact = needs.select{|n| File.fnmatch?(n,n)} +
|
|
88
|
+
exact = needs.select{|n| n !~ /[\[*?]/ }
|
|
89
|
+
globs = needs.collect{|n| Dir.glob(n)}.flatten
|
|
90
|
+
(exact + globs).uniq
|
|
91
|
+
end
|
|
92
|
+
|
|
93
|
+
end
|
|
94
|
+
|
|
95
|
+
end
|
|
File without changes
|
|
File without changes
|
|
@@ -22,8 +22,8 @@
|
|
|
22
22
|
# along with Ratch. If not, see <http://www.gnu.org/licenses/>.
|
|
23
23
|
|
|
24
24
|
require 'fileutils'
|
|
25
|
-
require '
|
|
26
|
-
|
|
25
|
+
require 'facets/dir/multiglob'
|
|
26
|
+
require 'ratch/support/filetest'
|
|
27
27
|
|
|
28
28
|
module Ratch
|
|
29
29
|
|
|
@@ -170,36 +170,36 @@ module Ratch
|
|
|
170
170
|
# task if FileTest.file?(task) && FileTest.executable?(task)
|
|
171
171
|
# end
|
|
172
172
|
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
|
|
173
|
+
# # Is a file a command executable?
|
|
174
|
+
# #
|
|
175
|
+
# # TODO Probably needs to be fixed for Windows.
|
|
176
|
+
#
|
|
177
|
+
# def bin?(path)
|
|
178
|
+
# is_bin = command_paths.any? do |f|
|
|
179
|
+
# FileTest.exist?(File.join(f, path))
|
|
180
|
+
# end
|
|
181
|
+
# is_bin ? File.basename(path) : false
|
|
182
|
+
# end
|
|
183
|
+
#
|
|
184
|
+
# # This is a support method of #bin?
|
|
185
|
+
#
|
|
186
|
+
# def command_paths
|
|
187
|
+
# @command_paths ||= ENV['PATH'].split(/[:;]/)
|
|
188
|
+
# end
|
|
189
|
+
#
|
|
190
|
+
# # TODO Make more robust.
|
|
191
|
+
#
|
|
192
|
+
# UNSAFE = [ '/', '/*', '/**/*' ]
|
|
193
|
+
#
|
|
194
|
+
# # Is a path considered reasonably "safe"?
|
|
195
|
+
#
|
|
196
|
+
# def safe?(path)
|
|
197
|
+
# case path
|
|
198
|
+
# when *UNSAFE
|
|
199
|
+
# return false
|
|
200
|
+
# end
|
|
201
|
+
# true
|
|
202
|
+
# end
|
|
203
203
|
|
|
204
204
|
end
|
|
205
205
|
end
|
|
File without changes
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
# TITLE:
|
|
2
|
+
#
|
|
3
|
+
# Task
|
|
4
|
+
#
|
|
5
|
+
# COPYING:
|
|
6
|
+
#
|
|
7
|
+
# Copyright (c) 2007 Psi T Corp.
|
|
8
|
+
#
|
|
9
|
+
# This file is part of the ProUtils' Ratch program.
|
|
10
|
+
#
|
|
11
|
+
# Ratch is free software: you can redistribute it and/or modify
|
|
12
|
+
# it under the terms of the GNU General Public License as published by
|
|
13
|
+
# the Free Software Foundation, either version 3 of the License, or
|
|
14
|
+
# (at your option) any later version.
|
|
15
|
+
#
|
|
16
|
+
# Ratch is distributed in the hope that it will be useful,
|
|
17
|
+
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
18
|
+
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
19
|
+
# GNU General Public License for more details.
|
|
20
|
+
#
|
|
21
|
+
# You should have received a copy of the GNU General Public License
|
|
22
|
+
# along with Ratch. If not, see <http://www.gnu.org/licenses/>.
|
|
23
|
+
|
|
24
|
+
module Ratch
|
|
25
|
+
|
|
26
|
+
# Task is a very simple store for the defined
|
|
27
|
+
# actions and it's prerequisites.
|
|
28
|
+
|
|
29
|
+
class Task
|
|
30
|
+
attr_reader :name, :needs, :action
|
|
31
|
+
|
|
32
|
+
def initialize(name, *needs, &action)
|
|
33
|
+
@name = name.to_s
|
|
34
|
+
@needs = needs
|
|
35
|
+
@action = action
|
|
36
|
+
end
|
|
37
|
+
|
|
38
|
+
def call
|
|
39
|
+
@action.call if @action
|
|
40
|
+
end
|
|
41
|
+
end
|
|
42
|
+
|
|
43
|
+
end
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
|
|
2
|
+
module Ratch
|
|
3
|
+
|
|
4
|
+
class Manager
|
|
5
|
+
|
|
6
|
+
def toolset_directory
|
|
7
|
+
File.join(File.dirname(__FILE__), 'toolset')
|
|
8
|
+
end
|
|
9
|
+
|
|
10
|
+
#
|
|
11
|
+
|
|
12
|
+
def toolset
|
|
13
|
+
files = []
|
|
14
|
+
Dir.chdir(toolset_directory) do
|
|
15
|
+
files = Dir.glob('**/*')
|
|
16
|
+
end
|
|
17
|
+
files
|
|
18
|
+
end
|
|
19
|
+
|
|
20
|
+
#
|
|
21
|
+
|
|
22
|
+
def tool?(fname)
|
|
23
|
+
file = File.join(toolset_directory, fname)
|
|
24
|
+
if File.exist?(file)
|
|
25
|
+
file
|
|
26
|
+
else
|
|
27
|
+
false
|
|
28
|
+
end
|
|
29
|
+
end
|
|
30
|
+
|
|
31
|
+
end
|
|
32
|
+
|
|
33
|
+
end
|
|
34
|
+
|
|
@@ -0,0 +1,257 @@
|
|
|
1
|
+
# = TITLE:
|
|
2
|
+
#
|
|
3
|
+
# Information
|
|
4
|
+
#
|
|
5
|
+
# = COPYING:
|
|
6
|
+
#
|
|
7
|
+
# Copyright (c) 2007 Psi T Corp.
|
|
8
|
+
#
|
|
9
|
+
# This file is part of the ProUtils' Ratch program.
|
|
10
|
+
#
|
|
11
|
+
# Ratch is free software: you can redistribute it and/or modify
|
|
12
|
+
# it under the terms of the GNU General Public License as published by
|
|
13
|
+
# the Free Software Foundation, either version 3 of the License, or
|
|
14
|
+
# (at your option) any later version.
|
|
15
|
+
#
|
|
16
|
+
# Ratch is distributed in the hope that it will be useful,
|
|
17
|
+
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
18
|
+
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
19
|
+
# GNU General Public License for more details.
|
|
20
|
+
#
|
|
21
|
+
# You should have received a copy of the GNU General Public License
|
|
22
|
+
# along with Ratch. If not, see <http://www.gnu.org/licenses/>.
|
|
23
|
+
|
|
24
|
+
require 'facets/hash/rekey'
|
|
25
|
+
|
|
26
|
+
|
|
27
|
+
module Ratch
|
|
28
|
+
|
|
29
|
+
# Validation Error
|
|
30
|
+
class ValidationError < Exception
|
|
31
|
+
end
|
|
32
|
+
|
|
33
|
+
#
|
|
34
|
+
|
|
35
|
+
class Information
|
|
36
|
+
|
|
37
|
+
class << self
|
|
38
|
+
|
|
39
|
+
def instance_attributes
|
|
40
|
+
@attributes ||= []
|
|
41
|
+
end
|
|
42
|
+
|
|
43
|
+
# Define an attribute.
|
|
44
|
+
|
|
45
|
+
def attr_accessor(name, *aliases, &blk)
|
|
46
|
+
instance_attributes << name.to_s
|
|
47
|
+
instance_attributes.uniq!
|
|
48
|
+
if blk
|
|
49
|
+
define_method(name, &blk)
|
|
50
|
+
attr_writer(name)
|
|
51
|
+
else
|
|
52
|
+
super(name)
|
|
53
|
+
end
|
|
54
|
+
aliases.each{ |aliaz| alias_accessor(aliaz, name) }
|
|
55
|
+
end
|
|
56
|
+
|
|
57
|
+
# Define an attribute alias.
|
|
58
|
+
|
|
59
|
+
def alias_accessor(aliaz, name)
|
|
60
|
+
alias_method aliaz, name
|
|
61
|
+
alias_method "#{aliaz}=", "#{name}="
|
|
62
|
+
end
|
|
63
|
+
|
|
64
|
+
def validation
|
|
65
|
+
@validation ||= []
|
|
66
|
+
end
|
|
67
|
+
|
|
68
|
+
def validate(message, &block)
|
|
69
|
+
validation << [message, block]
|
|
70
|
+
end
|
|
71
|
+
|
|
72
|
+
# Does this class provide open access?
|
|
73
|
+
#
|
|
74
|
+
#def open_access?
|
|
75
|
+
# false
|
|
76
|
+
#end
|
|
77
|
+
|
|
78
|
+
end
|
|
79
|
+
|
|
80
|
+
|
|
81
|
+
def instance_data
|
|
82
|
+
@instance_data ||= {}
|
|
83
|
+
end
|
|
84
|
+
|
|
85
|
+
# List attributes. (Needed?)
|
|
86
|
+
|
|
87
|
+
def attributes
|
|
88
|
+
self.class.instance_attributes
|
|
89
|
+
end
|
|
90
|
+
|
|
91
|
+
|
|
92
|
+
# Initialize
|
|
93
|
+
####################
|
|
94
|
+
|
|
95
|
+
def initialize(data={})
|
|
96
|
+
update(data)
|
|
97
|
+
end
|
|
98
|
+
|
|
99
|
+
def update(data)
|
|
100
|
+
instance_data.update(data.rekey(:to_s))
|
|
101
|
+
|
|
102
|
+
data.each do |k,v|
|
|
103
|
+
send("#{k}=", v) rescue nil
|
|
104
|
+
end
|
|
105
|
+
|
|
106
|
+
# TODO Could add yield(self) via:
|
|
107
|
+
#yld.to_h.each do |k,v|
|
|
108
|
+
# send( "#{k}=", v ) rescue nil
|
|
109
|
+
#end
|
|
110
|
+
end
|
|
111
|
+
|
|
112
|
+
|
|
113
|
+
# Access
|
|
114
|
+
####################
|
|
115
|
+
|
|
116
|
+
# Fetch attribute value, but return nil if it doesn't exist.
|
|
117
|
+
#--
|
|
118
|
+
# TODO Use in method missing instead?
|
|
119
|
+
#++
|
|
120
|
+
|
|
121
|
+
def [](name)
|
|
122
|
+
begin
|
|
123
|
+
h = send(name)
|
|
124
|
+
rescue NoMethodError
|
|
125
|
+
h = nil
|
|
126
|
+
end
|
|
127
|
+
end
|
|
128
|
+
|
|
129
|
+
# Gathers a group of info hash entries into a merged hash.
|
|
130
|
+
# The +names+ are taken in most to least significant order.
|
|
131
|
+
#
|
|
132
|
+
# gather(:package)
|
|
133
|
+
#
|
|
134
|
+
# TODO Change name of this method to something better?
|
|
135
|
+
|
|
136
|
+
def gather( *names )
|
|
137
|
+
result = names.inject({}) do |hash,name|
|
|
138
|
+
attributes.each do |n|
|
|
139
|
+
if n.to_s =~ /^#{name}_(.*?)$/
|
|
140
|
+
hash[$1] = self[n.to_s] if self[n.to_s]
|
|
141
|
+
end
|
|
142
|
+
end
|
|
143
|
+
hash
|
|
144
|
+
end
|
|
145
|
+
result
|
|
146
|
+
end
|
|
147
|
+
|
|
148
|
+
# Collects a group of info entries into a hash.
|
|
149
|
+
# Arguments are a list of info entry names and/or
|
|
150
|
+
# a hash or new name to info entry name.
|
|
151
|
+
#
|
|
152
|
+
# select(:name, :version, :date => :released)
|
|
153
|
+
#
|
|
154
|
+
# This is used to collect info to pass to tools.
|
|
155
|
+
|
|
156
|
+
def select( *args )
|
|
157
|
+
maps = (Hash === args.last ? args.pop : {})
|
|
158
|
+
h = {}
|
|
159
|
+
args.each{ |k| h[k.to_s] = self[k] }
|
|
160
|
+
maps.each{ |k, i| h[k.to_s] = self[i] }
|
|
161
|
+
h
|
|
162
|
+
end
|
|
163
|
+
|
|
164
|
+
|
|
165
|
+
# Validation
|
|
166
|
+
######################
|
|
167
|
+
|
|
168
|
+
#
|
|
169
|
+
def valid?
|
|
170
|
+
begin
|
|
171
|
+
validate
|
|
172
|
+
return true
|
|
173
|
+
rescue ValidationError
|
|
174
|
+
return false
|
|
175
|
+
end
|
|
176
|
+
end
|
|
177
|
+
|
|
178
|
+
#
|
|
179
|
+
def validate
|
|
180
|
+
self.class.validation.each do |message, block|
|
|
181
|
+
raise(ValidationError, message) unless instance_eval(&block)
|
|
182
|
+
end
|
|
183
|
+
end
|
|
184
|
+
|
|
185
|
+
alias_method :assert_valid, :validate
|
|
186
|
+
|
|
187
|
+
|
|
188
|
+
# Conversion
|
|
189
|
+
#################
|
|
190
|
+
|
|
191
|
+
# Order of attributes for yaml conversion.
|
|
192
|
+
|
|
193
|
+
def to_yaml_properties
|
|
194
|
+
attributes.collect{ |a| "@#{a}" }
|
|
195
|
+
end
|
|
196
|
+
|
|
197
|
+
# Use YAML format.
|
|
198
|
+
|
|
199
|
+
def to_yaml( opts={} )
|
|
200
|
+
require 'yaml'
|
|
201
|
+
super
|
|
202
|
+
end
|
|
203
|
+
|
|
204
|
+
# For yaml conversion, no tag.
|
|
205
|
+
|
|
206
|
+
def taguri; nil; end
|
|
207
|
+
|
|
208
|
+
# Convert to hash.
|
|
209
|
+
|
|
210
|
+
def to_hash
|
|
211
|
+
attributes.inject({}) do |h, a|
|
|
212
|
+
v = self[a.to_s] #send(a)
|
|
213
|
+
h[a] = v unless v.nil?
|
|
214
|
+
h
|
|
215
|
+
end
|
|
216
|
+
end
|
|
217
|
+
alias_method :to_h, :to_hash
|
|
218
|
+
|
|
219
|
+
# Use generic XML format.
|
|
220
|
+
|
|
221
|
+
def to_xml( opts={} )
|
|
222
|
+
raise "not yet implemented"
|
|
223
|
+
end
|
|
224
|
+
|
|
225
|
+
# # Use XOXO microformat.
|
|
226
|
+
#
|
|
227
|
+
# def to_xoxo( opts={} )
|
|
228
|
+
# begin
|
|
229
|
+
# require 'blow/xoxo' # EXTERNAL DEPENDENCY!
|
|
230
|
+
# rescue LoadError
|
|
231
|
+
# puts 'Blow (http://blow.rubyforge.org) is required to use XOXO format'
|
|
232
|
+
# end
|
|
233
|
+
# XOXO.dump(self.to_hash, opts)
|
|
234
|
+
# end
|
|
235
|
+
|
|
236
|
+
|
|
237
|
+
# Arbitrary information
|
|
238
|
+
############################
|
|
239
|
+
|
|
240
|
+
# # TODO Perhaps not define this at all if open_access? is false.
|
|
241
|
+
#
|
|
242
|
+
# def method_missing( s, *a, &b )
|
|
243
|
+
# super unless self.class.open_access?
|
|
244
|
+
# s = s.to_s
|
|
245
|
+
# if s[-1,1] == '='
|
|
246
|
+
# (class << self; self; end).class_eval do
|
|
247
|
+
# attr_accessor s.chomp('=')
|
|
248
|
+
# end
|
|
249
|
+
# send(s,*a,&b)
|
|
250
|
+
# else
|
|
251
|
+
# nil #super
|
|
252
|
+
# end
|
|
253
|
+
# end
|
|
254
|
+
|
|
255
|
+
end
|
|
256
|
+
|
|
257
|
+
end
|