vortex-nwp 2.0.0b1__py3-none-any.whl → 2.1.0__py3-none-any.whl

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 (141) hide show
  1. vortex/__init__.py +75 -47
  2. vortex/algo/__init__.py +3 -2
  3. vortex/algo/components.py +944 -618
  4. vortex/algo/mpitools.py +802 -497
  5. vortex/algo/mpitools_templates/__init__.py +1 -0
  6. vortex/algo/serversynctools.py +34 -33
  7. vortex/config.py +19 -22
  8. vortex/data/__init__.py +9 -3
  9. vortex/data/abstractstores.py +593 -655
  10. vortex/data/containers.py +217 -162
  11. vortex/data/contents.py +65 -39
  12. vortex/data/executables.py +93 -102
  13. vortex/data/flow.py +40 -34
  14. vortex/data/geometries.py +228 -132
  15. vortex/data/handlers.py +436 -227
  16. vortex/data/outflow.py +15 -15
  17. vortex/data/providers.py +185 -163
  18. vortex/data/resources.py +48 -42
  19. vortex/data/stores.py +540 -417
  20. vortex/data/sync_templates/__init__.py +0 -0
  21. vortex/gloves.py +114 -87
  22. vortex/layout/__init__.py +1 -8
  23. vortex/layout/contexts.py +150 -84
  24. vortex/layout/dataflow.py +353 -202
  25. vortex/layout/monitor.py +264 -128
  26. vortex/nwp/__init__.py +5 -2
  27. vortex/nwp/algo/__init__.py +14 -5
  28. vortex/nwp/algo/assim.py +205 -151
  29. vortex/nwp/algo/clim.py +683 -517
  30. vortex/nwp/algo/coupling.py +447 -225
  31. vortex/nwp/algo/eda.py +437 -229
  32. vortex/nwp/algo/eps.py +403 -231
  33. vortex/nwp/algo/forecasts.py +416 -275
  34. vortex/nwp/algo/fpserver.py +683 -307
  35. vortex/nwp/algo/ifsnaming.py +205 -145
  36. vortex/nwp/algo/ifsroot.py +215 -122
  37. vortex/nwp/algo/monitoring.py +137 -76
  38. vortex/nwp/algo/mpitools.py +330 -190
  39. vortex/nwp/algo/odbtools.py +637 -353
  40. vortex/nwp/algo/oopsroot.py +454 -273
  41. vortex/nwp/algo/oopstests.py +90 -56
  42. vortex/nwp/algo/request.py +287 -206
  43. vortex/nwp/algo/stdpost.py +878 -522
  44. vortex/nwp/data/__init__.py +22 -4
  45. vortex/nwp/data/assim.py +125 -137
  46. vortex/nwp/data/boundaries.py +121 -68
  47. vortex/nwp/data/climfiles.py +193 -211
  48. vortex/nwp/data/configfiles.py +73 -69
  49. vortex/nwp/data/consts.py +426 -401
  50. vortex/nwp/data/ctpini.py +59 -43
  51. vortex/nwp/data/diagnostics.py +94 -66
  52. vortex/nwp/data/eda.py +50 -51
  53. vortex/nwp/data/eps.py +195 -146
  54. vortex/nwp/data/executables.py +440 -434
  55. vortex/nwp/data/fields.py +63 -48
  56. vortex/nwp/data/gridfiles.py +183 -111
  57. vortex/nwp/data/logs.py +250 -217
  58. vortex/nwp/data/modelstates.py +180 -151
  59. vortex/nwp/data/monitoring.py +72 -99
  60. vortex/nwp/data/namelists.py +254 -202
  61. vortex/nwp/data/obs.py +400 -308
  62. vortex/nwp/data/oopsexec.py +22 -20
  63. vortex/nwp/data/providers.py +90 -65
  64. vortex/nwp/data/query.py +71 -82
  65. vortex/nwp/data/stores.py +49 -36
  66. vortex/nwp/data/surfex.py +136 -137
  67. vortex/nwp/syntax/__init__.py +1 -1
  68. vortex/nwp/syntax/stdattrs.py +173 -111
  69. vortex/nwp/tools/__init__.py +2 -2
  70. vortex/nwp/tools/addons.py +22 -17
  71. vortex/nwp/tools/agt.py +24 -12
  72. vortex/nwp/tools/bdap.py +16 -5
  73. vortex/nwp/tools/bdcp.py +4 -1
  74. vortex/nwp/tools/bdm.py +3 -0
  75. vortex/nwp/tools/bdmp.py +14 -9
  76. vortex/nwp/tools/conftools.py +728 -378
  77. vortex/nwp/tools/drhook.py +12 -8
  78. vortex/nwp/tools/grib.py +65 -39
  79. vortex/nwp/tools/gribdiff.py +22 -17
  80. vortex/nwp/tools/ifstools.py +82 -42
  81. vortex/nwp/tools/igastuff.py +167 -143
  82. vortex/nwp/tools/mars.py +14 -2
  83. vortex/nwp/tools/odb.py +234 -125
  84. vortex/nwp/tools/partitioning.py +61 -37
  85. vortex/nwp/tools/satrad.py +27 -12
  86. vortex/nwp/util/async.py +83 -55
  87. vortex/nwp/util/beacon.py +10 -10
  88. vortex/nwp/util/diffpygram.py +174 -86
  89. vortex/nwp/util/ens.py +144 -63
  90. vortex/nwp/util/hooks.py +30 -19
  91. vortex/nwp/util/taskdeco.py +28 -24
  92. vortex/nwp/util/usepygram.py +278 -172
  93. vortex/nwp/util/usetnt.py +31 -17
  94. vortex/sessions.py +72 -39
  95. vortex/syntax/__init__.py +1 -1
  96. vortex/syntax/stdattrs.py +410 -171
  97. vortex/syntax/stddeco.py +31 -22
  98. vortex/toolbox.py +327 -192
  99. vortex/tools/__init__.py +11 -2
  100. vortex/tools/actions.py +110 -121
  101. vortex/tools/addons.py +111 -92
  102. vortex/tools/arm.py +42 -22
  103. vortex/tools/compression.py +72 -69
  104. vortex/tools/date.py +11 -4
  105. vortex/tools/delayedactions.py +242 -132
  106. vortex/tools/env.py +75 -47
  107. vortex/tools/folder.py +342 -171
  108. vortex/tools/grib.py +341 -162
  109. vortex/tools/lfi.py +423 -216
  110. vortex/tools/listings.py +109 -40
  111. vortex/tools/names.py +218 -156
  112. vortex/tools/net.py +655 -299
  113. vortex/tools/parallelism.py +93 -61
  114. vortex/tools/prestaging.py +55 -31
  115. vortex/tools/schedulers.py +172 -105
  116. vortex/tools/services.py +403 -334
  117. vortex/tools/storage.py +293 -358
  118. vortex/tools/surfex.py +24 -24
  119. vortex/tools/systems.py +1234 -643
  120. vortex/tools/targets.py +156 -100
  121. vortex/util/__init__.py +1 -1
  122. vortex/util/config.py +378 -327
  123. vortex/util/empty.py +2 -2
  124. vortex/util/helpers.py +56 -24
  125. vortex/util/introspection.py +18 -12
  126. vortex/util/iosponge.py +8 -4
  127. vortex/util/roles.py +4 -6
  128. vortex/util/storefunctions.py +39 -13
  129. vortex/util/structs.py +3 -3
  130. vortex/util/worker.py +29 -17
  131. vortex_nwp-2.1.0.dist-info/METADATA +67 -0
  132. vortex_nwp-2.1.0.dist-info/RECORD +144 -0
  133. {vortex_nwp-2.0.0b1.dist-info → vortex_nwp-2.1.0.dist-info}/WHEEL +1 -1
  134. vortex/layout/appconf.py +0 -109
  135. vortex/layout/jobs.py +0 -1276
  136. vortex/layout/nodes.py +0 -1424
  137. vortex/layout/subjobs.py +0 -464
  138. vortex_nwp-2.0.0b1.dist-info/METADATA +0 -50
  139. vortex_nwp-2.0.0b1.dist-info/RECORD +0 -146
  140. {vortex_nwp-2.0.0b1.dist-info → vortex_nwp-2.1.0.dist-info/licenses}/LICENSE +0 -0
  141. {vortex_nwp-2.0.0b1.dist-info → vortex_nwp-2.1.0.dist-info}/top_level.txt +0 -0
