def addict(cfig, key, val, parents, index): """Add a new [parents...]key=value pair to a nested dict.""" for p in parents: # drop down the parent list cfig = cfig[p] if not isinstance(cfig, dict): # an item of this name has already been encountered at this level raise FileParseError( 'line %d: already encountered %s', index, itemstr(parents, key, val)) if key in cfig: # this item already exists if (key == 'graph' and ( parents == ['scheduling', 'dependencies'] or len(parents) == 3 and parents[-3:-1] == ['scheduling', 'dependencies'])): # append the new graph string to the existing one LOG.debug('Merging graph strings under %s', itemstr(parents)) if not isinstance(cfig[key], list): cfig[key] = [cfig[key]] cfig[key].append(val) else: # otherwise override the existing item LOG.debug( 'overriding %s old value: %s new value: %s', itemstr(parents, key), cfig[key], val) cfig[key] = val else: cfig[key] = val
def addict(cfig, key, val, parents, index): """Add a new [parents...]key=value pair to a nested dict.""" for p in parents: # drop down the parent list cfig = cfig[p] if not isinstance(cfig, dict): # an item of this name has already been encountered at this level raise FileParseError('line %d: already encountered %s', index, itemstr(parents, key, val)) if key in cfig: # this item already exists if (key == 'graph' and (parents == ['scheduling', 'dependencies'] or len(parents) == 3 and parents[-3:-1] == ['scheduling', 'dependencies'])): # append the new graph string to the existing one LOG.debug('Merging graph strings under %s', itemstr(parents)) if not isinstance(cfig[key], list): cfig[key] = [cfig[key]] cfig[key].append(val) else: # otherwise override the existing item LOG.debug('overriding %s old value: %s new value: %s', itemstr(parents, key), cfig[key], val) cfig[key] = val else: cfig[key] = val
def get(self, keys=None, sparse=False): """ Retrieve items or sections, sparse or dense, by list of keys: [sec1,sec2,item] => [sec1] [[sec2]] item = value """ if sparse: cfg = self.sparse else: self.expand() cfg = self.dense parents = [] if keys: for key in keys: try: cfg = cfg[key] except (KeyError, TypeError): if parents in self.manyparents or key in self.get(parents): raise ItemNotFoundError(itemstr(parents, key)) raise InvalidConfigError(itemstr(parents, key), self.spec.name) else: parents.append(key) return cfg
def __str__(self): msg = '' if self.vtype: msg += f'(type={self.vtype}) ' if self.key: msg += itemstr(self.keys, self.key) elif self.value: msg += itemstr(self.keys[:-1], self.keys[-1], value=self.value) if self.msg or self.exc: msg += (f' - ({self.exc or ""}' f'{": " if (self.exc and self.msg) else ""}' f'{self.msg or ""})') return msg
def __str__(self): msg = '' if self.vtype: msg += f'(type={self.vtype}) ' if self.key: msg += itemstr(self.keys, self.key) elif self.value: msg += itemstr(self.keys[:-1], self.keys[-1], value=self.value) if self.msg or self.exc: msg += ( f' - ({self.exc or ""}' f'{": " if (self.exc and self.msg) else ""}' f'{self.msg or ""})' ) return msg
def get(self, keys=None, sparse=False): """ Retrieve items or sections, sparse or dense, by list of keys: [sec1,sec2,item] => [sec1] [[sec2]] item = value """ if sparse: cfg = self.sparse else: self.expand() cfg = self.dense parents = [] if keys: for key in keys: try: cfg = cfg[key] except KeyError: raise ItemNotFoundError(itemstr(parents, key)) else: parents.append(key) return cfg
def get(self, keys=None, sparse=False): """ Retrieve items or sections, sparse or dense, by list of keys: [sec1,sec2,item] => [sec1] [[sec2]] item = value """ if sparse: cfg = self.sparse else: self.expand() cfg = self.dense parents = [] if keys: for key in keys: try: cfg = cfg[key] except KeyError: raise ItemNotFoundError(itemstr(parents, key)) else: parents.append(key) return cfg
def addict(cfig, key, val, parents, index): """Add a new [parents...]key=value pair to a nested dict.""" for p in parents: # drop down the parent list cfig = cfig[p] if not isinstance(cfig, dict): # an item of this name has already been encountered at this level raise FileParseError( 'line %d: already encountered %s', index, itemstr(parents, key, val)) if key in cfig: oldval = cfig[key] # this item already exists if ( parents[0:2] == ['scheduling', 'graph'] or parents[0:2] == ['scheduling', 'dependencies'] # back compat <=7.X ): # append the new graph string to the existing one if not isinstance(cfig, list): cfig[key] = [cfig[key]] cfig[key].append(val) else: cfig[key] = val LOG.debug( '%s: already exists in configuration:\nold: %s\nnew: %s', key, repr(oldval), repr(cfig[key])) # repr preserves \n else: cfig[key] = val
def addict(cfig, key, val, parents, index): """Add a new [parents...]key=value pair to a nested dict.""" for p in parents: # drop down the parent list cfig = cfig[p] if not isinstance(cfig, dict): # an item of this name has already been encountered at this level raise FileParseError('line %d: already encountered %s', index, itemstr(parents, key, val)) if key in cfig: oldval = cfig[key] # this item already exists if (parents[0:2] == ['scheduling', 'graph'] or # BACK COMPAT: [scheduling][dependencies] # url: # https://github.com/cylc/cylc-flow/pull/3191 # from: # Cylc<=7 # to: # Cylc8 # remove at: # Cylc9 parents[0:2] == ['scheduling', 'dependencies']): # append the new graph string to the existing one if not isinstance(cfig, list): cfig[key] = [cfig[key]] cfig[key].append(val) else: cfig[key] = val LOG.debug('%s: already exists in configuration:\nold: %s\nnew: %s', key, repr(oldval), repr(cfig[key])) # repr preserves \n else: cfig[key] = val
def addsect(cfig, sname, parents): """Add a new section to a nested dict.""" for p in parents: # drop down the parent list cfig = cfig[p] if sname in cfig: # this doesn't warrant a warning unless contained items are repeated LOG.debug( 'Section already encountered: %s', itemstr(parents + [sname])) else: cfig[sname] = OrderedDictWithDefaults()
def addsect(cfig, sname, parents): """Add a new section to a nested dict.""" for p in parents: # drop down the parent list cfig = cfig[p] if sname in cfig: # this doesn't warrant a warning unless contained items are repeated LOG.debug( 'Section already encountered: %s', itemstr(parents + [sname])) else: cfig[sname] = OrderedDictWithDefaults()
def checkspec(spec_root, parents=None): """Check that the file spec is a nested dict of specifications""" stack = [[spec_root, []]] while stack: spec, parents = stack.pop() for key, value in spec.items(): pars = parents + [key] if isinstance(value, dict): stack.append([value, pars]) elif not isinstance(value, list): raise ParsecError("Illegal file spec item: %s" % itemstr(pars, repr(value)))
def checkspec(spec_root, parents=None): """Check that the file spec is a nested dict of specifications""" stack = [[spec_root, []]] while stack: spec, parents = stack.pop() for key, value in spec.items(): pars = parents + [key] if isinstance(value, dict): stack.append([value, pars]) elif not isinstance(value, list): raise ParsecError( "Illegal file spec item: %s" % itemstr( pars, repr(value)))
def mdump(self, mkeys=None, sparse=False, pnative=False, prefix='', oneline=False, none_str=''): if oneline: items = [] if mkeys: for keys in mkeys: item = self.get(keys, sparse) if isinstance(item, list) or isinstance(item, dict): raise NotSingleItemError(itemstr(keys)) if not item: item = none_str or "None" items.append(str(item)) # TODO - quote items if they contain spaces or comment delimiters? print(prefix + ' '.join(items)) elif mkeys: for keys in mkeys: self.dump(keys, sparse, pnative, prefix, none_str)
def mdump(self, mkeys=None, sparse=False, pnative=False, prefix='', oneline=False, none_str=''): if oneline: items = [] if mkeys: for keys in mkeys: item = self.get(keys, sparse) if isinstance(item, list) or isinstance(item, dict): raise NotSingleItemError(itemstr(keys)) if not item: item = none_str or "None" items.append(str(item)) # TODO - quote items if they contain spaces or comment delimiters? print(prefix + ' '.join(items)) elif mkeys: for keys in mkeys: self.dump(keys, sparse, pnative, prefix, none_str)
def test_itemstr_no_item(self): parents = ["parent1", "parent2", "Value"] text = itemstr(parents=parents, item=None, value="Anything") self.assertEqual('[parent1][parent2]Value = Anything', text)
def test_itemstr_no_parents_no_value(self): text = itemstr(parents=None, item="Value", value=None) self.assertEqual('Value', text)
def test_itemstr_no_parents(self): text = itemstr(parents=None, item="Value", value='Anything') self.assertEqual('Value = Anything', text)