def test_get(): """ Tests Config.get(), comparing the return value with expected one. For inner structure check Config.flatten() is used. """ #Get scalar value by slashed-structured key config = Config({'a': {'b': 1}}) get_key = 'a/b' exp_ret = 1 exp_flat = {'a/b': 1} assert config.get(get_key) == exp_ret assert config.flatten() == exp_flat #Get scalar value by slashed-structured key via dotted access config = Config({'a': {'b': 1}}) get_key = 'a/b' exp_ret = 1 exp_flat = {'a/b': 1} for simple_key in get_key.split('/'): config = getattr(config, simple_key) assert config == exp_ret #Get dict value by simple key config = Config({'a': {'b': 1}}) get_key = 'a' exp_ret = {'b': 1} exp_flat = {'a/b': 1} assert config.get(get_key) == exp_ret assert getattr(config, get_key).flatten() == exp_ret # check dotted access assert config.flatten() == exp_flat
def test_config_init(): """ Tests Config.__init__() using input of Config type. For inner structure check Config.flatten() is used. """ #Basically, there nothing to test here, #but since Config can be initialized with its own instance... init_config = Config({'a': 0}) exp_flat = {'a': 0} config = Config(init_config) assert config.flatten() == exp_flat
def test_dict_init_bad(): """ Tests Config.__init__() using BAD input of dictionary type. """ #Int-keyed dictionary initialization init_dict = {0: 1} with pytest.raises(TypeError): Config(init_dict) #Bool-keyed dictionary initialization init_dict = {False: True} with pytest.raises(TypeError): Config(init_dict)
def test_save_to_c(self): pipeline = Pipeline(config=Config(some=100)) save_data_to(data=200, dst=C('value'), pipeline=pipeline) assert pipeline.config['some'] == 100 assert pipeline.config['value'] == 200
def test_save_to_list(self): arr = np.zeros(3) pipeline = Pipeline(config=Config(some=100)) save_data_to(data=[[1, 2, 3], 200], dst=[arr, C('value')], pipeline=pipeline) assert (arr == [1, 2, 3]).all() assert pipeline.config['value'] == 200
def test_list_init_bad(): """ Tests Config.__init__() using BAD input of list type. """ #Int-keyed list initialization init_list = [(0, 1)] with pytest.raises(TypeError): Config(init_list) #Bool-keyed list initialization init_list = [(False, True)] with pytest.raises(TypeError): Config(init_list) #Bad-shaped list initialization init_list = [('a', 0, 1)] with pytest.raises(ValueError): Config(init_list)
def test_add(): """ Tests Config.add(), adding up two Config instances. For result inner structure check Config.flatten() is used. """ #Simple summands with non-empty intersection augend = Config({'a': 1, 'b': 2}) addend = Config({'b': 3, 'c': 4}) exp_flat = {'a': 1, 'b': 3, 'c': 4} result = augend + addend assert result.flatten() == exp_flat #Nested summands with non-empty intersection augend = Config({'a/b': 1, 'a/c': 2}) addend = Config({'a/c/d': 3, 'e/f': 4}) exp_flat = {'a/b': 1, 'a/c/d': 3, 'e/f': 4} result = augend + addend assert result.flatten() == exp_flat #Nested summands with non-standard values such as None and empty dict augend = Config({'a/b': 1, 'b/d': {}}) addend = Config({'a': {}, 'b/d': None}) exp_flat = {'a/b': 1, 'b/d': None} result = augend + addend assert result.flatten() == exp_flat
def test_iadd_items(): """ Tests Config.config.__iadd__() For inner structure check Config.flatten() is used. """ config_old = Config({'a/b': 1, 'a/c': 2}) config_old['a'] = 0 exp_flat = {'a': 0} assert config_old.flatten() == exp_flat config_old = Config({'a/b': 1, 'a/c': 2}) config_old['a'] = dict(b=0, d=3) exp_flat = {'a/b': 0, 'a/d': 3} assert config_old.flatten() == exp_flat config_old = Config({'a/b': 1, 'a/c': 2}) config_old['a'] += dict(b=0, d=3) exp_flat = {'a/b': 0, 'a/c': 2, 'a/d': 3} assert config_old.flatten() == exp_flat
def test_get(): """ Tests Config.get(), comparing the return value with expected one. For inner structure check Config.flatten() is used. """ #Get scalar value by slashed-structured key config = Config({'a': {'b': 1}}) get_key = 'a/b' exp_ret = 1 exp_flat = {'a/b': 1} assert config.get(get_key) == exp_ret assert config.flatten() == exp_flat #Get dict value by simple key config = Config({'a': {'b': 1}}) get_key = 'a' exp_ret = {'b': 1} exp_flat = {'a/b': 1} assert config.get(get_key) == exp_ret assert config.flatten() == exp_flat
def test_pop(): """ Tests Config.pop(), comparing the return value with expected one. For inner structure check Config.flatten() is used. """ #Pop scalar value by slashed-structured key config = Config({'a': 1, 'b/c': 2, 'b/d': 3}) pop_key = 'b/c' exp_ret = 2 exp_flat = {'a': 1, 'b/d': 3} assert config.pop(pop_key) == exp_ret assert config.flatten() == exp_flat #Pop dict value by simple key config = Config({'a': 1, 'b/c': 2, 'b/d': 3}) pop_key = 'b' exp_ret = {'c': 2, 'd': 3} exp_flat = {'a': 1} assert config.pop(pop_key) == exp_ret assert config.flatten() == exp_flat
class MultiModel(TFModel): model_args = Config() @classmethod def default_config(cls): config = TFModel.default_config() config['body/block'] = {} return config @classmethod def initial_block(cls, inputs, name='initial_block', **kwargs): kwargs = cls.fill_params(name, **kwargs) cls.model_args['initial_block'] = kwargs return inputs @classmethod def body(cls, inputs, name='body', **kwargs): kwargs = cls.fill_params(name, **kwargs) cls.model_args['body'] = kwargs block_args = cls.pop('block', kwargs) block_args = {**kwargs, **block_args} input_1, _ = inputs inputs = cls.block(input_1, **block_args) return inputs @classmethod def block(cls, input_1, **kwargs): kwargs = cls.fill_params('body/block', **kwargs) cls.model_args['block'] = kwargs return input_1 @classmethod def head(cls, inputs, name='head', **kwargs): inputs = super().head(inputs, name='head', **kwargs) kwargs = cls.fill_params(name, **kwargs) cls.model_args['head'] = kwargs return inputs
def test_list_init(): """ Tests Config.__init__() using input of list type. For inner structure check Config.flatten() is used. """ #Slashed-structured list initialization init_list = [('a', 1), ('b/c', 2), ('b/d', 3)] exp_flat = {'a': 1, 'b/c': 2, 'b/d': 3} config = Config(init_list) assert config.flatten() == exp_flat #Nested-structured list initialization init_list = [('a', {}), ('b', {'c': 2, 'd': 3})] exp_flat = {'a': {}, 'b/c': 2, 'b/d': 3} config = Config(init_list) assert config.flatten() == exp_flat #Mixed-structured list initialization init_list = [('a', None), ('b/c', 2), ('b', {'d': 3})] exp_flat = {'a': None, 'b/c': 2, 'b/d': 3} config = Config(init_list) assert config.flatten() == exp_flat #Config-structured list initialization init_list = [('a', Config({'b': 2}))] exp_flat = {'a/b': 2} config = Config(init_list) assert config.flatten() == exp_flat
def test_flatten(): """ Tests Config.flatten() """ #Flatten none config config = Config(None) exp_flat = {} assert config.flatten() == exp_flat #Flatten empty config config = Config({}) exp_flat = {} assert config.flatten() == exp_flat #Flatten simple config config = Config({'a': 1}) exp_flat = {'a': 1} assert config.flatten() == exp_flat #Flatten nested config config = Config({'a': {'b': {}, 'c': {'d': None}}}) exp_flat = {'a/b': {}, 'a/c/d': None} assert config.flatten() == exp_flat
def test_update(): """ Tests Config.update() For inner structure check Config.flatten() is used. """ #Value replacement by slashed-structured key config_old = Config({'a/b': 1, 'a/c': 2}) config_new = Config({'a/c': 3, 'a/d': 4}) exp_flat = {'a/b': 1, 'a/c': 3, 'a/d': 4} config_old.update(config_new) assert config_old.flatten() == exp_flat #Value insertion by slashed-structured key config_old = Config({'a/b': 1}) config_new = Config({'a/c/d': 2}) exp_flat = {'a/b': 1, 'a/c/d': 2} config_old.update(config_new) assert config_old.flatten() == exp_flat #Update with Config instance including None and empty dict values config_old = Config({'a': {}, 'b': None}) config_new = Config({'a': None, 'b': {}}) config_old.update(config_new) exp_flat = {'a': None, 'b': {}} assert config_old.flatten() == exp_flat
def config(): _config = dict(key1='val1', key2=dict()) _config['key2']['subkey1'] = 'val21' return Config(_config)
def test_values(): """ Tests Config.values() For dict_values conversion cast to list is used. """ #Simple config = Config({'a': 1}) exp_full = [1] exp_flat = [1] assert list(config.values(flatten=False)).sort() == exp_full.sort() assert list(config.values(flatten=True)).sort() == exp_flat.sort() #Nested config = Config({'a': {'b': 1, 'c': 2}}) exp_full = [{'b': 1, 'c': 2}] exp_flat = [1, 2] assert list(config.values(flatten=False)).sort() == exp_full.sort() assert list(config.values(flatten=True)).sort() == exp_flat.sort() #Deeply nested config = Config({'a': {'b': 1, 'c': {'d': 2}}}) exp_full = [{'b': 1, 'c': {'d': 2}}] exp_flat = [1, 2] assert list(config.values(flatten=False)).sort() == exp_full.sort() assert list(config.values(flatten=True)).sort() == exp_flat.sort()
def test_keys(): """ Tests Config.keys() For dict_keys conversion cast to list is used. """ #Simple config = Config({'a': 1}) exp_full = ['a'] exp_flat = ['a'] assert list(config.keys(flatten=False)).sort() == exp_full.sort() assert list(config.keys(flatten=True)).sort() == exp_flat.sort() #Nested config = Config({'a': {'b': 1, 'c': 2}}) exp_full = ['a'] exp_flat = ['a/b', 'a/c'] assert list(config.keys(flatten=False)).sort() == exp_full.sort() assert list(config.keys(flatten=True)).sort() == exp_flat.sort() #Deeply nested config = Config({'a': {'b': 1, 'c': {'d': 2}}}) exp_full = ['a'] exp_flat = ['a/b', 'a/c/d'] assert list(config.keys(flatten=False)).sort() == exp_full.sort() assert list(config.keys(flatten=True)).sort() == exp_flat.sort()
def test_items(): """ Tests Config.items() For dict_items conversion cast to list is used. """ #Simple config = Config({'a': 1}) exp_full = [('a', 1)] exp_flat = [('a', 1)] assert list(config.items(flatten=False)) == exp_full assert list(config.items(flatten=True)) == exp_flat #Nested config = Config({'a': {'b': 1, 'c': 2}}) exp_full = [('a', {'b': 1, 'c': 2})] exp_flat = [('a/b', 1), ('a/c', 2)] assert list(config.items(flatten=False)).sort() == exp_full.sort() assert list(config.items(flatten=True)).sort() == exp_flat.sort() #Deeply nested config = Config({'a': {'b': 1, 'c': {'d': 2}}}) exp_full = [('a', {'b': 1, 'c': {'d': 2}})] exp_flat = [('a/b', 1), ('a/c/d', 2)] assert list(config.items(flatten=False)).sort() == exp_full.sort() assert list(config.items(flatten=True)).sort() == exp_flat.sort()
def test_dict_init(): """ Tests Config.__init__() using input of dictionary type. For inner structure check Config.flatten() is used. """ #Slashed-structured dictionary initialization init_dict = {'a': 1, 'b/c': 2, 'b/d': 3} exp_flat = {'a': 1, 'b/c': 2, 'b/d': 3} config = Config(init_dict) assert config.flatten() == exp_flat #Nested-structured dictionary initialization init_dict = {'a': {}, 'b': {'c': 2, 'd': 3}} exp_flat = {'a': {}, 'b/c': 2, 'b/d': 3} config = Config(init_dict) assert config.flatten() == exp_flat #Mixed-structured dictionary initialization init_dict = {'a': None, 'b/c': 2, 'b': {'d': 3}} exp_flat = {'a': None, 'b/c': 2, 'b/d': 3} config = Config(init_dict) assert config.flatten() == exp_flat #Config-structured dictionary initialization init_dict = {'a': Config({'b': 2})} exp_flat = {'a/b': 2} config = Config(init_dict) assert config.flatten() == exp_flat
def test_put(): """ Tests Config.put(), placing value by key in Config instance. For inner structure check Config.flatten() is used. """ #Put scalar value by simple key config = Config({'a': 1}) put_key = 'b' put_val = 2 exp_flat = {'a': 1, 'b': 2} config.put(put_key, put_val) assert config.flatten() == exp_flat #Put scalar value by slashed-structured key config = Config({'a/b': 1}) put_key = 'a/c' put_val = 2 exp_flat = {'a/b': 1, 'a/c': 2} config.put(put_key, put_val) assert config.flatten() == exp_flat #Put dict value by simple key config = Config({'a/b': 1}) put_key = 'a' put_val = {'c': 2} exp_flat = {'a/b': 1, 'a/c': 2} config.put(put_key, put_val) assert config.flatten() == exp_flat