vortex/toolbox.py CHANGED
@@ -16,18 +16,24 @@ from bronx.syntax import mktuple
16
16
 
17
17
  import footprints
18
18
 
19
- from vortex import sessions, data, proxy, VortexForceComplete
19
+ from vortex import sessions, data, proxy
20
20
  from vortex.layout.dataflow import stripargs_section, intent, ixo, Section
21
21
 
22
22
  #: Automatic export of superstar interface.
23
- __all__ = ['rload', 'rget', 'rput']
23
+ __all__ = ["rload", "rget", "rput"]
24
24
 
25
25
  logger = loggers.getLogger(__name__)
26
26
 
27
27
  #: Shortcut to footprint env defaults
28
28
  defaults = footprints.setup.defaults
29
29
 
30
- sectionmap = {'input': 'get', 'output': 'put', 'executable': 'get'}
30
+ sectionmap = {"input": "get", "output": "put", "executable": "get"}
31
+
32
+
33
+ class VortexForceComplete(Exception):
34
+ """Exception for handling fast exit mecanisms."""
35
+
36
+ pass
31
37
 
32
38
 
33
39
  # Toolbox defaults
@@ -55,34 +61,44 @@ active_incache = False
55
61
  active_batchinputs = True
56
62
 
57
63
  #: History recording
58
- history = History(tag='rload')
64
+ history = History(tag="rload")
59
65
 
60
66
 
61
67
  # Most commonly used functions
62
68
 
69
+
63
70
  def show_toolbox_settings(ljust=24):
64
71
  """Print the current settings of the toolbox."""
65
- for key in ['active_{}'.format(act) for act in
66
- ('now', 'insitu', 'verbose', 'promise', 'clear',
67
- 'metadatacheck', 'incache')]:
72
+ for key in [
73
+ "active_{}".format(act)
74
+ for act in (
75
+ "now",
76
+ "insitu",
77
+ "verbose",
78
+ "promise",
79
+ "clear",
80
+ "metadatacheck",
81
+ "incache",
82
+ )
83
+ ]:
68
84
  kval = globals().get(key, None)
69
85
  if kval is not None:
70
- print('+', key.ljust(ljust), '=', kval)
86
+ print("+", key.ljust(ljust), "=", kval)
71
87
 
72
88
 
73
89
  def quickview(args, nb=0, indent=0):
74
90
  """Recursive call to any quick view of objects specified as arguments."""
75
91
  if not isinstance(args, list) and not isinstance(args, tuple):
76
- args = (args, )
92
+ args = (args,)
77
93
  for x in args:
78
94
  if nb:
79
95
  print()
80
96
  nb += 1
81
- quickview = getattr(x, 'quickview', None)
97
+ quickview = getattr(x, "quickview", None)
82
98
  if quickview:
83
99
  quickview(nb, indent)
84
100
  else:
85
- print('{:02d}. {:s}'.format(nb, x))
101
+ print("{:02d}. {:s}".format(nb, x))
86
102
 
87
103
 
88
104
  class VortexToolboxDescError(Exception):
@@ -118,18 +134,18 @@ def rload(*args, **kw):
118
134
  if isinstance(a, dict):
119
135
  rd.update(a)
120
136
  else:
121
- logger.warning('Discard rload argument <%s>', a)
137
+ logger.warning("Discard rload argument <%s>", a)
122
138
  rd.update(kw)
123
139
  if rd:
124
140
  history.append(rd.copy())
125
141
  rhx = []
126
142
  for x in footprints.util.expand(rd):
