rbbt-util 5.44.1 → 6.0.4

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.
Files changed (175) hide show
  1. checksums.yaml +4 -4
  2. data/LICENSE +1 -1
  3. data/bin/rbbt +67 -90
  4. data/bin/rbbt_exec.rb +2 -2
  5. data/etc/app.d/base.rb +2 -2
  6. data/etc/app.d/semaphores.rb +3 -3
  7. data/lib/rbbt/annotations/annotated_array.rb +207 -207
  8. data/lib/rbbt/annotations/refactor.rb +27 -0
  9. data/lib/rbbt/annotations/util.rb +282 -282
  10. data/lib/rbbt/annotations.rb +343 -320
  11. data/lib/rbbt/association/database.rb +200 -225
  12. data/lib/rbbt/association/index.rb +294 -291
  13. data/lib/rbbt/association/item.rb +227 -227
  14. data/lib/rbbt/association/open.rb +35 -34
  15. data/lib/rbbt/association/util.rb +0 -169
  16. data/lib/rbbt/association.rb +2 -4
  17. data/lib/rbbt/entity/identifiers.rb +119 -118
  18. data/lib/rbbt/entity/refactor.rb +12 -0
  19. data/lib/rbbt/entity.rb +319 -315
  20. data/lib/rbbt/hpc/batch.rb +72 -53
  21. data/lib/rbbt/hpc/lsf.rb +2 -2
  22. data/lib/rbbt/hpc/orchestrate/batches.rb +2 -2
  23. data/lib/rbbt/hpc/orchestrate/chains.rb +25 -5
  24. data/lib/rbbt/hpc/orchestrate/rules.rb +2 -2
  25. data/lib/rbbt/hpc/orchestrate.rb +19 -13
  26. data/lib/rbbt/hpc/slurm.rb +18 -18
  27. data/lib/rbbt/knowledge_base/entity.rb +13 -5
  28. data/lib/rbbt/knowledge_base/query.rb +2 -2
  29. data/lib/rbbt/knowledge_base/registry.rb +32 -31
  30. data/lib/rbbt/knowledge_base/traverse.rb +1 -1
  31. data/lib/rbbt/knowledge_base.rb +1 -1
  32. data/lib/rbbt/monitor.rb +36 -25
  33. data/lib/rbbt/persist/refactor.rb +166 -0
  34. data/lib/rbbt/persist/tsv/tokyocabinet.rb +105 -105
  35. data/lib/rbbt/persist/tsv.rb +187 -185
  36. data/lib/rbbt/persist.rb +556 -551
  37. data/lib/rbbt/refactor.rb +20 -0
  38. data/lib/rbbt/resource/path/refactor.rb +178 -0
  39. data/lib/rbbt/resource/path.rb +317 -497
  40. data/lib/rbbt/resource/util.rb +0 -48
  41. data/lib/rbbt/resource.rb +3 -390
  42. data/lib/rbbt/tsv/accessor.rb +2 -838
  43. data/lib/rbbt/tsv/attach.rb +303 -299
  44. data/lib/rbbt/tsv/change_id.rb +244 -245
  45. data/lib/rbbt/tsv/csv.rb +87 -85
  46. data/lib/rbbt/tsv/dumper.rb +2 -100
  47. data/lib/rbbt/tsv/excel.rb +26 -24
  48. data/lib/rbbt/tsv/field_index.rb +4 -1
  49. data/lib/rbbt/tsv/filter.rb +3 -2
  50. data/lib/rbbt/tsv/index.rb +2 -284
  51. data/lib/rbbt/tsv/manipulate.rb +750 -747
  52. data/lib/rbbt/tsv/marshal.rb +3 -3
  53. data/lib/rbbt/tsv/matrix.rb +2 -2
  54. data/lib/rbbt/tsv/parallel/through.rb +2 -1
  55. data/lib/rbbt/tsv/parallel/traverse.rb +783 -781
  56. data/lib/rbbt/tsv/parser.rb +678 -678
  57. data/lib/rbbt/tsv/refactor.rb +195 -0
  58. data/lib/rbbt/tsv/stream.rb +253 -251
  59. data/lib/rbbt/tsv/util.rb +420 -420
  60. data/lib/rbbt/tsv.rb +210 -208
  61. data/lib/rbbt/util/R/eval.rb +4 -4
  62. data/lib/rbbt/util/R/plot.rb +62 -166
  63. data/lib/rbbt/util/R.rb +21 -18
  64. data/lib/rbbt/util/cmd.rb +2 -318
  65. data/lib/rbbt/util/color.rb +269 -269
  66. data/lib/rbbt/util/colorize.rb +89 -89
  67. data/lib/rbbt/util/concurrency/processes/refactor.rb +22 -0
  68. data/lib/rbbt/util/concurrency/processes/worker.rb +2 -2
  69. data/lib/rbbt/util/concurrency/processes.rb +389 -386
  70. data/lib/rbbt/util/config.rb +169 -167
  71. data/lib/rbbt/util/filecache.rb +1 -1
  72. data/lib/rbbt/util/iruby.rb +20 -0
  73. data/lib/rbbt/util/log/progress/report.rb +241 -241
  74. data/lib/rbbt/util/log/progress/util.rb +99 -99
  75. data/lib/rbbt/util/log/progress.rb +102 -102
  76. data/lib/rbbt/util/log/refactor.rb +49 -0
  77. data/lib/rbbt/util/log.rb +486 -532
  78. data/lib/rbbt/util/migrate.rb +2 -2
  79. data/lib/rbbt/util/misc/concurrent_stream.rb +248 -246
  80. data/lib/rbbt/util/misc/development.rb +12 -11
  81. data/lib/rbbt/util/misc/exceptions.rb +117 -112
  82. data/lib/rbbt/util/misc/format.rb +2 -230
  83. data/lib/rbbt/util/misc/indiferent_hash.rb +2 -107
  84. data/lib/rbbt/util/misc/inspect.rb +2 -476
  85. data/lib/rbbt/util/misc/lock.rb +109 -106
  86. data/lib/rbbt/util/misc/omics.rb +9 -1
  87. data/lib/rbbt/util/misc/pipes.rb +765 -793
  88. data/lib/rbbt/util/misc/refactor.rb +20 -0
  89. data/lib/rbbt/util/misc/ssw.rb +27 -17
  90. data/lib/rbbt/util/misc/system.rb +92 -105
  91. data/lib/rbbt/util/misc.rb +39 -20
  92. data/lib/rbbt/util/named_array/refactor.rb +4 -0
  93. data/lib/rbbt/util/named_array.rb +3 -220
  94. data/lib/rbbt/util/open/refactor.rb +7 -0
  95. data/lib/rbbt/util/open.rb +3 -857
  96. data/lib/rbbt/util/procpath.rb +6 -6
  97. data/lib/rbbt/util/python/paths.rb +27 -0
  98. data/lib/rbbt/util/python/run.rb +115 -0
  99. data/lib/rbbt/util/python/script.rb +110 -0
  100. data/lib/rbbt/util/python/util.rb +3 -3
  101. data/lib/rbbt/util/python.rb +22 -81
  102. data/lib/rbbt/util/semaphore.rb +152 -148
  103. data/lib/rbbt/util/simpleopt.rb +9 -8
  104. data/lib/rbbt/util/ssh/refactor.rb +19 -0
  105. data/lib/rbbt/util/ssh.rb +122 -118
  106. data/lib/rbbt/util/tar.rb +117 -115
  107. data/lib/rbbt/util/tmpfile.rb +69 -67
  108. data/lib/rbbt/util/version.rb +2 -0
  109. data/lib/rbbt/workflow/refactor/entity.rb +11 -0
  110. data/lib/rbbt/workflow/refactor/export.rb +66 -0
  111. data/lib/rbbt/workflow/refactor/inputs.rb +24 -0
  112. data/lib/rbbt/workflow/refactor/recursive.rb +64 -0
  113. data/lib/rbbt/workflow/refactor/task_info.rb +66 -0
  114. data/lib/rbbt/workflow/refactor.rb +150 -0
  115. data/lib/rbbt/workflow/remote_workflow/driver/rest.rb +1 -2
  116. data/lib/rbbt/workflow/remote_workflow/driver/ssh.rb +55 -32
  117. data/lib/rbbt/workflow/remote_workflow/remote_step/rest.rb +3 -1
  118. data/lib/rbbt/workflow/remote_workflow/remote_step/ssh.rb +14 -5
  119. data/lib/rbbt/workflow/remote_workflow/remote_step.rb +19 -7
  120. data/lib/rbbt/workflow/remote_workflow.rb +6 -1
  121. data/lib/rbbt/workflow/step/run.rb +766 -766
  122. data/lib/rbbt/workflow/step/save_load_inputs.rb +254 -254
  123. data/lib/rbbt/workflow/step.rb +2 -362
  124. data/lib/rbbt/workflow/task.rb +118 -118
  125. data/lib/rbbt/workflow/usage.rb +289 -287
  126. data/lib/rbbt/workflow/util/archive.rb +6 -5
  127. data/lib/rbbt/workflow/util/data.rb +1 -1
  128. data/lib/rbbt/workflow/util/orchestrator.rb +249 -246
  129. data/lib/rbbt/workflow/util/trace.rb +79 -44
  130. data/lib/rbbt/workflow.rb +4 -882
  131. data/lib/rbbt-util.rb +21 -13
  132. data/lib/rbbt.rb +16 -3
  133. data/python/rbbt/__init__.py +96 -4
  134. data/python/rbbt/workflow/remote.py +104 -0
  135. data/python/rbbt/workflow.py +64 -0
  136. data/python/test.py +10 -0
  137. data/share/Rlib/plot.R +37 -37
  138. data/share/Rlib/svg.R +22 -5
  139. data/share/install/software/lib/install_helpers +1 -1
  140. data/share/rbbt_commands/hpc/list +2 -3
  141. data/share/rbbt_commands/hpc/orchestrate +4 -4
  142. data/share/rbbt_commands/hpc/tail +2 -0
  143. data/share/rbbt_commands/hpc/task +10 -7
  144. data/share/rbbt_commands/lsf/list +2 -3
  145. data/share/rbbt_commands/lsf/orchestrate +4 -4
  146. data/share/rbbt_commands/lsf/tail +2 -0
  147. data/share/rbbt_commands/lsf/task +10 -7
  148. data/share/rbbt_commands/migrate +1 -1
  149. data/share/rbbt_commands/pbs/list +2 -3
  150. data/share/rbbt_commands/pbs/orchestrate +4 -4
  151. data/share/rbbt_commands/pbs/tail +2 -0
  152. data/share/rbbt_commands/pbs/task +10 -7
  153. data/share/rbbt_commands/resource/produce +8 -1
  154. data/share/rbbt_commands/slurm/list +2 -3
  155. data/share/rbbt_commands/slurm/orchestrate +4 -4
  156. data/share/rbbt_commands/slurm/tail +2 -0
  157. data/share/rbbt_commands/slurm/task +10 -7
  158. data/share/rbbt_commands/system/clean +5 -5
  159. data/share/rbbt_commands/system/status +5 -5
  160. data/share/rbbt_commands/tsv/get +2 -3
  161. data/share/rbbt_commands/tsv/info +10 -13
  162. data/share/rbbt_commands/tsv/keys +18 -14
  163. data/share/rbbt_commands/tsv/slice +2 -2
  164. data/share/rbbt_commands/tsv/transpose +6 -2
  165. data/share/rbbt_commands/workflow/info +20 -24
  166. data/share/rbbt_commands/workflow/list +1 -1
  167. data/share/rbbt_commands/workflow/prov +20 -13
  168. data/share/rbbt_commands/workflow/retry +43 -0
  169. data/share/rbbt_commands/workflow/server +12 -2
  170. data/share/rbbt_commands/workflow/task +80 -73
  171. data/share/rbbt_commands/workflow/write_info +26 -9
  172. data/share/software/opt/ssw/ssw.c +861 -0
  173. data/share/software/opt/ssw/ssw.h +130 -0
  174. data/share/workflow_config.ru +3 -3
  175. metadata +45 -6
