rbbt-util 5.32.4 → 5.32.10
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/lib/rbbt/hpc/slurm.rb +4 -0
- data/lib/rbbt/persist/tsv/adapter.rb +1 -5
- data/lib/rbbt/resource.rb +58 -40
- data/lib/rbbt/util/cmd.rb +14 -4
- data/lib/rbbt/util/migrate.rb +118 -0
- data/lib/rbbt/workflow.rb +11 -0
- data/lib/rbbt/workflow/util/archive.rb +31 -102
- data/share/rbbt_commands/hpc/orchestrate +3 -1
- data/share/rbbt_commands/hpc/task +3 -1
- data/share/rbbt_commands/lsf/clean +212 -0
- data/share/rbbt_commands/lsf/list +311 -0
- data/share/rbbt_commands/lsf/orchestrate +58 -0
- data/share/rbbt_commands/lsf/tail +55 -0
- data/share/rbbt_commands/lsf/task +57 -0
- data/share/rbbt_commands/migrate +3 -76
- data/share/rbbt_commands/slurm/clean +212 -0
- data/share/rbbt_commands/slurm/list +311 -0
- data/share/rbbt_commands/slurm/orchestrate +58 -0
- data/share/rbbt_commands/slurm/tail +55 -0
- data/share/rbbt_commands/slurm/task +57 -0
- data/test/rbbt/util/test_migrate.rb +36 -0
- data/test/rbbt/workflow/util/test_archive.rb +31 -0
- metadata +18 -3
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 258c55a2b59d81426d1aa3980f35104ef193774068330b25c9aad29061d70e6a
|
|
4
|
+
data.tar.gz: 8265a128c161349455f7803d5a70a259c03481bb7a441aa1ffec58626fbb0226
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: 8eb143ab5cf5e4e55851ccd11b24eeae7d3e60948e30a71de3b5fb87f5333d7e40823b268d6ac894eea5d3d73ffa47101f7bb229378837799597df54545bb8c8
|
|
7
|
+
data.tar.gz: 0ebddaae9d523d9dd767dfde1b351b011ba3dd65c4abd7c0bcc0e78cc3e604a6850250bf0e74dac9f5ca0172a56a067541bdc34b5037e2ffc7ba972558f2ce4c
|
data/lib/rbbt/hpc/slurm.rb
CHANGED
|
@@ -28,6 +28,8 @@ export BATCH_SYSTEM=SLURM
|
|
|
28
28
|
workdir = Misc.process_options options, :workdir
|
|
29
29
|
exclusive = Misc.process_options options, :exclusive
|
|
30
30
|
highmem = Misc.process_options options, :highmem
|
|
31
|
+
licenses = Misc.process_options options, :licenses
|
|
32
|
+
constraint = Misc.process_options options, :constraint
|
|
31
33
|
|
|
32
34
|
batch_dir = Misc.process_options options, :batch_dir
|
|
33
35
|
batch_name = Misc.process_options options, :batch_name
|
|
@@ -51,6 +53,8 @@ export BATCH_SYSTEM=SLURM
|
|
|
51
53
|
|
|
52
54
|
header << "#SBATCH --exclusive" << "\n" if exclusive
|
|
53
55
|
header << "#SBATCH --constraint=highmem" << "\n" if highmem
|
|
56
|
+
header << "#SBATCH --licenses=#{licenses}" << "\n" if licenses
|
|
57
|
+
header << "#SBATCH --constraint=#{constraint}" << "\n" if constraint
|
|
54
58
|
|
|
55
59
|
header
|
|
56
60
|
end
|
data/lib/rbbt/resource.rb
CHANGED
|
@@ -4,10 +4,10 @@ require 'rbbt/resource/path'
|
|
|
4
4
|
require 'net/http'
|
|
5
5
|
require 'set'
|
|
6
6
|
|
|
7
|
-
|
|
8
7
|
module Resource
|
|
9
8
|
class ResourceNotFound < RbbtException; end
|
|
10
9
|
|
|
10
|
+
|
|
11
11
|
class << self
|
|
12
12
|
attr_accessor :lock_dir
|
|
13
13
|
|
|
@@ -90,51 +90,62 @@ module Resource
|
|
|
90
90
|
uri = URI(url)
|
|
91
91
|
|
|
92
92
|
http = Net::HTTP.new(uri.host, uri.port)
|
|
93
|
-
|
|
93
|
+
|
|
94
|
+
if uri.scheme == "https"
|
|
95
|
+
http.use_ssl = true
|
|
96
|
+
http.verify_mode = OpenSSL::SSL::VERIFY_NONE
|
|
97
|
+
http.instance_variable_set("@ssl_options", OpenSSL::SSL::OP_NO_SSLv2 + OpenSSL::SSL::OP_NO_SSLv3 + OpenSSL::SSL::OP_NO_COMPRESSION)
|
|
98
|
+
end
|
|
99
|
+
|
|
94
100
|
timeout = 60 * 10
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
101
|
+
http.read_timeout = timeout
|
|
102
|
+
http.open_timeout = timeout
|
|
103
|
+
request = Net::HTTP::Get.new(uri.request_uri)
|
|
104
|
+
http.request request do |response|
|
|
105
|
+
filename = if response["Content-Disposition"]
|
|
106
|
+
response["Content-Disposition"].split(";").select{|f| f.include? "filename"}.collect{|f| f.split("=").last.gsub('"','')}.first
|
|
107
|
+
else
|
|
108
|
+
nil
|
|
109
|
+
end
|
|
110
|
+
|
|
111
|
+
if filename && filename =~ /\.b?gz$/ && final_path !~ /\.b?gz$/
|
|
112
|
+
extension = filename.split(".").last
|
|
113
|
+
final_path += '.' + extension
|
|
114
|
+
end
|
|
115
|
+
case response
|
|
116
|
+
when Net::HTTPSuccess, Net::HTTPOK
|
|
117
|
+
Misc.sensiblewrite(final_path) do |file|
|
|
118
|
+
response.read_body do |chunk|
|
|
119
|
+
file.write chunk
|
|
113
120
|
end
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
FileUtils.mv tmp_dir, final_path
|
|
124
|
-
end
|
|
125
|
-
else
|
|
126
|
-
Open.open(location, :nocache => true) do |s|
|
|
127
|
-
Misc.sensiblewrite(final_path, s)
|
|
121
|
+
end
|
|
122
|
+
when Net::HTTPRedirection, Net::HTTPFound
|
|
123
|
+
location = response['location']
|
|
124
|
+
if location.include? 'get_directory'
|
|
125
|
+
Log.debug("Feching directory from: #{location}. Into: #{final_path}")
|
|
126
|
+
FileUtils.mkdir_p final_path unless File.exist? final_path
|
|
127
|
+
TmpFile.with_file do |tmp_dir|
|
|
128
|
+
Misc.in_dir tmp_dir do
|
|
129
|
+
CMD.cmd('tar xvfz -', :in => Open.open(location, :nocache => true))
|
|
128
130
|
end
|
|
131
|
+
FileUtils.mv tmp_dir, final_path
|
|
129
132
|
end
|
|
130
|
-
when Net::HTTPInternalServerError
|
|
131
|
-
@server_missing_resource_cache << url
|
|
132
|
-
raise "Resource Not Found"
|
|
133
133
|
else
|
|
134
|
-
|
|
134
|
+
url = location
|
|
135
|
+
raise TryAgain
|
|
136
|
+
#Open.open(location, :nocache => true) do |s|
|
|
137
|
+
# Misc.sensiblewrite(final_path, s)
|
|
138
|
+
#end
|
|
135
139
|
end
|
|
140
|
+
when Net::HTTPInternalServerError
|
|
141
|
+
@server_missing_resource_cache << url
|
|
142
|
+
raise "Resource Not Found"
|
|
143
|
+
else
|
|
144
|
+
raise "Response not understood: #{response.inspect}"
|
|
136
145
|
end
|
|
137
146
|
end
|
|
147
|
+
rescue TryAgain
|
|
148
|
+
retry
|
|
138
149
|
end
|
|
139
150
|
rescue
|
|
140
151
|
Log.warn "Could not retrieve (#{self.to_s}) #{ path } from #{ remote_server }"
|
|
@@ -159,7 +170,11 @@ module Resource
|
|
|
159
170
|
begin
|
|
160
171
|
produce(path.annotate(path + '.gz'), force)
|
|
161
172
|
rescue ResourceNotFound
|
|
162
|
-
|
|
173
|
+
begin
|
|
174
|
+
produce(path.annotate(path + '.bgz'), force)
|
|
175
|
+
rescue ResourceNotFound
|
|
176
|
+
raise ResourceNotFound, "Resource is missing and does not seem to be claimed: #{ self } -- #{ path } "
|
|
177
|
+
end
|
|
163
178
|
end
|
|
164
179
|
else
|
|
165
180
|
raise ResourceNotFound, "Resource is missing and does not seem to be claimed: #{ self } -- #{ path } "
|
|
@@ -309,7 +324,10 @@ url='#{url}'
|
|
|
309
324
|
def identify(path)
|
|
310
325
|
path = File.expand_path(path)
|
|
311
326
|
resource ||= Rbbt
|
|
312
|
-
(Path::STANDARD_SEARCH + resource.search_order + resource.search_paths.keys)
|
|
327
|
+
locations = (Path::STANDARD_SEARCH + resource.search_order + resource.search_paths.keys)
|
|
328
|
+
locations -= [:current, "current"]
|
|
329
|
+
locations << :current
|
|
330
|
+
locations.uniq.each do |name|
|
|
313
331
|
pattern = resource.search_paths[name]
|
|
314
332
|
next if pattern.nil?
|
|
315
333
|
pattern = pattern.sub('{PWD}', Dir.pwd)
|
data/lib/rbbt/util/cmd.rb
CHANGED
|
@@ -248,16 +248,26 @@ module CMD
|
|
|
248
248
|
pid = io.pids.first
|
|
249
249
|
|
|
250
250
|
line = "" if bar
|
|
251
|
+
starting = true
|
|
251
252
|
while c = io.getc
|
|
252
|
-
|
|
253
|
-
line << c if bar
|
|
254
|
-
if c == "\n"
|
|
255
|
-
bar.process(line) if bar
|
|
253
|
+
if starting
|
|
256
254
|
if pid
|
|
257
255
|
Log.logn "STDOUT [#{pid}]: ", level
|
|
258
256
|
else
|
|
259
257
|
Log.logn "STDOUT: ", level
|
|
260
258
|
end
|
|
259
|
+
starting = false
|
|
260
|
+
end
|
|
261
|
+
STDERR << c if Log.severity <= level
|
|
262
|
+
line << c if bar
|
|
263
|
+
if c == "\n"
|
|
264
|
+
bar.process(line) if bar
|
|
265
|
+
starting = true
|
|
266
|
+
#if pid
|
|
267
|
+
# Log.logn "STDOUT [#{pid}]: ", level
|
|
268
|
+
#else
|
|
269
|
+
# Log.logn "STDOUT: ", level
|
|
270
|
+
#end
|
|
261
271
|
line = "" if bar
|
|
262
272
|
end
|
|
263
273
|
end
|
|
@@ -0,0 +1,118 @@
|
|
|
1
|
+
module Rbbt
|
|
2
|
+
def self.migrate_source_paths(path, resource = Rbbt, source = nil)
|
|
3
|
+
if source
|
|
4
|
+
lpath, *paths = Misc.ssh_run(source, <<-EOF).split("\n")
|
|
5
|
+
require 'rbbt-util'
|
|
6
|
+
path = "#{path}"
|
|
7
|
+
if Open.exists?(path)
|
|
8
|
+
path = #{resource.to_s}.identify(path)
|
|
9
|
+
else
|
|
10
|
+
path = Path.setup(path)
|
|
11
|
+
end
|
|
12
|
+
puts path
|
|
13
|
+
puts path.glob_all.collect{|p| File.directory?(p) ? p + "/" : p } * "\n"
|
|
14
|
+
EOF
|
|
15
|
+
|
|
16
|
+
[path, paths.collect{|p| [source, p] * ":"}, lpath]
|
|
17
|
+
else
|
|
18
|
+
if File.exists?(path)
|
|
19
|
+
path = resource.identify(path)
|
|
20
|
+
else
|
|
21
|
+
path = Path.setup(path)
|
|
22
|
+
end
|
|
23
|
+
|
|
24
|
+
[path, (path.directory? ? path.glob_all : path.find_all), path]
|
|
25
|
+
end
|
|
26
|
+
end
|
|
27
|
+
|
|
28
|
+
def self.migrate_target_path(path, search_path = 'user', resource = Rbbt, target = nil)
|
|
29
|
+
if target
|
|
30
|
+
Misc.ssh_run(target, <<-EOF).split("\n").first
|
|
31
|
+
require 'rbbt-util'
|
|
32
|
+
path = "#{path}"
|
|
33
|
+
resource = #{resource.to_s}
|
|
34
|
+
search_path = "#{search_path}"
|
|
35
|
+
puts resource[path].find(search_path)
|
|
36
|
+
EOF
|
|
37
|
+
else
|
|
38
|
+
resource[path].find(search_path)
|
|
39
|
+
end
|
|
40
|
+
end
|
|
41
|
+
|
|
42
|
+
def self.migrate_files(real_paths, target, options = {})
|
|
43
|
+
excludes = %w(.save .crap .source tmp filecache open-remote)
|
|
44
|
+
excludes += (options[:exclude] || "").split(/,\s*/)
|
|
45
|
+
excludes_str = excludes.collect{|s| "--exclude '#{s}'" } * " "
|
|
46
|
+
|
|
47
|
+
other = options[:other] || []
|
|
48
|
+
|
|
49
|
+
test_str = options[:test] ? '-nv' : ''
|
|
50
|
+
|
|
51
|
+
real_paths.each do |source_path|
|
|
52
|
+
if File.directory?(source_path) || source_path =~ /\/$/
|
|
53
|
+
source_path += "/" unless source_path[-1] == "/"
|
|
54
|
+
target += "/" unless target[-1] == "/"
|
|
55
|
+
end
|
|
56
|
+
|
|
57
|
+
next if source_path == target
|
|
58
|
+
|
|
59
|
+
if options[:target]
|
|
60
|
+
CMD.cmd("ssh #{options[:target]} mkdir -p '#{File.dirname(target)}'")
|
|
61
|
+
else
|
|
62
|
+
Open.mkdir File.dirname(target)
|
|
63
|
+
end
|
|
64
|
+
|
|
65
|
+
if options[:target]
|
|
66
|
+
target_path = [options[:target], "'" + target + "'"] * ":"
|
|
67
|
+
else
|
|
68
|
+
target_path = "'" + target + "'"
|
|
69
|
+
end
|
|
70
|
+
|
|
71
|
+
TmpFile.with_file do |tmp_files|
|
|
72
|
+
if options[:files]
|
|
73
|
+
Open.write(tmp_files, options[:files] * "\n")
|
|
74
|
+
files_from_str = "--files-from='#{tmp_files}'"
|
|
75
|
+
else
|
|
76
|
+
files_from_str = ""
|
|
77
|
+
end
|
|
78
|
+
|
|
79
|
+
cmd = "rsync -avztAXHP --copy-unsafe-links #{test_str} #{files_from_str} #{excludes_str} '#{source_path}' #{target_path} #{other * " "}"
|
|
80
|
+
|
|
81
|
+
|
|
82
|
+
cmd << " && rm -Rf #{source_path}" if options[:delete] && ! options[:files]
|
|
83
|
+
|
|
84
|
+
if options[:print]
|
|
85
|
+
puts cmd
|
|
86
|
+
exit 0
|
|
87
|
+
else
|
|
88
|
+
CMD.cmd_log(cmd, :log => Log::INFO)
|
|
89
|
+
|
|
90
|
+
if options[:delete] && options[:files]
|
|
91
|
+
remove_files = options[:files].collect{|f| File.join(source_path, f) }
|
|
92
|
+
dirs = remove_files.select{|f| File.directory? f }
|
|
93
|
+
remove_files.each do |file|
|
|
94
|
+
next if dirs.include? file
|
|
95
|
+
Open.rm file
|
|
96
|
+
end
|
|
97
|
+
dirs.each do |dir|
|
|
98
|
+
FileUtils.rmdir dir if Dir.glob(dir).empty?
|
|
99
|
+
end
|
|
100
|
+
end
|
|
101
|
+
end
|
|
102
|
+
end
|
|
103
|
+
end
|
|
104
|
+
end
|
|
105
|
+
|
|
106
|
+
|
|
107
|
+
def self.migrate(path, search_path, options = {})
|
|
108
|
+
search_path = 'user' if search_path.nil?
|
|
109
|
+
|
|
110
|
+
resource = Rbbt
|
|
111
|
+
|
|
112
|
+
path, real_paths, lpath = migrate_source_paths(path, resource, options[:source])
|
|
113
|
+
|
|
114
|
+
target = migrate_target_path(lpath, search_path, resource, options[:target])
|
|
115
|
+
|
|
116
|
+
migrate_files(real_paths, target, options)
|
|
117
|
+
end
|
|
118
|
+
end
|
data/lib/rbbt/workflow.rb
CHANGED
|
@@ -600,6 +600,17 @@ module Workflow
|
|
|
600
600
|
true
|
|
601
601
|
end
|
|
602
602
|
end
|
|
603
|
+
|
|
604
|
+
if ! Open.exists?(step.info_file)
|
|
605
|
+
begin
|
|
606
|
+
workflow = step.path.split("/")[-3]
|
|
607
|
+
task_name = step.path.split("/")[-2]
|
|
608
|
+
workflow = Kernel.const_get workflow
|
|
609
|
+
step.task = workflow.tasks[task_name.to_sym]
|
|
610
|
+
rescue
|
|
611
|
+
Log.exception $!
|
|
612
|
+
end
|
|
613
|
+
end
|
|
603
614
|
step
|
|
604
615
|
end
|
|
605
616
|
|
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
require 'rbbt/util/migrate'
|
|
1
2
|
class Step
|
|
2
3
|
|
|
3
4
|
MAIN_RSYNC_ARGS="-avztAXHP --copy-links"
|
|
@@ -126,63 +127,48 @@ class Step
|
|
|
126
127
|
end
|
|
127
128
|
end
|
|
128
129
|
|
|
129
|
-
def self.
|
|
130
|
-
resource=Rbbt
|
|
131
|
-
|
|
132
|
-
orig_path = path
|
|
133
|
-
other_rsync_args = options[:rsync]
|
|
134
|
-
|
|
135
|
-
recursive = options[:recursive]
|
|
130
|
+
def self.migrate_source_paths(path, resource = Rbbt, source = nil, recursive = true)
|
|
136
131
|
recursive = false if recursive.nil?
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
Misc.ssh_run(options[:source], <<-EOF).split("\n")
|
|
132
|
+
if source
|
|
133
|
+
lpath, *paths = Misc.ssh_run(source, <<-EOF).split("\n")
|
|
140
134
|
require 'rbbt-util'
|
|
141
135
|
require 'rbbt/workflow'
|
|
142
136
|
|
|
143
|
-
path = "#{path}"
|
|
144
137
|
recursive = #{ recursive.to_s }
|
|
138
|
+
path = "#{path}"
|
|
145
139
|
|
|
146
|
-
if
|
|
140
|
+
if Open.exists?(path)
|
|
147
141
|
path = #{resource.to_s}.identify(path)
|
|
148
142
|
else
|
|
149
143
|
path = Path.setup(path)
|
|
150
144
|
end
|
|
151
145
|
|
|
152
|
-
files = path.glob_all
|
|
153
|
-
|
|
146
|
+
files = path.glob_all.collect{|p| File.directory?(p) ? p + "/" : p }
|
|
154
147
|
files = Step.job_files_for_archive(files, recursive)
|
|
155
148
|
|
|
149
|
+
puts path
|
|
156
150
|
puts files * "\n"
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
path = "var/jobs"
|
|
176
|
-
resource = #{resource.to_s}
|
|
177
|
-
search_path = "#{search_path}"
|
|
178
|
-
puts resource[path].find(search_path)
|
|
179
|
-
EOF
|
|
180
|
-
else
|
|
181
|
-
resource['var/jobs'].find(search_path)
|
|
182
|
-
end
|
|
151
|
+
EOF
|
|
152
|
+
|
|
153
|
+
[path, paths.collect{|p| [source, p] * ":"}, lpath]
|
|
154
|
+
else
|
|
155
|
+
path = Path.setup(path.dup)
|
|
156
|
+
files = path.glob_all
|
|
157
|
+
files = Step.job_files_for_archive(files, recursive)
|
|
158
|
+
|
|
159
|
+
[path, files, path]
|
|
160
|
+
end
|
|
161
|
+
end
|
|
162
|
+
|
|
163
|
+
def self.migrate(path, search_path, options = {})
|
|
164
|
+
search_path = 'user' if search_path.nil?
|
|
165
|
+
|
|
166
|
+
resource = Rbbt
|
|
167
|
+
|
|
168
|
+
path, real_paths, lpath = self.migrate_source_paths(path, resource, options[:source], options[:recursive])
|
|
183
169
|
|
|
184
170
|
subpath_files = {}
|
|
185
|
-
|
|
171
|
+
real_paths.sort.each do |path|
|
|
186
172
|
parts = path.split("/")
|
|
187
173
|
subpath = parts[0..-4] * "/" + "/"
|
|
188
174
|
|
|
@@ -190,73 +176,16 @@ puts resource[path].find(search_path)
|
|
|
190
176
|
subpath = subpath_files.keys.last
|
|
191
177
|
end
|
|
192
178
|
|
|
193
|
-
source = path[subpath.length..-1]
|
|
179
|
+
source = path.chars[subpath.length..-1] * ""
|
|
194
180
|
|
|
195
181
|
subpath_files[subpath] ||= []
|
|
196
182
|
subpath_files[subpath] << source
|
|
197
183
|
end
|
|
198
184
|
|
|
199
|
-
|
|
200
|
-
subpath_files.each do |subpath, files|
|
|
201
|
-
if options[:target]
|
|
202
|
-
CMD.cmd("ssh #{options[:target]} mkdir -p '#{File.dirname(target)}'")
|
|
203
|
-
else
|
|
204
|
-
Open.mkdir File.dirname(target)
|
|
205
|
-
end
|
|
185
|
+
target = Rbbt.migrate_target_path('var/jobs', search_path, resource, options[:target])
|
|
206
186
|
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
else
|
|
210
|
-
source = subpath
|
|
211
|
-
end
|
|
212
|
-
target = [options[:target], target] * ":" if options[:target]
|
|
213
|
-
|
|
214
|
-
next if File.exists?(source) && File.exists?(target) && File.expand_path(source) == File.expand_path(target)
|
|
215
|
-
|
|
216
|
-
files_and_dirs = Set.new( files )
|
|
217
|
-
files.each do |file|
|
|
218
|
-
synced_files << File.join(subpath, file)
|
|
219
|
-
|
|
220
|
-
parts = file.split("/")[0..-2].reject{|p| p.empty?}
|
|
221
|
-
while parts.any?
|
|
222
|
-
files_and_dirs << parts * "/"
|
|
223
|
-
parts.pop
|
|
224
|
-
end
|
|
225
|
-
end
|
|
226
|
-
|
|
227
|
-
TmpFile.with_file(files_and_dirs.sort_by{|l| l.length}.to_a * "\n") do |tmp_include_file|
|
|
228
|
-
test_str = options[:test] ? '-nv' : ''
|
|
229
|
-
|
|
230
|
-
cmd = "rsync #{MAIN_RSYNC_ARGS} --progress #{test_str} --files-from='#{tmp_include_file}' #{source}/ #{target}/ #{other_rsync_args}"
|
|
231
|
-
|
|
232
|
-
#cmd << " && rm -Rf #{source}" if options[:delete]
|
|
233
|
-
if options[:print]
|
|
234
|
-
ppp Open.read(tmp_include_file)
|
|
235
|
-
puts cmd
|
|
236
|
-
else
|
|
237
|
-
CMD.cmd_log(cmd, :log => Log::INFO)
|
|
238
|
-
end
|
|
239
|
-
end
|
|
240
|
-
end
|
|
241
|
-
|
|
242
|
-
if options[:delete] && synced_files.any?
|
|
243
|
-
puts Log.color :magenta, "About to erase these files:"
|
|
244
|
-
synced_files.each do |p|
|
|
245
|
-
puts Log.color :red, p
|
|
246
|
-
end
|
|
247
|
-
|
|
248
|
-
if options[:non_interactive]
|
|
249
|
-
response = 'yes'
|
|
250
|
-
else
|
|
251
|
-
puts Log.color :magenta, "Type 'yes' if you are sure:"
|
|
252
|
-
response = STDIN.gets.chomp
|
|
253
|
-
end
|
|
254
|
-
|
|
255
|
-
if response == 'yes'
|
|
256
|
-
synced_files.each do |p|
|
|
257
|
-
Open.rm p
|
|
258
|
-
end
|
|
259
|
-
end
|
|
187
|
+
subpath_files.each do |subpath, files|
|
|
188
|
+
Rbbt.migrate_files([subpath], target, options.merge(:files => files))
|
|
260
189
|
end
|
|
261
190
|
end
|
|
262
191
|
|