127
143
  picked_up = proxy.containers.pickup( # @UndefinedVariable
128
- * proxy.providers.pickup_and_cache( # @UndefinedVariable
129
- * proxy.resources.pickup_and_cache(x) # @UndefinedVariable
144
+ *proxy.providers.pickup_and_cache( # @UndefinedVariable
145
+ *proxy.resources.pickup_and_cache(x) # @UndefinedVariable
130
146
  )
131
147
  )
132
- logger.debug('Resource desc %s', picked_up)
148
+ logger.debug("Resource desc %s", picked_up)
133
149
  picked_rh = data.handlers.Handler(picked_up)
134
150
  if not picked_rh.complete:
135
151
  raise VortexToolboxDescError("The ResourceHandler is incomplete")
@@ -151,7 +167,7 @@ def rget(*args, **kw):
151
167
  This function calls the :meth:`get` method on any resource handler returned
152
168
  by the :func:`rload` function.
153
169
  """
154
- loc_incache = kw.pop('incache', active_incache)
170
+ loc_incache = kw.pop("incache", active_incache)
155
171
  rl = rload(*args, **kw)
156
172
  for rh in rl:
157
173
  rh.get(incache=loc_incache)
@@ -163,7 +179,7 @@ def rput(*args, **kw):
163
179
  This function calls the :meth:`put` method on any resource handler returned
164
180
  by the :func:`rload` function.
165
181
  """
166
- loc_incache = kw.pop('incache', active_incache)
182
+ loc_incache = kw.pop("incache", active_incache)
167
183
  rl = rload(*args, **kw)
168
184
  for rh in rl:
169
185
  rh.put(incache=loc_incache)
@@ -172,9 +188,9 @@ def rput(*args, **kw):
172
188
 
173
189
  def nicedump(msg, **kw):
174
190
  """Simple dump the **kw** dict content with ``msg`` as header."""
175
- print('#', msg, ':')
191
+ print("#", msg, ":")
176
192
  for k, v in sorted(kw.items()):
177
- print('+', k.ljust(12), '=', str(v))
193
+ print("+", k.ljust(12), "=", str(v))
178
194
  print()
179
195
 
180
196
 
@@ -238,32 +254,33 @@ def add_section(section, args, kw):
238
254
  t = sessions.current()
239
255
 
240
256
  # First, retrieve arguments of the toolbox command itself
241
- now = kw.pop('now', active_now)
242
- loglevel = kw.pop('loglevel', None)
243
- talkative = kw.pop('verbose', active_verbose)
244
- complete = kw.pop('complete', False)
245
- insitu = kw.get('insitu', False)
246
- batch = kw.pop('batch', False)
247
- lastfatal = kw.pop('lastfatal', None)
257
+ now = kw.pop("now", active_now)
258
+ loglevel = kw.pop("loglevel", None)
259
+ talkative = kw.pop("verbose", active_verbose)
260
+ complete = kw.pop("complete", False)
261
+ insitu = kw.get("insitu", False)
262
+ batch = kw.pop("batch", False)
263
+ lastfatal = kw.pop("lastfatal", None)
248
264
 
249
265
  if complete:
250
- kw['fatal'] = False
266
+ kw["fatal"] = False
251
267
 
252
268
  if batch:
253
- if section not in ('input', 'excutable'):
254
- logger.info("batch=True is not implemented for section=%s. overwriting to batch=Fase.",
255
- section)
269
+ if section not in ("input", "excutable"):
270
+ logger.info(
271
+ "batch=True is not implemented for section=%s. overwriting to batch=Fase.",
272
+ section,
273
+ )
256
274
  batch = False
257
275
 
258
276
  # Second, retrieve arguments that could be used by the now command
259
277
  cmdopts = dict(
260
- incache=kw.pop('incache', active_incache),
261
- force=kw.pop('force', False)
278
+ incache=kw.pop("incache", active_incache), force=kw.pop("force", False)
262
279
  )
263
280
 
264
281
  # Third, collect arguments for triggering some hook
265
282
  hooks = dict()
266
- for ahook in [x for x in kw.keys() if x.startswith('hook_')]:
283
+ for ahook in [x for x in kw.keys() if x.startswith("hook_")]:
267
284
  cbhook = mktuple(kw.pop(ahook))
268
285
  cbfunc = cbhook[0]
269
286
  if not callable(cbfunc):
@@ -272,29 +289,30 @@ def add_section(section, args, kw):
272
289
 
273
290
  # Print the user inputs
274
291
  def print_user_inputs():
275
- nicedump('New {:s} section with options'.format(section), **opts)
276
- nicedump('Resource handler description', **kwclean)
292
+ nicedump("New {:s} section with options".format(section), **opts)
293
+ nicedump("Resource handler description", **kwclean)
277
294
  nicedump(
278
- 'This command options',
295
+ "This command options",
279
296
  complete=complete,
280
297
  loglevel=loglevel,
281
298
  now=now,
282
299
  verbose=talkative,
283
300
  )
284
301
  if hooks:
285
- nicedump('Hooks triggered', **hooks)
302
+ nicedump("Hooks triggered", **hooks)
286
303
 
287
304
  with _tb_isolate(t, loglevel):
288
-
289
305
  # Distinguish between section arguments, and resource loader arguments
290
306
  opts, kwclean = stripargs_section(**kw)
291
307
 
292
308
  # Strip the metadatacheck option depending on active_metadatacheck
293
309
  if not active_metadatacheck and not insitu:
294
- if kwclean.get('metadatacheck', False):
295
- logger.info("The metadatacheck option is forced to False since " +
296
- "active_metadatacheck=False.")
297
- kwclean['metadatacheck'] = False
310
+ if kwclean.get("metadatacheck", False):
311
+ logger.info(
312
+ "The metadatacheck option is forced to False since "
313
+ + "active_metadatacheck=False."
314
+ )
315
+ kwclean["metadatacheck"] = False
298
316
 
299
317
  # Show the actual set of arguments
300
318
  if talkative and not insitu:
@@ -311,23 +329,32 @@ def add_section(section, args, kw):
311
329
 
312
330
  # Create a section for each resource handler
313
331
  if rl and lastfatal is not None:
314
- newsections = [push(rh=rhandler, **opts)[0] for rhandler in rl[:-1]]
332
+ newsections = [
333
+ push(rh=rhandler, **opts)[0] for rhandler in rl[:-1]
334
+ ]
315
335
  tmpopts = opts.copy()
316
- tmpopts['fatal'] = lastfatal
336
+ tmpopts["fatal"] = lastfatal
317
337
  newsections.append(push(rh=rl[-1], **tmpopts)[0])
318
338
  else:
319
339
  newsections = [push(rh=rhandler, **opts)[0] for rhandler in rl]
320
340
 
321
341
  # If insitu and now, try a quiet get...
322
- do_quick_insitu = section in ('input', 'executable') and insitu and now
342
+ do_quick_insitu = section in ("input", "executable") and insitu and now
323
343
  if do_quick_insitu:
324
- quickget = [sec.rh.insitu_quickget(alternate=sec.alternate, **cmdopts) for sec in newsections]
344
+ quickget = [
345
+ sec.rh.insitu_quickget(alternate=sec.alternate, **cmdopts)
346
+ for sec in newsections
347
+ ]
325
348
  if all(quickget):
326
349
  if len(quickget) > 1:
327
- logger.info("The insitu get succeeded for all of the %d resource handlers.",
328
- len(rl))
350
+ logger.info(
351
+ "The insitu get succeeded for all of the %d resource handlers.",
352
+ len(rl),
353
+ )
329
354
  else:
330
- logger.info("The insitu get succeeded for this resource handler.")
355
+ logger.info(
356
+ "The insitu get succeeded for this resource handler."
357
+ )
331
358
  rlok = [sec.rh for sec in newsections]
332
359
  else:
333
360
  # Start again with the usual get sequence
@@ -338,64 +365,118 @@ def add_section(section, args, kw):
338
365
  if now:
339
366
  with t.sh.ftppool():
340
367
  # Create a section for each resource handler, and perform action on demand
341
- batchflags = [None, ] * len(newsections)
368
+ batchflags = [
369
+ None,
370
+ ] * len(newsections)
342
371
  if batch:
343
372
  if talkative:
344
- t.sh.subtitle('Early-{:s} for all resources.'.format(doitmethod))
373
+ t.sh.subtitle(
374
+ "Early-{:s} for all resources.".format(
375
+ doitmethod
376
+ )
377
+ )
345
378
  for ir, newsection in enumerate(newsections):
346
379
  rhandler = newsection.rh
347
- batchflags[ir] = getattr(newsection, 'early' + doitmethod)(**cmdopts)
380
+ batchflags[ir] = getattr(
381
+ newsection, "early" + doitmethod
382
+ )(**cmdopts)
348
383
  if talkative:
349
384
  if any(batchflags):
350
385
  for ir, newsection in enumerate(newsections):
351
386
  if talkative and batchflags[ir]:
352
- logger.info('Resource no %02d/%02d: Early-%s registered with id: %s.',
353
- ir + 1, len(rl), doitmethod, str(batchflags[ir]))
387
+ logger.info(
388
+ "Resource no %02d/%02d: Early-%s registered with id: %s.",
389
+ ir + 1,
390
+ len(rl),
391
+ doitmethod,
392
+ str(batchflags[ir]),
393
+ )
354
394
  else:
355
- logger.debug('Resource no %02d/%02d: Early-%s registered with id: %s.',
356
- ir + 1, len(rl), doitmethod, str(batchflags[ir]))
395
+ logger.debug(
396
+ "Resource no %02d/%02d: Early-%s registered with id: %s.",
397
+ ir + 1,
398
+ len(rl),
399
+ doitmethod,
400
+ str(batchflags[ir]),
401
+ )
357
402
  else:
358
- logger.info('Early-%s was unavailable for all of the resources.',
359
- doitmethod)
403
+ logger.info(
404
+ "Early-%s was unavailable for all of the resources.",
405
+ doitmethod,
406
+ )
360
407
  # trigger finalise for all of the DelayedActions
361
- tofinalise = [r_id for r_id in batchflags if r_id and r_id is not True]
408
+ tofinalise = [
409
+ r_id
410
+ for r_id in batchflags
411
+ if r_id and r_id is not True
412
+ ]
362
413
  if tofinalise:
363
414
  if talkative:
364
- t.sh.subtitle('Finalising all of the delayed actions...')
365
- t.context.delayedactions_hub.finalise(* tofinalise)
415
+ t.sh.subtitle(
416
+ "Finalising all of the delayed actions..."
417
+ )
418
+ t.context.delayedactions_hub.finalise(*tofinalise)
366
419
  secok = list()
367
420
  for ir, newsection in enumerate(newsections):
368
421
  rhandler = newsection.rh
369
422
  # If quick get was ok for this resource don't call get again...
370
423
  if talkative:
371
- t.sh.subtitle('Resource no {:02d}/{:02d}'.format(ir + 1, len(rl)))
424
+ t.sh.subtitle(
425
+ "Resource no {:02d}/{:02d}".format(
426
+ ir + 1, len(rl)
427
+ )
428
+ )
372
429
  rhandler.quickview(nb=ir + 1, indent=0)
373
- if batchflags[ir] is not True or (do_quick_insitu and quickget[ir]):
374
- t.sh.highlight('Action {:s} on {:s}'.format(doitmethod.upper(),
375
- rhandler.location(fatal=False)))
430
+ if batchflags[ir] is not True or (
431
+ do_quick_insitu and quickget[ir]
432
+ ):
433
+ t.sh.highlight(
434
+ "Action {:s} on {:s}".format(
435
+ doitmethod.upper(),
436
+ rhandler.location(fatal=False),
437
+ )
438
+ )
376
439
  ok = do_quick_insitu and quickget[ir]
377
440
  if batchflags[ir]:
378
- actual_doitmethod = 'finalise' + doitmethod
441
+ actual_doitmethod = "finalise" + doitmethod
379
442
  ok = ok or getattr(newsection, actual_doitmethod)()
380
443
  else:
381
444
  actual_doitmethod = doitmethod
382
- ok = ok or getattr(newsection, actual_doitmethod)(**cmdopts)
445
+ ok = ok or getattr(newsection, actual_doitmethod)(
446
+ **cmdopts
447
+ )
383
448
  if talkative:
384
- t.sh.highlight('Result from {:s}: [{!s}]'.format(actual_doitmethod, ok))
449
+ t.sh.highlight(
450
+ "Result from {:s}: [{!s}]".format(
451
+ actual_doitmethod, ok
452
+ )
453
+ )
385
454
  if talkative and not ok:
386
- logger.error('Could not %s resource %s',
387
- doitmethod, rhandler.container.localpath())
455
+ logger.error(
456
+ "Could not %s resource %s",
457
+ doitmethod,
458
+ rhandler.container.localpath(),
459
+ )
388
460
  if not ok:
389
461
  if complete:
390
- logger.warning('Force complete for %s',
391
- rhandler.location(fatal=False))
392
- raise VortexForceComplete('Force task complete on resource error')
462
+ logger.warning(
463
+ "Force complete for %s",
464
+ rhandler.location(fatal=False),
465
+ )
466
+ raise VortexForceComplete(
467
+ "Force task complete on resource error"
468
+ )
393
469
  else:
394
470
  secok.append(newsection)
395
471
  if t.sh.trace:
396
472
  print()
397
- rlok.extend([newsection.rh for newsection in secok
398
- if newsection.any_coherentgroup_opened])
473
+ rlok.extend(
474
+ [
475
+ newsection.rh
476
+ for newsection in secok
477
+ if newsection.any_coherentgroup_opened
478
+ ]
479
+ )
399
480
  else:
400
481
  rlok.extend([newsection.rh for newsection in newsections])
401
482
 
@@ -414,9 +495,9 @@ def input(*args, **kw): # @ReservedAssignment
414
495
  :return: A list of :class:`vortex.data.handlers.Handler` objects (associated
415
496
  with the newly created class:`~vortex.layout.dataflow.Section` objects).
416
497
  """
417
- kw.setdefault('insitu', active_insitu)
418
- kw.setdefault('batch', active_batchinputs)
419
- return add_section('input', args, kw)
498
+ kw.setdefault("insitu", active_insitu)
499
+ kw.setdefault("batch", active_batchinputs)
500
+ return add_section("input", args, kw)
420
501
 
421
502
 
422
503
  def inputs(ticket=None, context=None):
@@ -445,7 +526,7 @@ def show_inputs(context=None):
445
526
  """
446
527
  t = sessions.current()
447
528
  for csi in inputs(ticket=t):
448
- t.sh.header('Input ' + str(csi))
529
+ t.sh.header("Input " + str(csi))
449
530
  csi.show(ticket=t, context=context)
450
531
  print()
451
532
 
@@ -462,11 +543,14 @@ def output(*args, **kw):
462
543
  """
463
544
  # Strip the metadatacheck option depending on active_metadatacheck
464
545
  if not active_promise:
465
- for target in ('promised', 'expected'):
546
+ for target in ("promised", "expected"):
466
547
  if target in kw and kw[target]:
467
- logger.info("The %s argument is removed since active_promise=False.", target)
548
+ logger.info(
549
+ "The %s argument is removed since active_promise=False.",
550
+ target,
551
+ )
468
552
  del kw[target]
469
- return add_section('output', args, kw)
553
+ return add_section("output", args, kw)
470
554
 
471
555
 
472
556
  def outputs(ticket=None, context=None):
@@ -493,7 +577,7 @@ def show_outputs(context=None):
493
577
  """
494
578
  t = sessions.current()
495
579
  for cso in outputs(ticket=t):
496
- t.sh.header('Output ' + str(cso))
580
+ t.sh.header("Output " + str(cso))
497
581
  cso.show(ticket=t, context=context)
498
582
  print()
499
583
 
@@ -517,9 +601,9 @@ def promise(*args, **kw):
517
601
  now=active_promise,
518
602
  )
