scout-gear 6.0.0 → 7.2.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.
- checksums.yaml +4 -4
- data/.vimproject +465 -432
- data/VERSION +1 -1
- data/bin/scout +5 -1
- data/lib/rbbt-scout.rb +5 -0
- data/lib/scout/concurrent_stream.rb +6 -2
- data/lib/scout/config.rb +168 -0
- data/lib/scout/exceptions.rb +9 -0
- data/lib/scout/indiferent_hash/options.rb +1 -0
- data/lib/scout/indiferent_hash.rb +4 -2
- data/lib/scout/log/color.rb +31 -2
- data/lib/scout/log/progress/report.rb +1 -0
- data/lib/scout/log/progress/util.rb +3 -1
- data/lib/scout/log/progress.rb +7 -3
- data/lib/scout/log.rb +8 -3
- data/lib/scout/misc/digest.rb +1 -3
- data/lib/scout/misc/monitor.rb +3 -0
- data/lib/scout/misc/system.rb +15 -0
- data/lib/scout/misc.rb +1 -0
- data/lib/scout/named_array.rb +68 -0
- data/lib/scout/open/stream.rb +58 -26
- data/lib/scout/path/find.rb +27 -3
- data/lib/scout/path/util.rb +7 -4
- data/lib/scout/persist/serialize.rb +7 -14
- data/lib/scout/persist.rb +21 -1
- data/lib/scout/resource/produce.rb +7 -94
- data/lib/scout/resource/software.rb +176 -0
- data/lib/scout/tsv/dumper.rb +107 -0
- data/lib/scout/tsv/index.rb +49 -0
- data/lib/scout/tsv/parser.rb +317 -0
- data/lib/scout/tsv/path.rb +13 -0
- data/lib/scout/tsv/persist/adapter.rb +348 -0
- data/lib/scout/tsv/persist/tokyocabinet.rb +113 -0
- data/lib/scout/tsv/persist.rb +15 -0
- data/lib/scout/tsv/traverse.rb +48 -0
- data/lib/scout/tsv/util.rb +24 -0
- data/lib/scout/tsv.rb +27 -0
- data/lib/scout/work_queue/worker.rb +16 -11
- data/lib/scout/work_queue.rb +63 -21
- data/lib/scout/workflow/definition.rb +93 -4
- data/lib/scout/workflow/step/config.rb +18 -0
- data/lib/scout/workflow/step/dependencies.rb +40 -0
- data/lib/scout/workflow/step/file.rb +15 -0
- data/lib/scout/workflow/step/info.rb +33 -6
- data/lib/scout/workflow/step/provenance.rb +148 -0
- data/lib/scout/workflow/step.rb +70 -20
- data/lib/scout/workflow/task.rb +5 -4
- data/lib/scout/workflow/usage.rb +1 -1
- data/lib/scout/workflow.rb +11 -3
- data/lib/scout-gear.rb +1 -0
- data/lib/scout.rb +1 -0
- data/scout-gear.gemspec +38 -3
- data/scout_commands/find +1 -1
- data/scout_commands/workflow/task +16 -10
- data/share/software/install_helpers +523 -0
- data/test/scout/log/test_progress.rb +0 -2
- data/test/scout/misc/test_system.rb +21 -0
- data/test/scout/open/test_stream.rb +160 -1
- data/test/scout/path/test_find.rb +14 -7
- data/test/scout/resource/test_software.rb +24 -0
- data/test/scout/test_config.rb +66 -0
- data/test/scout/test_meta_extension.rb +10 -0
- data/test/scout/test_named_array.rb +19 -0
- data/test/scout/test_persist.rb +35 -0
- data/test/scout/test_semaphore.rb +1 -1
- data/test/scout/test_tmpfile.rb +2 -2
- data/test/scout/test_tsv.rb +74 -0
- data/test/scout/test_work_queue.rb +63 -8
- data/test/scout/tsv/persist/test_adapter.rb +34 -0
- data/test/scout/tsv/persist/test_tokyocabinet.rb +92 -0
- data/test/scout/tsv/test_dumper.rb +44 -0
- data/test/scout/tsv/test_index.rb +64 -0
- data/test/scout/tsv/test_parser.rb +173 -0
- data/test/scout/tsv/test_persist.rb +36 -0
- data/test/scout/tsv/test_traverse.rb +9 -0
- data/test/scout/tsv/test_util.rb +0 -0
- data/test/scout/work_queue/test_worker.rb +49 -1
- data/test/scout/workflow/step/test_dependencies.rb +25 -0
- data/test/scout/workflow/step/test_info.rb +15 -17
- data/test/scout/workflow/step/test_load.rb +16 -18
- data/test/scout/workflow/step/test_provenance.rb +25 -0
- data/test/scout/workflow/test_step.rb +206 -10
- data/test/scout/workflow/test_task.rb +0 -3
- data/test/test_helper.rb +6 -0
- metadata +37 -2
data/lib/scout/open/stream.rb
CHANGED
@@ -1,5 +1,5 @@
|
|
1
1
|
module Open
|
2
|
-
BLOCK_SIZE = 1024
|
2
|
+
BLOCK_SIZE = 1024 * 8
|
3
3
|
|
4
4
|
class << self
|
5
5
|
attr_accessor :sensible_write_lock_dir
|
@@ -31,13 +31,16 @@ module Open
|
|
31
31
|
Thread.current.report_on_exception = false
|
32
32
|
consume_stream(io, false, into, into_close)
|
33
33
|
end
|
34
|
+
|
34
35
|
io.threads.push(consumer_thread) if io.respond_to?(:threads)
|
36
|
+
Thread.pass until consumer_thread["name"]
|
37
|
+
|
35
38
|
consumer_thread
|
36
39
|
else
|
37
40
|
if into
|
38
|
-
Log.
|
41
|
+
Log.low "Consuming stream #{Log.fingerprint io} -> #{Log.fingerprint into}"
|
39
42
|
else
|
40
|
-
Log.
|
43
|
+
Log.low "Consuming stream #{Log.fingerprint io}"
|
41
44
|
end
|
42
45
|
|
43
46
|
begin
|
@@ -49,11 +52,8 @@ module Open
|
|
49
52
|
into_path, into = into, File.open(into, 'w')
|
50
53
|
end
|
51
54
|
|
52
|
-
into.sync = true if IO === into
|
53
55
|
into_close = false unless into.respond_to? :close
|
54
|
-
io.sync = true
|
55
56
|
|
56
|
-
Log.high "started consuming stream #{Log.fingerprint io}"
|
57
57
|
begin
|
58
58
|
while c = io.readpartial(BLOCK_SIZE)
|
59
59
|
into << c if into
|
@@ -67,16 +67,15 @@ module Open
|
|
67
67
|
into.close if into and into_close and not into.closed?
|
68
68
|
block.call if block_given?
|
69
69
|
|
70
|
-
Log.high "Done consuming stream #{Log.fingerprint io} into #{into_path || into}"
|
71
70
|
c
|
72
71
|
rescue Aborted
|
73
|
-
Log.
|
72
|
+
Log.low "Consume stream Aborted #{Log.fingerprint io} into #{into_path || into}"
|
74
73
|
io.abort $! if io.respond_to? :abort
|
75
74
|
into.close if into.respond_to?(:closed?) && ! into.closed?
|
76
75
|
FileUtils.rm into_path if into_path and File.exist?(into_path)
|
77
76
|
rescue Exception
|
78
|
-
Log.
|
79
|
-
exception = io.stream_exception
|
77
|
+
Log.low "Consume stream Exception reading #{Log.fingerprint io} into #{into_path || into} - #{$!.message}"
|
78
|
+
exception = (io.respond_to?(:stream_exception) && io.stream_exception) ? io.stream_exception : $!
|
80
79
|
io.abort exception if io.respond_to? :abort
|
81
80
|
into.close if into.respond_to?(:closed?) && ! into.closed?
|
82
81
|
into_path = into if into_path.nil? && String === into
|
@@ -109,7 +108,7 @@ module Open
|
|
109
108
|
Log.warn "Path exists in sensible_write, not forcing update: #{ path }"
|
110
109
|
Open.consume_stream content
|
111
110
|
else
|
112
|
-
FileUtils.mkdir_p File.dirname(tmp_path) unless File.directory?
|
111
|
+
FileUtils.mkdir_p File.dirname(tmp_path) unless File.directory?(File.dirname(tmp_path))
|
113
112
|
FileUtils.rm_f tmp_path if File.exist? tmp_path
|
114
113
|
begin
|
115
114
|
|
@@ -120,7 +119,7 @@ module Open
|
|
120
119
|
File.open(tmp_path, 'wb') do |f| f.write content end
|
121
120
|
when (IO === content or StringIO === content or File === content)
|
122
121
|
Open.write(tmp_path) do |f|
|
123
|
-
f.sync = true
|
122
|
+
#f.sync = true
|
124
123
|
begin
|
125
124
|
while block = content.readpartial(BLOCK_SIZE)
|
126
125
|
f.write block
|
@@ -145,12 +144,12 @@ module Open
|
|
145
144
|
|
146
145
|
Open.notify_write(path)
|
147
146
|
rescue Aborted
|
148
|
-
Log.
|
147
|
+
Log.low "Aborted sensible_write -- #{ Log.reset << Log.color(:blue, path) }"
|
149
148
|
content.abort if content.respond_to? :abort
|
150
149
|
Open.rm path if File.exist? path
|
151
150
|
rescue Exception
|
152
151
|
exception = (AbortedStream === content and content.exception) ? content.exception : $!
|
153
|
-
Log.
|
152
|
+
Log.low "Exception in sensible_write: [#{Process.pid}] #{exception.message} -- #{ Log.color :blue, path }"
|
154
153
|
content.abort if content.respond_to? :abort
|
155
154
|
Open.rm path if File.exist? path
|
156
155
|
raise exception
|
@@ -219,16 +218,15 @@ module Open
|
|
219
218
|
|
220
219
|
#parent_pid = Process.pid
|
221
220
|
pid = Process.fork {
|
222
|
-
purge_pipes(sin)
|
223
|
-
sout.close
|
224
221
|
begin
|
222
|
+
purge_pipes(sin)
|
223
|
+
sout.close
|
225
224
|
|
226
225
|
yield sin
|
227
226
|
sin.close if close and not sin.closed?
|
228
227
|
|
229
228
|
rescue Exception
|
230
229
|
Log.exception $!
|
231
|
-
#Process.kill :INT, parent_pid
|
232
230
|
Kernel.exit!(-1)
|
233
231
|
end
|
234
232
|
Kernel.exit! 0
|
@@ -242,18 +240,18 @@ module Open
|
|
242
240
|
ConcurrentStream.setup sout, :pair => sin
|
243
241
|
|
244
242
|
thread = Thread.new do
|
245
|
-
Thread.current["name"] = "Pipe input #{Log.fingerprint sin} => #{Log.fingerprint sout}"
|
246
|
-
Thread.current.report_on_exception = false
|
247
243
|
begin
|
244
|
+
Thread.current.report_on_exception = false
|
245
|
+
Thread.current["name"] = "Pipe input #{Log.fingerprint sin} => #{Log.fingerprint sout}"
|
248
246
|
|
249
247
|
yield sin
|
250
248
|
|
251
249
|
sin.close if close and not sin.closed? and not sin.aborted?
|
252
250
|
rescue Aborted
|
253
|
-
Log.
|
251
|
+
Log.low "Aborted open_pipe: #{$!.message}"
|
254
252
|
raise $!
|
255
253
|
rescue Exception
|
256
|
-
Log.
|
254
|
+
Log.low "Exception in open_pipe: #{$!.message}"
|
257
255
|
begin
|
258
256
|
sout.threads.delete(Thread.current)
|
259
257
|
sout.pair = []
|
@@ -269,6 +267,7 @@ module Open
|
|
269
267
|
|
270
268
|
sin.threads = [thread]
|
271
269
|
sout.threads = [thread]
|
270
|
+
Thread.pass until thread["name"]
|
272
271
|
end
|
273
272
|
|
274
273
|
sout
|
@@ -287,8 +286,8 @@ module Open
|
|
287
286
|
|
288
287
|
splitter_thread = Thread.new(Thread.current) do |parent|
|
289
288
|
begin
|
290
|
-
Thread.current["name"] = "Splitter #{Log.fingerprint stream}"
|
291
289
|
Thread.current.report_on_exception = false
|
290
|
+
Thread.current["name"] = "Splitter #{Log.fingerprint stream}"
|
292
291
|
|
293
292
|
skip = [false] * num
|
294
293
|
begin
|
@@ -317,7 +316,7 @@ module Open
|
|
317
316
|
out_pipes.each do |sout|
|
318
317
|
sout.abort if sout.respond_to? :abort
|
319
318
|
end
|
320
|
-
Log.
|
319
|
+
Log.low "Tee aborting #{Log.fingerprint stream}"
|
321
320
|
raise $!
|
322
321
|
rescue Exception
|
323
322
|
begin
|
@@ -332,7 +331,7 @@ module Open
|
|
332
331
|
in_pipes.each do |sin|
|
333
332
|
sin.close unless sin.closed?
|
334
333
|
end
|
335
|
-
Log.
|
334
|
+
Log.low "Tee exception #{Log.fingerprint stream}"
|
336
335
|
rescue
|
337
336
|
Log.exception $!
|
338
337
|
ensure
|
@@ -344,11 +343,10 @@ module Open
|
|
344
343
|
end
|
345
344
|
end
|
346
345
|
|
347
|
-
|
348
346
|
out_pipes.each do |sout|
|
349
347
|
ConcurrentStream.setup sout, :threads => splitter_thread, :filename => filename, :pair => stream
|
350
348
|
end
|
351
|
-
|
349
|
+
Thread.pass until splitter_thread["name"]
|
352
350
|
|
353
351
|
main_pipe = out_pipes.first
|
354
352
|
main_pipe.autojoin = true
|
@@ -399,5 +397,39 @@ module Open
|
|
399
397
|
end
|
400
398
|
str
|
401
399
|
end
|
400
|
+
|
401
|
+
def self.sort_stream(stream, header_hash = "#", cmd_args = "-u")
|
402
|
+
Open.open_pipe do |sin|
|
403
|
+
line = stream.gets
|
404
|
+
while line =~ /^#{header_hash}/ do
|
405
|
+
sin.puts line
|
406
|
+
line = stream.gets
|
407
|
+
end
|
408
|
+
|
409
|
+
line_stream = Open.open_pipe do |line_stream_in|
|
410
|
+
line_stream_in.puts line
|
411
|
+
begin
|
412
|
+
Open.consume_stream(stream, false, line_stream_in)
|
413
|
+
rescue
|
414
|
+
raise $!
|
415
|
+
end
|
416
|
+
end
|
417
|
+
|
418
|
+
sorted = CMD.cmd("env LC_ALL=C sort #{cmd_args || ""}", :in => line_stream, :pipe => true)
|
419
|
+
|
420
|
+
begin
|
421
|
+
Open.consume_stream(sorted, false, sin)
|
422
|
+
rescue
|
423
|
+
Log.exception $!
|
424
|
+
begin
|
425
|
+
sorted.raise($!) if sorted.respond_to? :raise
|
426
|
+
stream.raise($!) if stream.respond_to? :raise
|
427
|
+
ensure
|
428
|
+
raise $!
|
429
|
+
end
|
430
|
+
end
|
431
|
+
end
|
432
|
+
end
|
433
|
+
|
402
434
|
|
403
435
|
end
|
data/lib/scout/path/find.rb
CHANGED
@@ -9,7 +9,8 @@ module Path
|
|
9
9
|
break unless file =~ /(?:scout|rbbt)\/(?:resource\.rb|workflow\.rb)/ or
|
10
10
|
file =~ /(?:scout|rbbt)\/(?:.*\/)?path\.rb/ or
|
11
11
|
file =~ /(?:scout|rbbt)\/(?:.*\/)?path\/(?:find|refactor|util)\.rb/ or
|
12
|
-
file =~ /(?:scout|rbbt)\/persist.rb/
|
12
|
+
file =~ /(?:scout|rbbt)\/persist.rb/ or
|
13
|
+
file =~ /modules\/rbbt-util/
|
13
14
|
end
|
14
15
|
file = file.sub(/\.rb[^\w].*/,'.rb')
|
15
16
|
end
|
@@ -136,15 +137,38 @@ module Path
|
|
136
137
|
found
|
137
138
|
end
|
138
139
|
|
140
|
+
def self.exists_file_or_alternatives(file)
|
141
|
+
return file if File.exist?(file) or File.directory?(file)
|
142
|
+
%w(gz bgz zip).each do |extension|
|
143
|
+
alt_file = file + '.' + extension
|
144
|
+
return alt_file if File.exist?(alt_file) or File.directory?(alt_file)
|
145
|
+
end
|
146
|
+
nil
|
147
|
+
end
|
148
|
+
|
139
149
|
def find(where = nil)
|
140
|
-
|
150
|
+
if located?
|
151
|
+
if File.exist?(self)
|
152
|
+
return self if located?
|
153
|
+
else
|
154
|
+
found = Path.exists_file_or_alternatives(self)
|
155
|
+
if found
|
156
|
+
return self.annotate(found)
|
157
|
+
else
|
158
|
+
return self if located?
|
159
|
+
end
|
160
|
+
end
|
161
|
+
end
|
162
|
+
|
141
163
|
return find_all if where == 'all' || where == :all
|
164
|
+
|
142
165
|
return follow(where) if where
|
143
166
|
|
144
167
|
map_order.each do |map_name|
|
145
168
|
found = follow(map_name, false)
|
146
169
|
|
147
|
-
|
170
|
+
found = Path.exists_file_or_alternatives(found)
|
171
|
+
return annotate_found_where(found, map_name) if found
|
148
172
|
end
|
149
173
|
|
150
174
|
return follow(:default)
|
data/lib/scout/path/util.rb
CHANGED
@@ -1,4 +1,9 @@
|
|
1
1
|
module Path
|
2
|
+
def no_method_missing
|
3
|
+
class << self
|
4
|
+
undef_method :method_missing
|
5
|
+
end
|
6
|
+
end
|
2
7
|
|
3
8
|
def self.is_filename?(string, need_to_exists = true)
|
4
9
|
return false if string.nil?
|
@@ -56,9 +61,7 @@ module Path
|
|
56
61
|
end.flatten.uniq
|
57
62
|
end
|
58
63
|
|
59
|
-
def
|
60
|
-
|
61
|
-
undef_method :method_missing
|
62
|
-
end
|
64
|
+
def set_extension(extension)
|
65
|
+
self.annotate(self + ".#{extension}")
|
63
66
|
end
|
64
67
|
end
|
@@ -93,22 +93,15 @@ module Persist
|
|
93
93
|
|
94
94
|
Log.debug "Save #{Log.fingerprint type} on #{file}"
|
95
95
|
if save_drivers[type]
|
96
|
-
|
97
|
-
|
98
|
-
|
99
|
-
|
100
|
-
if IO === content || StringIO === content
|
101
|
-
main, copy = Open.tee_stream_thread content
|
102
|
-
t = Thread.new do
|
103
|
-
Thread.current["name"] = "file saver: " + file
|
104
|
-
Open.sensible_write(file, main)
|
96
|
+
if save_drivers[type].arity == 1
|
97
|
+
return Open.sensible_write(file, save_drivers[type].call(content))
|
98
|
+
else
|
99
|
+
return save_drivers[type].call(file, content)
|
105
100
|
end
|
106
|
-
ConcurrentStream.setup copy, :threads => t, :filename => file, :autojoin => true
|
107
|
-
else
|
108
|
-
serialized = serialize(content, type)
|
109
|
-
Open.sensible_write(file, serialized, :force => true)
|
110
|
-
content
|
111
101
|
end
|
102
|
+
serialized = serialize(content, type)
|
103
|
+
Open.sensible_write(file, serialized, :force => true)
|
104
|
+
return nil
|
112
105
|
end
|
113
106
|
|
114
107
|
def self.load(file, type = :serializer)
|
data/lib/scout/persist.rb
CHANGED
@@ -26,6 +26,7 @@ module Persist
|
|
26
26
|
|
27
27
|
def self.persist(name, type = :serializer, options = {}, &block)
|
28
28
|
persist_options = IndiferentHash.pull_keys options, :persist
|
29
|
+
return yield if FalseClass === persist_options[:persist]
|
29
30
|
file = persist_options[:path] || options[:path] || persistence_path(name, options)
|
30
31
|
|
31
32
|
update = options[:update] || persist_options[:update]
|
@@ -35,10 +36,29 @@ module Persist
|
|
35
36
|
if Open.exist?(file) && ! update
|
36
37
|
Persist.load(file, type)
|
37
38
|
else
|
39
|
+
return yield(file) if block.arity == 1
|
38
40
|
res = yield
|
39
41
|
begin
|
40
42
|
Open.rm(file)
|
41
|
-
|
43
|
+
|
44
|
+
if IO === res || StringIO === res
|
45
|
+
tee_copies = options[:tee_copies] || 1
|
46
|
+
main, *copies = Open.tee_stream_thread_multiple res, tee_copies + 1
|
47
|
+
t = Thread.new do
|
48
|
+
Thread.current.report_on_exception = false
|
49
|
+
Thread.current["name"] = "file saver: " + file
|
50
|
+
Open.sensible_write(file, main)
|
51
|
+
end
|
52
|
+
Thread.pass until t["name"]
|
53
|
+
copies.each_with_index do |copy,i|
|
54
|
+
next_stream = copies[i+1] if copies.length > i
|
55
|
+
ConcurrentStream.setup copy, :threads => t, :filename => file, :autojoin => true, :next => next_stream
|
56
|
+
end
|
57
|
+
res = copies.first
|
58
|
+
else
|
59
|
+
pres = Persist.save(res, file, type)
|
60
|
+
res = pres unless pres.nil?
|
61
|
+
end
|
42
62
|
rescue
|
43
63
|
raise $! unless options[:canfail]
|
44
64
|
Log.debug "Could not persist #{type} on #{file}"
|
@@ -39,7 +39,7 @@ module Resource
|
|
39
39
|
else
|
40
40
|
ScoutRake.run(rakefile, rake_dir, task)
|
41
41
|
end
|
42
|
-
rescue
|
42
|
+
rescue ScoutRake::TaskNotFound
|
43
43
|
if rake_dir.nil? or rake_dir.empty? or rake_dir == "/" or rake_dir == "./"
|
44
44
|
raise $!
|
45
45
|
end
|
@@ -51,9 +51,9 @@ module Resource
|
|
51
51
|
|
52
52
|
def produce(path, force = false)
|
53
53
|
case
|
54
|
-
when @resources.include?(path)
|
54
|
+
when (@resources && @resources.include?(path))
|
55
55
|
type, content = @resources[path]
|
56
|
-
when (Path === path && @resources.include?(path.original))
|
56
|
+
when (Path === path && @resources && @resources.include?(path.original))
|
57
57
|
type, content = @resources[path.original]
|
58
58
|
when has_rake(path)
|
59
59
|
type = :rake
|
@@ -126,97 +126,10 @@ module Resource
|
|
126
126
|
when :rake
|
127
127
|
run_rake(path, content, rake_dir)
|
128
128
|
when :install
|
129
|
-
|
130
|
-
|
131
|
-
|
132
|
-
|
133
|
-
software_dir = path.resource.root.software.find :user
|
134
|
-
helper_file = File.expand_path(Rbbt.share.install.software.lib.install_helpers.find(:lib, caller_lib_dir(__FILE__)))
|
135
|
-
#helper_file = File.expand_path(Rbbt.share.install.software.lib.install_helpers.find)
|
136
|
-
|
137
|
-
preamble = <<-EOF
|
138
|
-
#!/bin/bash
|
139
|
-
|
140
|
-
RBBT_SOFTWARE_DIR="#{software_dir}"
|
141
|
-
|
142
|
-
INSTALL_HELPER_FILE="#{helper_file}"
|
143
|
-
source "$INSTALL_HELPER_FILE"
|
144
|
-
EOF
|
145
|
-
|
146
|
-
content = content.call if Proc === content
|
147
|
-
|
148
|
-
content = if content =~ /git:|\.git$/
|
149
|
-
{:git => content}
|
150
|
-
else
|
151
|
-
{:src => content}
|
152
|
-
end if String === content and Open.remote?(content)
|
153
|
-
|
154
|
-
script_text = case content
|
155
|
-
when nil
|
156
|
-
raise "No way to install #{path}"
|
157
|
-
when Path
|
158
|
-
Open.read(content)
|
159
|
-
when String
|
160
|
-
if Path.is_filename?(content) and Open.exists?(content)
|
161
|
-
Open.read(content)
|
162
|
-
else
|
163
|
-
content
|
164
|
-
end
|
165
|
-
when Hash
|
166
|
-
name = content[:name] || File.basename(path)
|
167
|
-
git = content[:git]
|
168
|
-
src = content[:src]
|
169
|
-
url = content[:url]
|
170
|
-
jar = content[:jar]
|
171
|
-
extra = content[:extra]
|
172
|
-
commands = content[:commands]
|
173
|
-
if git
|
174
|
-
<<-EOF
|
175
|
-
|
176
|
-
name='#{name}'
|
177
|
-
url='#{git}'
|
178
|
-
|
179
|
-
install_git "$name" "$url" #{extra}
|
180
|
-
|
181
|
-
#{commands}
|
182
|
-
EOF
|
183
|
-
elsif src
|
184
|
-
<<-EOF
|
185
|
-
|
186
|
-
name='#{name}'
|
187
|
-
url='#{src}'
|
188
|
-
|
189
|
-
install_src "$name" "$url" #{extra}
|
190
|
-
|
191
|
-
#{commands}
|
192
|
-
EOF
|
193
|
-
elsif jar
|
194
|
-
<<-EOF
|
195
|
-
|
196
|
-
name='#{name}'
|
197
|
-
url='#{jar}'
|
198
|
-
|
199
|
-
install_jar "$name" "$url" #{extra}
|
200
|
-
|
201
|
-
#{commands}
|
202
|
-
EOF
|
203
|
-
else
|
204
|
-
<<-EOF
|
205
|
-
|
206
|
-
name='#{name}'
|
207
|
-
url='#{url}'
|
208
|
-
|
209
|
-
#{commands}
|
210
|
-
EOF
|
211
|
-
end
|
212
|
-
end
|
213
|
-
|
214
|
-
script = preamble + "\n" + script_text
|
215
|
-
Log.debug "Installing software with script:\n" << script
|
216
|
-
CMD.cmd_log('bash', :in => script)
|
217
|
-
|
218
|
-
set_software_env(software_dir) unless $set_software_env
|
219
|
-
$set_software_env = true
|
129
|
+
software_dir = self.root.software
|
130
|
+
name = File.basename(path)
|
131
|
+
Resource.install(content, name, software_dir)
|
132
|
+
set_software_env(software_dir)
|
220
133
|
else
|
221
134
|
raise "Could not produce #{ resource }. (#{ type }, #{ content })"
|
222
135
|
end
|
@@ -0,0 +1,176 @@
|
|
1
|
+
module Resource
|
2
|
+
|
3
|
+
def self.install_helpers
|
4
|
+
File.expand_path(Scout.share.software.install_helpers.find(:lib))
|
5
|
+
end
|
6
|
+
|
7
|
+
def self.install(content, name, software_dir = Path.setup('software'), &block)
|
8
|
+
software_dir ||= Path.setup('software')
|
9
|
+
software_dir = software_dir.find if Path === software_dir
|
10
|
+
|
11
|
+
content = block if block_given?
|
12
|
+
|
13
|
+
preamble = <<-EOF
|
14
|
+
#!/bin/bash
|
15
|
+
|
16
|
+
SOFTWARE_DIR="#{software_dir}"
|
17
|
+
|
18
|
+
INSTALL_HELPER_FILE="#{install_helpers}"
|
19
|
+
source "$INSTALL_HELPER_FILE"
|
20
|
+
EOF
|
21
|
+
|
22
|
+
content = content.call if Proc === content
|
23
|
+
|
24
|
+
name = content[:name] if Hash === content && content.include?(:name)
|
25
|
+
content =
|
26
|
+
if content =~ /git:|\.git$/
|
27
|
+
{:git => content}
|
28
|
+
else
|
29
|
+
{:src => content}
|
30
|
+
end if String === content and Open.remote?(content)
|
31
|
+
|
32
|
+
script_text =
|
33
|
+
case content
|
34
|
+
when nil
|
35
|
+
raise "No way to install #{name}"
|
36
|
+
when Path
|
37
|
+
Open.read(content)
|
38
|
+
when String
|
39
|
+
if Path.is_filename?(content) and Open.exists?(content)
|
40
|
+
Open.read(content)
|
41
|
+
else
|
42
|
+
content
|
43
|
+
end
|
44
|
+
when Hash
|
45
|
+
name = content[:name] || name
|
46
|
+
git = content[:git]
|
47
|
+
src = content[:src]
|
48
|
+
url = content[:url]
|
49
|
+
jar = content[:jar]
|
50
|
+
extra = content[:extra]
|
51
|
+
commands = content[:commands]
|
52
|
+
if git
|
53
|
+
<<-EOF
|
54
|
+
|
55
|
+
name='#{name}'
|
56
|
+
url='#{git}'
|
57
|
+
|
58
|
+
install_git "$name" "$url" #{extra}
|
59
|
+
|
60
|
+
#{commands}
|
61
|
+
EOF
|
62
|
+
elsif src
|
63
|
+
<<-EOF
|
64
|
+
|
65
|
+
name='#{name}'
|
66
|
+
url='#{src}'
|
67
|
+
|
68
|
+
install_src "$name" "$url" #{extra}
|
69
|
+
|
70
|
+
#{commands}
|
71
|
+
EOF
|
72
|
+
elsif jar
|
73
|
+
<<-EOF
|
74
|
+
|
75
|
+
name='#{name}'
|
76
|
+
url='#{jar}'
|
77
|
+
|
78
|
+
install_jar "$name" "$url" #{extra}
|
79
|
+
|
80
|
+
#{commands}
|
81
|
+
EOF
|
82
|
+
else
|
83
|
+
<<-EOF
|
84
|
+
|
85
|
+
name='#{name}'
|
86
|
+
url='#{url}'
|
87
|
+
|
88
|
+
#{commands}
|
89
|
+
EOF
|
90
|
+
end
|
91
|
+
end
|
92
|
+
|
93
|
+
script = preamble + "\n" + script_text
|
94
|
+
Log.debug "Installing software #{name} into #{software_dir} with script:\n" << script
|
95
|
+
CMD.cmd_log('bash', :in => script)
|
96
|
+
Resource.set_software_env(software_dir)
|
97
|
+
end
|
98
|
+
|
99
|
+
def self.set_software_env(software_dir = Path.setup('software'))
|
100
|
+
software_dir.opt.find_all.collect{|d| d.annotate(File.dirname(d)) }.reverse.each do |software_dir|
|
101
|
+
next unless software_dir.exists?
|
102
|
+
Log.medium "Preparing software env at #{software_dir}"
|
103
|
+
|
104
|
+
software_dir = File.expand_path(software_dir)
|
105
|
+
opt_dir = File.join(software_dir, 'opt')
|
106
|
+
bin_dir = File.join(opt_dir, 'bin')
|
107
|
+
|
108
|
+
Misc.env_add 'PATH', bin_dir
|
109
|
+
|
110
|
+
FileUtils.mkdir_p opt_dir unless File.exist? opt_dir
|
111
|
+
|
112
|
+
%w(.ld-paths .c-paths .pkgconfig-paths .aclocal-paths .java-classpaths).each do |file|
|
113
|
+
filename = File.join(opt_dir, file)
|
114
|
+
begin
|
115
|
+
FileUtils.touch filename unless File.exist? filename
|
116
|
+
rescue
|
117
|
+
Log.warn("Could not touch #{ filename }")
|
118
|
+
end
|
119
|
+
end
|
120
|
+
|
121
|
+
Open.read(File.join opt_dir, '.c-paths').split(/\n/).each do |line|
|
122
|
+
dir = line.chomp
|
123
|
+
dir = File.join(opt_dir, dir) unless dir[0] == "/"
|
124
|
+
Misc.env_add('CPLUS_INCLUDE_PATH',dir)
|
125
|
+
Misc.env_add('C_INCLUDE_PATH',dir)
|
126
|
+
end if File.exist? File.join(opt_dir, '.c-paths')
|
127
|
+
|
128
|
+
Open.read(File.join opt_dir, '.ld-paths').split(/\n/).each do |line|
|
129
|
+
dir = line.chomp
|
130
|
+
dir = File.join(opt_dir, dir) unless dir[0] == "/"
|
131
|
+
Misc.env_add('LIBRARY_PATH',dir)
|
132
|
+
Misc.env_add('LD_LIBRARY_PATH',dir)
|
133
|
+
Misc.env_add('LD_RUN_PATH',dir)
|
134
|
+
end if File.exist? File.join(opt_dir, '.ld-paths')
|
135
|
+
|
136
|
+
Open.read(File.join opt_dir, '.pkgconfig-paths').split(/\n/).each do |line|
|
137
|
+
dir = line.chomp
|
138
|
+
dir = File.join(opt_dir, dir) unless dir[0] == "/"
|
139
|
+
Misc.env_add('PKG_CONFIG_PATH',dir)
|
140
|
+
end if File.exist? File.join(opt_dir, '.pkgconfig-paths')
|
141
|
+
|
142
|
+
Open.read(File.join opt_dir, '.aclocal-paths').split(/\n/).each do |line|
|
143
|
+
dir = line.chomp
|
144
|
+
dir = File.join(opt_dir, dir) unless dir[0] == "/"
|
145
|
+
Misc.env_add('ACLOCAL_FLAGS', "-I #{dir}", ' ')
|
146
|
+
end if File.exist? File.join(opt_dir, '.aclocal-paths')
|
147
|
+
|
148
|
+
Open.read(File.join opt_dir, '.java-classpaths').split(/\n/).each do |line|
|
149
|
+
dir = line.chomp
|
150
|
+
dir = File.join(opt_dir, dir) unless dir[0] == "/"
|
151
|
+
Misc.env_add('CLASSPATH', "#{dir}")
|
152
|
+
end if File.exist? File.join(opt_dir, '.java-classpaths')
|
153
|
+
|
154
|
+
Dir.glob(File.join opt_dir, 'jars', '*.jar').each do |file|
|
155
|
+
Misc.env_add('CLASSPATH', "#{file}")
|
156
|
+
end
|
157
|
+
|
158
|
+
if File.exist?(File.join(opt_dir, '.post_install')) and File.directory?(File.join(opt_dir, '.post_install'))
|
159
|
+
Dir.glob(File.join(opt_dir, '.post_install','*')).each do |file|
|
160
|
+
|
161
|
+
# Load exports
|
162
|
+
Open.read(file).split("\n").each do |line|
|
163
|
+
next unless line =~ /^\s*export\s+([^=]+)=(.*)/
|
164
|
+
var = $1.strip
|
165
|
+
value = $2.strip
|
166
|
+
value.sub!(/^['"]/,'')
|
167
|
+
value.sub!(/['"]$/,'')
|
168
|
+
value.gsub!(/\$[a-z_0-9]+/i){|var| ENV[var[1..-1]] }
|
169
|
+
Log.debug "Set variable export from .post_install: #{Misc.fingerprint [var,value]*"="}"
|
170
|
+
ENV[var] = value
|
171
|
+
end
|
172
|
+
end
|
173
|
+
end
|
174
|
+
end
|
175
|
+
end
|
176
|
+
end
|