@@ -1,246 +1,249 @@
1
- require 'rbbt/workflow'
2
-
3
- module Workflow
4
- class Orchestrator
5
-
6
- def self.job_workload(job)
7
- workload = {job => []}
8
- return workload if job.done? && ! job.dirty?
9
-
10
- job.dependencies.each do |dep|
11
- next if dep.done? && ! job.dirty?
12
- workload.merge!(job_workload(dep))
13
- workload[job] += workload[dep]
14
- workload[job] << dep
15
- workload[job].uniq!
16
- end
17
-
18
- job.input_dependencies.each do |dep|
19
- next if dep.done? && ! job.dirty?
20
- workload.merge!(job_workload(dep))
21
- workload[job] += workload[dep]
22
- workload[job] << dep
23
- workload[job].uniq!
24
- end
25
-
26
- workload
27
- end
28
-
29
- def self.workload(jobs)
30
- jobs.inject({}) do |acc,job|
31
- Orchestrator.job_workload(job).each do |j,d|
32
- acc[j] = d unless acc.keys.collect{|k| k.path }.include? j.path
33
- end
34
- acc
35
- end
36
- end
37
-
38
- def self.job_rules(rules, job)
39
- workflow = job.workflow.to_s
40
- task_name = job.task_name.to_s
41
- defaults = rules["defaults"] || {}
42
-
43
- return IndiferentHash.setup(defaults) unless rules[workflow]
44
- return IndiferentHash.setup(defaults) unless rules[workflow][task_name]
45
-
46
- job_rules = IndiferentHash.setup(rules[workflow][task_name])
47
- defaults.each{|k,v| job_rules[k] = v if job_rules[k].nil? } if defaults
48
- job_rules
49
- end
50
-
51
- def self.purge_duplicates(candidates)
52
- seen = Set.new
53
- candidates.select do |job|
54
- if seen.include? job.path
55
- false
56
- else
57
- seen << job.path
58
- true
59
- end
60
- end
61
- end
62
-
63
- def self.job_resources(rules, job)
64
- resources = (job_rules(rules, job) || {})["resources"] || {}
65
-
66
- IndiferentHash.setup(resources)
67
-
68
- default_resources = rules["default_resources"]
69
- default_resources ||= rules["defaults"]["resources"] if rules["defaults"]
70
- default_resources ||= {}
71
-
72
- default_resources.each{|k,v| resources[k] ||= v } if default_resources
73
-
74
- resources = {:cpus => 1} if resources.empty?
75
- resources
76
- end
77
-
78
- def self.sort_candidates(candidates, rules)
79
- seen = Set.new
80
- candidates.sort_by do |job|
81
- - job_resources(rules, job).values.inject(0){|acc,e| acc += e}
82
- end
83
- end
84
-
85
- def self.candidates(workload, rules)
86
- if rules.empty?
87
- candidates = workload.
88
- select{|k,v| v.empty? }.
89
- collect{|k,v| k }.
90
- reject{|k| k.done? }
91
- else
92
- candidates = workload. #select{|k,v| Orchestrator.job_rules(rules, k) }.
93
- select{|k,v| v.empty? }.
94
- collect{|k,v| k }.
95
- reject{|k| k.done? }
96
- end
97
-
98
- top_level = workload.keys - workload.values.flatten
99
-
100
- candidates = purge_duplicates candidates
101
- candidates = sort_candidates candidates, rules
102
-
103
- candidates
104
- end
105
-
106
- def self.process(*args)
107
- self.new.process(*args)
108
- end
109
-
110
- attr_accessor :available_resources, :resources_requested, :resources_used, :timer
111
-
112
- def initialize(timer = 5, available_resources = nil)
113
- available_resources = {:cpus => Etc.nprocessors } if available_resources.nil?
114
- @timer = timer
115
- @available_resources = IndiferentHash.setup(available_resources)
116
- @resources_requested = IndiferentHash.setup({})
117
- @resources_used = IndiferentHash.setup({})
118
- end
119
-
120
- def release_resources(job)
121
- if resources_used[job]
122
- Log.debug "Orchestrator releasing resouces from #{job.path}"
123
- resources_used[job].each do |resource,value|
124
- next if resource == 'size'
125
- resources_requested[resource] -= value.to_i
126
- end
127
- resources_used.delete job
128
- end
129
- end
130
-
131
- def check_resources(rules, job)
132
- resources = Orchestrator.job_resources(rules, job)
133
-
134
- limit_resources = resources.select{|resource,value| available_resources[resource] && ((resources_requested[resource] || 0) + value) > available_resources[resource] }.collect{|resource,v| resource }
135
- if limit_resources.any?
136
- Log.debug "Orchestrator waiting on #{job.path} due to #{limit_resources * ", "}"
137
- else
138
-
139
- resources_used[job] = resources
140
- resources.each do |resource,value|
141
- resources_requested[resource] ||= 0
142
- resources_requested[resource] += value.to_i
143
- end
144
- Log.low "Orchestrator producing #{job.path} with resources #{resources}"
145
-
146
- return yield
147
- end
148
- end
149
-
150
- def run_with_rules(rules, job)
151
- job_rules = Orchestrator.job_rules(rules, job)
152
-
153
- Rbbt::Config.with_config do
154
- job_rules[:config_keys].each do |config|
155
- Rbbt::Config.process_config config
156
- end if job_rules && job_rules[:config_keys]
157
-
158
- log = job_rules[:log] if job_rules
159
- log = Log.severity if log.nil?
160
- Log.with_severity log do
161
- job.produce(false, :nowait)
162
- end
163
- end
164
- end
165
-
166
- def erase_job_dependencies(job, rules, all_jobs, top_level_jobs)
167
- job.dependencies.each do |dep|
168
- next if top_level_jobs.include? dep.path
169
- next unless Orchestrator.job_rules(rules, dep)["erase"].to_s == 'true'
170
-
171
- dep_path = dep.path
172
- parents = all_jobs.select do |parent|
173
- paths = parent.info[:dependencies].nil? ? parent.dependencies.collect{|d| d.path } : parent.info[:dependencies].collect{|d| d.last }
174
- paths.include? dep_path
175
- end
176
-
177
- next unless parents.reject{|parent| parent.done? }.empty?
178
-
179
- parents.each do |parent|
180
- Log.high "Erasing #{dep.path} from #{parent.path}"
181
- parent.archive_deps
182
- parent.copy_files_dir
183
- parent.dependencies = parent.dependencies - [dep]
184
- end
185
- dep.clean
186
- end
187
- end
188
-
189
- def process(rules, jobs = nil)
190
- jobs, rules = rules, {} if jobs.nil?
191
- jobs = [jobs] if Step === jobs
192
- begin
193
-
194
- workload = Orchestrator.workload(jobs)
195
- all_jobs = workload.keys
196
-
197
- top_level_jobs = jobs.collect{|job| job.path }
198
- while workload.any?
199
-
200
- candidates = resources_used.keys + Orchestrator.candidates(workload, rules)
201
- raise "No candidates and no running jobs" if candidates.empty?
202
-
203
- candidates.each do |job|
204
- case
205
- when (job.error? || job.aborted?)
206
- begin
207
- if job.recoverable_error?
208
- job.clean
209
- raise TryAgain
210
- else
211
- next
212
- end
213
- ensure
214
- Log.warn "Releases resources from failed job: #{job.path}"
215
- release_resources(job)
216
- end
217
- when job.done?
218
- Log.debug "Orchestrator done #{job.path}"
219
- release_resources(job)
220
- erase_job_dependencies(job, rules, all_jobs, top_level_jobs)
221
-
222
- when job.running?
223
- next
224
-
225
- else
226
- check_resources(rules, job) do
227
- run_with_rules(rules, job)
228
- end
229
- end
230
- end
231
-
232
- new_workload = {}
233
- workload.each do |k,v|
234
- next if k.done? || k.error? || k.aborted?
235
- #new_workload[k] = v.reject{|d| d.done? || ((d.error? || d.aborted?) && ! d.recoverable_error?)}
236
- new_workload[k] = v.reject{|d| d.done? || d.error? || d.aborted?}
237
- end
238
- workload = new_workload
239
- sleep timer
240
- end
241
- rescue TryAgain
242
- retry
243
- end
244
- end
245
- end
246
- end
1
+ require_relative '../../refactor'
2
+ Rbbt.require_instead 'scout/workflow/deployment/orchestrator'
3
+ #require 'rbbt/workflow'
4
+ #
5
+ #module Workflow
6
+ # class Orchestrator
7
+ #
8
+ # def self.job_workload(job)
9
+ # workload = {job => []}
10
+ # return workload if job.done? && job.updated?
11
+ #
12
+ # job.dependencies.each do |dep|
13
+ # next if dep.done? && job.updated?
14
+ # workload.merge!(job_workload(dep))
15
+ # workload[job] += workload[dep]
16
+ # workload[job] << dep
17
+ # workload[job].uniq!
18
+ # end
19
+ #
20
+ # job.input_dependencies.each do |dep|
21
+ # next if dep.done? && job.updated?
22
+ # workload.merge!(job_workload(dep))
23
+ # workload[job] += workload[dep]
24
+ # workload[job] << dep
25
+ # workload[job].uniq!
26
+ # end
27
+ #
28
+ # workload
29
+ # end
30
+ #
31
+ # def self.workload(jobs)
32
+ # jobs.inject({}) do |acc,job|
33
+ # Orchestrator.job_workload(job).each do |j,d|
34
+ # acc[j] = d unless acc.keys.collect{|k| k.path }.include? j.path
35
+ # end
36
+ # acc
37
+ # end
38
+ # end
39
+ #
40
+ # def self.job_rules(rules, job)
41
+ # workflow = job.workflow.to_s
42
+ # task_name = job.task_name.to_s
43
+ # defaults = rules["defaults"] || {}
44
+ #
45
+ # return IndiferentHash.setup(defaults) unless rules[workflow]
46
+ # return IndiferentHash.setup(defaults) unless rules[workflow][task_name]
47
+ #
48
+ # job_rules = IndiferentHash.setup(rules[workflow][task_name])
49
+ # defaults.each{|k,v| job_rules[k] = v if job_rules[k].nil? } if defaults
50
+ # job_rules
51
+ # end
52
+ #
53
+ # def self.purge_duplicates(candidates)
54
+ # seen = Set.new
55
+ # candidates.select do |job|
56
+ # if seen.include? job.path
57
+ # false
58
+ # else
59
+ # seen << job.path
60
+ # true
61
+ # end
62
+ # end
63
+ # end
64
+ #
65
+ # def self.job_resources(rules, job)
66
+ # resources = (job_rules(rules, job) || {})["resources"] || {}
67
+ #
68
+ # IndiferentHash.setup(resources)
69
+ #
70
+ # default_resources = rules["default_resources"]
71
+ # default_resources ||= rules["defaults"]["resources"] if rules["defaults"]
72
+ # default_resources ||= {}
73
+ #
74
+ # default_resources.each{|k,v| resources[k] ||= v } if default_resources
75
+ #
76
+ # resources = {:cpus => 1} if resources.empty?
77
+ # resources
78
+ # end
79
+ #
80
+ # def self.sort_candidates(candidates, rules)
81
+ # seen = Set.new
82
+ # candidates.sort_by do |job|
83
+ # - job_resources(rules, job).values.inject(0){|acc,e| acc += e}
84
+ # end
85
+ # end
86
+ #
87
+ # def self.candidates(workload, rules)
88
+ # if rules.empty?
89
+ # candidates = workload.
90
+ # select{|k,v| v.empty? }.
91
+ # collect{|k,v| k }.
92
+ # reject{|k| k.done? }
93
+ # else
94
+ # candidates = workload. #select{|k,v| Orchestrator.job_rules(rules, k) }.
95
+ # select{|k,v| v.empty? }.
96
+ # collect{|k,v| k }.
97
+ # reject{|k| k.done? }
98
+ # end
99
+ #
100
+ # top_level = workload.keys - workload.values.flatten
101
+ #
102
+ # candidates = purge_duplicates candidates
103
+ # candidates = sort_candidates candidates, rules
104
+ #
105
+ # candidates
106
+ # end
107
+ #
108
+ # def self.process(*args)
109
+ # self.new.process(*args)
110
+ # end
111
+ #
112
+ # attr_accessor :available_resources, :resources_requested, :resources_used, :timer
113
+ #
114
+ # def initialize(timer = 5, available_resources = nil)
115
+ # available_resources = {:cpus => Etc.nprocessors } if available_resources.nil?
116
+ # @timer = timer
117
+ # @available_resources = IndiferentHash.setup(available_resources)
118
+ # @resources_requested = IndiferentHash.setup({})
119
+ # @resources_used = IndiferentHash.setup({})
120
+ # end
121
+ #
122
+ # def release_resources(job)
123
+ # if resources_used[job]
124
+ # Log.debug "Orchestrator releasing resouces from #{job.path}"
125
+ # resources_used[job].each do |resource,value|
126
+ # next if resource == 'size'
127
+ # resources_requested[resource] -= value.to_i
128
+ # end
129
+ # resources_used.delete job
130
+ # end
131
+ # end
132
+ #
133
+ # def check_resources(rules, job)
134
+ # resources = Orchestrator.job_resources(rules, job)
135
+ #
136
+ # limit_resources = resources.select{|resource,value| available_resources[resource] && ((resources_requested[resource] || 0) + value) > available_resources[resource] }.collect{|resource,v| resource }
137
+ # if limit_resources.any?
138
+ # Log.debug "Orchestrator waiting on #{job.path} due to #{limit_resources * ", "}"
139
+ # else
140
+ #
141
+ # resources_used[job] = resources
142
+ # resources.each do |resource,value|
143
+ # resources_requested[resource] ||= 0
144
+ # resources_requested[resource] += value.to_i
145
+ # end
146
+ # Log.low "Orchestrator producing #{job.path} with resources #{resources}"
147
+ #
148
+ # return yield
149
+ # end
150
+ # end
151
+ #
152
+ # def run_with_rules(rules, job)
153
+ # job_rules = Orchestrator.job_rules(rules, job)
154
+ #
155
+ # Rbbt::Config.with_config do
156
+ # job_rules[:config_keys].each do |config|
157
+ # Rbbt::Config.process_config config
158
+ # end if job_rules && job_rules[:config_keys]
159
+ #
160
+ # log = job_rules[:log] if job_rules
161
+ # log = Log.severity if log.nil?
162
+ # Log.with_severity log do
163
+ # #job.produce(false, :nowait)
164
+ # job.produce(with_fork: true)
165
+ # end
166
+ # end
167
+ # end
168
+ #
169
+ # def erase_job_dependencies(job, rules, all_jobs, top_level_jobs)
170
+ # job.dependencies.each do |dep|
171
+ # next if top_level_jobs.include? dep.path
172
+ # next unless Orchestrator.job_rules(rules, dep)["erase"].to_s == 'true'
173
+ #
174
+ # dep_path = dep.path
175
+ # parents = all_jobs.select do |parent|
176
+ # paths = parent.info[:dependencies].nil? ? parent.dependencies.collect{|d| d.path } : parent.info[:dependencies].collect{|d| d.last }
177
+ # paths.include? dep_path
178
+ # end
179
+ #
180
+ # next unless parents.reject{|parent| parent.done? }.empty?
181
+ #
182
+ # parents.each do |parent|
183
+ # Log.high "Erasing #{dep.path} from #{parent.path}"
184
+ # parent.archive_deps
185
+ # parent.copy_files_dir
186
+ # parent.dependencies = parent.dependencies - [dep]
187
+ # end
188
+ # dep.clean
189
+ # end
190
+ # end
191
+ #
192
+ # def process(rules, jobs = nil)
193
+ # jobs, rules = rules, {} if jobs.nil?
194
+ # jobs = [jobs] if Step === jobs
195
+ # begin
196
+ #
197
+ # workload = Orchestrator.workload(jobs)
198
+ # all_jobs = workload.keys
199
+ #
200
+ # top_level_jobs = jobs.collect{|job| job.path }
201
+ # while workload.any?
202
+ #
203
+ # candidates = resources_used.keys + Orchestrator.candidates(workload, rules)
204
+ # raise "No candidates and no running jobs" if candidates.empty?
205
+ #
206
+ # candidates.each do |job|
207
+ # case
208
+ # when (job.error? || job.aborted?)
209
+ # begin
210
+ # if job.recoverable_error?
211
+ # job.clean
212
+ # raise TryAgain
213
+ # else
214
+ # next
215
+ # end
216
+ # ensure
217
+ # Log.warn "Releases resources from failed job: #{job.path}"
218
+ # release_resources(job)
219
+ # end
220
+ # when job.done?
221
+ # Log.debug "Orchestrator done #{job.path}"
222
+ # release_resources(job)
223
+ # erase_job_dependencies(job, rules, all_jobs, top_level_jobs)
224
+ #
225
+ # when job.running?
226
+ # next
227
+ #
228
+ # else
229
+ # check_resources(rules, job) do
230
+ # run_with_rules(rules, job)
231
+ # end
232
+ # end
233
+ # end
234
+ #
235
+ # new_workload = {}
236
+ # workload.each do |k,v|
237
+ # next if k.done? || k.error? || k.aborted?
238
+ # #new_workload[k] = v.reject{|d| d.done? || ((d.error? || d.aborted?) && ! d.recoverable_error?)}
239
+ # new_workload[k] = v.reject{|d| d.done? || d.error? || d.aborted?}
240
+ # end
241
+ # workload = new_workload
242
+ # sleep timer
243
+ # end
244
+ # rescue TryAgain
245
+ # retry
246
+ # end
247
+ # end
248
+ # end
249
+ #end