519
603
  if not active_promise:
520
- kw.setdefault('verbose', False)
521
- logger.warning('Promise flag is <%s> in that context', active_promise)
522
- return add_section('output', args, kw)
604
+ kw.setdefault("verbose", False)
605
+ logger.warning("Promise flag is <%s> in that context", active_promise)
606
+ return add_section("output", args, kw)
523
607
 
524
608
 
525
609
  def executable(*args, **kw):
@@ -533,8 +617,8 @@ def executable(*args, **kw):
533
617
  :return: A list of :class:`vortex.data.handlers.Handler` objects (associated
534
618
  with the newly created class:`~vortex.layout.dataflow.Section` objects).
535
619
  """
536
- kw.setdefault('insitu', active_insitu)
537
- return add_section('executable', args, kw)
620
+ kw.setdefault("insitu", active_insitu)
621
+ return add_section("executable", args, kw)
538
622
 
539
623
 
540
624
  def algo(*args, **kw):
@@ -559,13 +643,12 @@ def algo(*args, **kw):
559
643
  t = sessions.current()
560
644
 
561
645
  # First, retrieve arguments of the toolbox command itself
562
- loglevel = kw.pop('loglevel', None)
563
- talkative = kw.pop('verbose', active_verbose)
646
+ loglevel = kw.pop("loglevel", None)
647
+ talkative = kw.pop("verbose", active_verbose)
564
648
 
565
649
  with _tb_isolate(t, loglevel):
566
-
567
650
  if talkative:
568
- nicedump('Loading algo component with description:', **kw)
651
+ nicedump("Loading algo component with description:", **kw)
569
652
 
570
653
  ok = proxy.component(**kw) # @UndefinedVariable
571
654
  if ok and talkative:
@@ -606,34 +689,36 @@ def diff(*args, **kw):
606
689
  """
607
690
 
608
691
  # First, retrieve arguments of the toolbox command itself
609
- fatal = kw.pop('fatal', True)
610
- loglevel = kw.pop('loglevel', None)
611
- talkative = kw.pop('verbose', active_verbose)
612
- batch = kw.pop('batch', active_batchinputs)
692
+ fatal = kw.pop("fatal", True)
693
+ loglevel = kw.pop("loglevel", None)
694
+ talkative = kw.pop("verbose", active_verbose)
695
+ batch = kw.pop("batch", active_batchinputs)
613
696
 
614
697
  # Distinguish between section arguments, and resource loader arguments
615
698
  opts, kwclean = stripargs_section(**kw)
616
699
 
617
700
  # Show the actual set of arguments
618
701
  if talkative:
619
- nicedump('Discard section options', **opts)
620
- nicedump('Resource handler description', **kwclean)
702
+ nicedump("Discard section options", **opts)
703
+ nicedump("Resource handler description", **kwclean)
621
704
 
622
705
  # Fast exit in case of undefined value
623
706
  rlok = list()
624
- none_skip = {k for k, v in kwclean.items()
625
- if v is None and k in ('experiment', 'namespace')}
707
+ none_skip = {
708
+ k
709
+ for k, v in kwclean.items()
710
+ if v is None and k in ("experiment", "namespace")
711
+ }
626
712
  if none_skip:
627
- logger.warning('Skip diff because of undefined argument(s)')
713
+ logger.warning("Skip diff because of undefined argument(s)")
628
714
  return rlok
629
715
 
630
716
  t = sessions.current()
631
717
 
632
718
  # Swich off autorecording of the current context + deal with loggging
633
719
  with _tb_isolate(t, loglevel):
634
-
635
720
  # Do not track the reference files
636
- kwclean['storetrack'] = False
721
+ kwclean["storetrack"] = False
637
722
 
638
723
  rhandlers = rload(*args, **kwclean)
639
724
  sections = list()
@@ -647,12 +732,17 @@ def diff(*args, **kw):
647
732
  for ir, rhandler in enumerate(rhandlers):
648
733
  source_container.append(rhandler.container)
649
734
  # Create a new container to hold the reference file
650
- lazzy_container.append(footprints.proxy.container(shouldfly=True,
651
- actualfmt=rhandler.container.actualfmt))
735
+ lazzy_container.append(
736
+ footprints.proxy.container(
737
+ shouldfly=True, actualfmt=rhandler.container.actualfmt
738
+ )
739
+ )
652
740
  # Swapp the original container with the lazzy one
653
741
  rhandler.container = lazzy_container[-1]
654
742
  # Create a new section
655
- sec = Section(rh=rhandler, kind=ixo.INPUT, intent=intent.IN, fatal=False)
743
+ sec = Section(
744
+ rh=rhandler, kind=ixo.INPUT, intent=intent.IN, fatal=False
745
+ )
656
746
  sections.append(sec)
657
747
  # Early-get
658
748
  if rhandler.complete:
@@ -661,9 +751,14 @@ def diff(*args, **kw):
661
751
  earlyget_id.append(None)
662
752
  # Finalising
663
753
  if any([r_id and r_id is not True for r_id in earlyget_id]):
664
- t.sh.highlight('Finalising Early-gets')
665
- t.context.delayedactions_hub.finalise(* [r_id for r_id in earlyget_id
666
- if r_id and r_id is not True])
754
+ t.sh.highlight("Finalising Early-gets")
755
+ t.context.delayedactions_hub.finalise(
756
+ *[
757
+ r_id
758
+ for r_id in earlyget_id
759
+ if r_id and r_id is not True
760
+ ]
761
+ )
667
762
 
668
763
  for ir, rhandler in enumerate(rhandlers):
669
764
  if talkative:
@@ -671,9 +766,11 @@ def diff(*args, **kw):
671
766
  rhandler.quickview(nb=ir + 1, indent=0)
672
767
  print(t.line)
673
768
  if not rhandler.complete:
674
- logger.error('Incomplete Resource Handler for diff [%s]', rhandler)
769
+ logger.error(
770
+ "Incomplete Resource Handler for diff [%s]", rhandler
771
+ )
675
772
  if fatal:
676
- raise ValueError('Incomplete Resource Handler for diff')
773
+ raise ValueError("Incomplete Resource Handler for diff")
677
774
  else:
678
775
  rlok.append(False)
679
776
  continue
@@ -686,52 +783,65 @@ def diff(*args, **kw):
686
783
  rc = sections[ir].get()
687
784
  if not rc:
688
785
  try:
689
- logger.error('Cannot get the reference resource: %s',
690
- rhandler.locate())
786
+ logger.error(
787
+ "Cannot get the reference resource: %s",
788
+ rhandler.locate(),
789
+ )
691
790
  except Exception:
692
- logger.error('Cannot get the reference resource: ???')
791
+ logger.error("Cannot get the reference resource: ???")
693
792
  if fatal:
694
- raise ValueError('Cannot get the reference resource')
793
+ raise ValueError("Cannot get the reference resource")
695
794
  else:
696
- logger.info('The reference file is stored under: %s',
697
- rhandler.container.localpath())
795
+ logger.info(
796
+ "The reference file is stored under: %s",
797
+ rhandler.container.localpath(),
798
+ )
698
799
 
699
800
  # What are the differences ?
700
801
  if rc:
701
802
  # priority is given to the diff implemented in the DataContent
702
803
  if rhandler.resource.clscontents.is_diffable():
703
804
  source_contents = rhandler.resource.contents_handler(
704
- datafmt=source_container[ir].actualfmt)
805
+ datafmt=source_container[ir].actualfmt
806
+ )
705
807
  source_contents.slurp(source_container[ir])
706
808
  ref_contents = rhandler.contents
707
809
  rc = source_contents.diff(ref_contents)
708
810
  else:
709
- rc = t.sh.diff(source_container[ir].localpath(),
710
- rhandler.container.localpath(),
711
- fmt=rhandler.container.actualfmt)
811
+ rc = t.sh.diff(
812
+ source_container[ir].localpath(),
813
+ rhandler.container.localpath(),
814
+ fmt=rhandler.container.actualfmt,
815
+ )
712
816
 
713
817
  # Delete the reference file
714
818
  lazzy_container[ir].clear()
715
819
 
716
820
  # Now proceed with the result
717
- logger.info('Diff return %s', str(rc))
718
- t.context.diff_history.append_record(rc, source_container[ir], rhandler)
821
+ logger.info("Diff return %s", str(rc))
822
+ t.context.diff_history.append_record(
823
+ rc, source_container[ir], rhandler
824
+ )
719
825
  try:
720
- logger.info('Diff result %s', str(rc.result))
826
+ logger.info("Diff result %s", str(rc.result))
721
827
  except AttributeError:
722
828
  pass
723
829
  if not rc:
724
830
  try:
725
- logger.warning('Some diff occurred with %s', rhandler.locate())
831
+ logger.warning(
832
+ "Some diff occurred with %s", rhandler.locate()
833
+ )
726
834
  except Exception:
727
- logger.warning('Some diff occurred with ???')
835
+ logger.warning("Some diff occurred with ???")
728
836
  try:
729
837
  rc.result.differences()
730
838
  except Exception:
731
839
  pass
732
840
  if fatal:
733
- logger.critical('Difference in resource comparison is fatal')
734
- raise ValueError('Fatal diff')
841
+ logger.critical(
842
+ "Difference in resource comparison is fatal"
843
+ )
844
+ raise ValueError("Fatal diff")
735
845
  if t.sh.trace:
736
846
  print()
737
847
  rlok.append(rc)
@@ -746,7 +856,7 @@ def magic(localpath, **kw):
746
856
  """
747
857
  kw.update(
748
858
  unknown=True,
749
- magic='magic://localhost/' + localpath,
859
+ magic="magic://localhost/" + localpath,
750
860
  filename=localpath,
751
861
  )
752
862
  rhmagic = rh(**kw)
@@ -770,22 +880,24 @@ def archive_refill(*args, **kw):
770
880
  t = sessions.current()
771
881
 
772
882
  # First, retrieve arguments of the toolbox command itself
773
- loglevel = kw.pop('loglevel', None)
774
- talkative = kw.pop('verbose', active_verbose)
883
+ loglevel = kw.pop("loglevel", None)
884
+ talkative = kw.pop("verbose", active_verbose)
775
885
 
776
886
  with _tb_isolate(t, loglevel):
777
-
778
887
  # Distinguish between section arguments, and resource loader arguments
779
888
  opts, kwclean = stripargs_section(**kw)
780
- fatal = opts.get('fatal', True)
889
+ fatal = opts.get("fatal", True)
781
890
 
782
891
  # Print the user inputs
783
892
  if talkative:
784
- nicedump('Archive Refill Ressource+Provider description', **kwclean)
893
+ nicedump(
894
+ "Archive Refill Ressource+Provider description", **kwclean
895
+ )
785
896
 
786
897
  # Create the resource handlers
787
- kwclean['container'] = footprints.proxy.container(uuid4fly=True,
788
- uuid4flydir="archive_refills")
898
+ kwclean["container"] = footprints.proxy.container(
899
+ uuid4fly=True, uuid4flydir="archive_refills"
900
+ )
789
901
  rl = rload(*args, **kwclean)
790
902
 
791
903
  @contextmanager
@@ -795,36 +907,56 @@ def archive_refill(*args, **kw):
795
907
  try:
796
908
  yield wrap_rc
797
909
  except Exception as e:
798
- logger.error('Something wrong (action %s): %s. %s',
799
- action, str(e), traceback.format_exc())
800
- wrap_rc['rc'] = False
801
- wrap_rc['exc'] = e
802
- if fatal and not wrap_rc['rc']:
803
- logger.critical('Fatal error with action %s.', action)
804
- raise RuntimeError('Could not {:s} resource: {!s}'.format(action,
805
- wrap_rc['rc']))
910
+ logger.error(
911
+ "Something wrong (action %s): %s. %s",
912
+ action,
913
+ str(e),
914
+ traceback.format_exc(),
915
+ )
916
+ wrap_rc["rc"] = False
917
+ wrap_rc["exc"] = e
918
+ if fatal and not wrap_rc["rc"]:
919
+ logger.critical("Fatal error with action %s.", action)
920
+ raise RuntimeError(
921
+ "Could not {:s} resource: {!s}".format(
922
+ action, wrap_rc["rc"]
923
+ )
924
+ )
806
925
 
807
926
  with t.sh.ftppool():
808
927
  for ir, rhandler in enumerate(rl):
809
928
  if talkative:
810
- t.sh.subtitle('Resource no {:02d}/{:02d}'.format(ir + 1, len(rl)))
929
+ t.sh.subtitle(
930
+ "Resource no {:02d}/{:02d}".format(ir + 1, len(rl))
931
+ )
811
932
  rhandler.quickview(nb=ir + 1, indent=0)
812
- if not (rhandler.store.use_cache() and rhandler.store.use_archive()):
813
- logger.info('The requested store does not have both the cache and archive capabilities. ' +
814
- 'Skipping this ressource handler.')
933
+ if not (
934
+ rhandler.store.use_cache() and rhandler.store.use_archive()
935
+ ):
936
+ logger.info(
937
+ "The requested store does not have both the cache and archive capabilities. "
938
+ + "Skipping this ressource handler."
939
+ )
815
940
  continue
816
- with _fatal_wrap('get') as get_status:
817
- get_status['rc'] = rhandler.get(incache=True, intent=intent.IN,
818
- fmt=rhandler.resource.nativefmt)
941
+ with _fatal_wrap("get") as get_status:
942
+ get_status["rc"] = rhandler.get(
943
+ incache=True,
944
+ intent=intent.IN,
945
+ fmt=rhandler.resource.nativefmt,
946
+ )
819
947
  put_status = dict(rc=False)
820
- if get_status['rc']:
821
- with _fatal_wrap('put') as put_status:
822
- put_status['rc'] = rhandler.put(inarchive=True,
823
- fmt=rhandler.resource.nativefmt)
948
+ if get_status["rc"]:
949
+ with _fatal_wrap("put") as put_status:
950
+ put_status["rc"] = rhandler.put(
951
+ inarchive=True, fmt=rhandler.resource.nativefmt
952
+ )
824
953
  rhandler.container.clear()
825
954
  if talkative:
826
- t.sh.highlight('Result from get: [{!s}], from put: [{!s}]'
827
- .format(get_status['rc'], put_status['rc']))
955
+ t.sh.highlight(
956
+ "Result from get: [{!s}], from put: [{!s}]".format(
957
+ get_status["rc"], put_status["rc"]
958
+ )
959
+ )
828
960
 
829
961
  return rl
830
962
 
@@ -842,7 +974,7 @@ def stack_archive_refill(*args, **kw):
842
974
 
843
975
  :return: A list of :class:`vortex.data.handlers.Handler` objects.
844
976
  """
845
- kw['block'] = 'stacks'
977
+ kw["block"] = "stacks"
846
978
  return archive_refill(*args, **kw)
847
979
 
848
980
 
@@ -852,21 +984,24 @@ def namespaces(**kw):
852
984
  used. By default tracks ``stores`` and ``providers`` but one could give an
853
985
  ``only`` argument.
854
986
  """
855
- rematch = re.compile('|'.join(kw.get('match', '.').split(',')),
856
- re.IGNORECASE)
857
- if 'only' in kw:
858
- usedcat = kw['only'].split(',')
987
+ rematch = re.compile(
988
+ "|".join(kw.get("match", ".").split(",")), re.IGNORECASE
989
+ )
990
+ if "only" in kw:
991
+ usedcat = kw["only"].split(",")
859
992
  else:
860
- usedcat = ('provider', 'store')
993
+ usedcat = ("provider", "store")
861
994
  nameseen = dict()
862
995
  for cat in [footprints.collectors.get(tag=x) for x in usedcat]:
863
996
  for cls in cat():
864
997
  fp = cls.footprint_retrieve().attr
865
- netattr = fp.get('namespace', None)
998
+ netattr = fp.get("namespace", None)
866
999
  if not netattr:
867
- netattr = fp.get('netloc', None)
868
- if netattr and 'values' in netattr:
869
- for netname in filter(lambda x: rematch.search(x), netattr['values']):
1000
+ netattr = fp.get("netloc", None)
1001
+ if netattr and "values" in netattr:
1002
+ for netname in filter(
1003
+ lambda x: rematch.search(x), netattr["values"]
1004
+ ):
870
1005
  if netname not in nameseen:
871
1006
  nameseen[netname] = list()
872
1007
  nameseen[netname].append(cls.fullname())
@@ -875,17 +1010,18 @@ def namespaces(**kw):
875
1010
 
876
1011
  def print_namespaces(**kw):
877
1012
  """Formatted print of current namespaces."""
878
- prefix = kw.pop('prefix', '+ ')
1013
+ prefix = kw.pop("prefix", "+ ")
879
1014
  nd = namespaces(**kw)
880
1015
  justify = max([len(x) for x in nd.keys()])
881
- linesep = ",\n" + ' ' * (justify + len(prefix) + 2)
1016
+ linesep = ",\n" + " " * (justify + len(prefix) + 2)
882
1017
  for k, v in sorted(nd.items()):
883
1018
  nice_v = linesep.join(v) if len(v) > 1 else v[0]
884
- print(prefix + k.ljust(justify), '[' + nice_v + ']')
1019
+ print(prefix + k.ljust(justify), "[" + nice_v + "]")
885
1020
 
886
1021
 
887
- def clear_promises(clear=None, netloc='promise.cache.fr', scheme='vortex',
888
- storeoptions=None):
1022
+ def clear_promises(
1023
+ clear=None, netloc="promise.cache.fr", scheme="vortex", storeoptions=None
1024
+ ):
889
1025
  """Remove all promises that have been made in the current session.
890
1026
 
891
1027
  :param netloc: Netloc of the promise's cache store to clean up
@@ -913,50 +1049,49 @@ def rescue(*files, **opts):
913
1049
 
914
1050
  # Summarise diffs...
915
1051
  if len(t.context.diff_history):
916
- sh.header('Summary of automatic toolbox diffs')
1052
+ sh.header("Summary of automatic toolbox diffs")
917
1053
  t.context.diff_history.show()
918
1054
 
919
1055
  # Force clearing of all promises
920
1056
  clear_promises(clear=True)
921
1057
 
922
- sh.header('Rescuing current dir')
1058
+ sh.header("Rescuing current dir")
923
1059
  sh.dir(output=False, fatal=False)
924
1060
 
925
- logger.info('Rescue files %s', files)
1061
+ logger.info("Rescue files %s", files)
926
1062
 
927
- if 'VORTEX_RESCUE' in env and env.false('VORTEX_RESCUE'):
928
- logger.warning('Skip rescue <VORTEX_RESCUE=%s>', env.VORTEX_RESCUE)
1063
+ if "VORTEX_RESCUE" in env and env.false("VORTEX_RESCUE"):
1064
+ logger.warning("Skip rescue <VORTEX_RESCUE=%s>", env.VORTEX_RESCUE)
929
1065
  return False
930
1066
 
931
1067
  if files:
932
1068
  items = list(files)
933
1069
  else:
934
- items = sh.glob('*')
1070
+ items = sh.glob("*")
935
1071
 
936
- rfilter = opts.get('filter', env.VORTEX_RESCUE_FILTER)
1072
+ rfilter = opts.get("filter", env.VORTEX_RESCUE_FILTER)
937
1073
  if rfilter is not None:
938
- logger.warning('Rescue filter <%s>', rfilter)
939
- select = '|'.join(re.split(r'[,;:]+', rfilter))
1074
+ logger.warning("Rescue filter <%s>", rfilter)
1075
+ select = "|".join(re.split(r"[,;:]+", rfilter))
940
1076
  items = [x for x in items if re.search(select, x, re.IGNORECASE)]
941
- logger.info('Rescue filter [%s]', select)
1077
+ logger.info("Rescue filter [%s]", select)
942
1078
 
943
- rdiscard = opts.get('discard', env.VORTEX_RESCUE_DISCARD)
1079
+ rdiscard = opts.get("discard", env.VORTEX_RESCUE_DISCARD)
944
1080
  if rdiscard is not None:
945
- logger.warning('Rescue discard <%s>', rdiscard)
946
- select = '|'.join(re.split(r'[,;:]+', rdiscard))
1081
+ logger.warning("Rescue discard <%s>", rdiscard)
1082
+ select = "|".join(re.split(r"[,;:]+", rdiscard))
947
1083
  items = [x for x in items if not re.search(select, x, re.IGNORECASE)]
948
- logger.info('Rescue discard [%s]', select)
1084
+ logger.info("Rescue discard [%s]", select)
949
1085
 
950
1086
  if items:
951
-
952
- bkupdir = opts.get('bkupdir', env.VORTEX_RESCUE_PATH)
1087
+ bkupdir = opts.get("bkupdir", env.VORTEX_RESCUE_PATH)
953
1088
 
954
1089
  if bkupdir is None:
955
- logger.error('No rescue directory defined.')
1090
+ logger.error("No rescue directory defined.")
956
1091
  else:
957
- logger.info('Backup directory defined by user < %s >', bkupdir)
1092
+ logger.info("Backup directory defined by user < %s >", bkupdir)
958
1093
  items.sort()
959
- logger.info('Rescue items %s', str(items))
1094
+ logger.info("Rescue items %s", str(items))
960
1095
  sh.mkdir(bkupdir)
961
1096
  mkmove = False
962
1097
  st1 = sh.stat(sh.getcwd())
@@ -977,6 +1112,6 @@ def rescue(*files, **opts):
977
1112
  thisrescue(ritem, rtarget)
978
1113
 
979
1114
  else:
980
- logger.warning('No item to rescue.')
1115
+ logger.warning("No item to rescue.")
981
1116
 
982
1117
  return bool(items)