def _get_constants() -> dict[str, Any]: """Get constants from config or local json with updating system. Pick new constants that are defined in TYPES but are not saved in the config yet from the json. Upgrades constants that already exist, given the version number. """ from labster.domain.models.config import Config config = Config.query.first() if config is None: config = Config() db.session.add(config) initial_constants = get_initial_constants() # upgrade _upgrade_if_needed(config, initial_constants) constants = config.data dotted_constants = DottedCollection.factory(constants) json_dotted_constants = DottedCollection.factory(initial_constants) if dotted_constants: for key in TYPES.keys(): # do not write "key not in .keys()", it doesn't return "dotted keys". if dotted_constants.get(key, _MARKER) is _MARKER: dotted_constants[key] = json_dotted_constants.get(key) constants = dotted_constants.to_python() return constants
def _print_table_from(print_obj, fields): if isinstance(print_obj, dict): print_obj = [print_obj] arr = DottedCollection.factory(print_obj) col_lengths = [] if fields is None: fields = [x for x in arr[0].keys()] else: fields = fields.split(",") for col in fields: try: col_lengths.append( max([ len(str(DottedDict(item)[col])) for item in arr if col in item ])) except ValueError: # we don't have a "col" field or it's not used. # and we can't use 0 as width cause this will cause a weird # exception col_lengths.append(1) print(f"WARNING: field {col} either never filled or non-existant.", file=sys.stderr) for row in arr: for col_idx, col in enumerate(fields): val = str(row[col]) if col in row else "" print(f"{val:{col_lengths[col_idx]}} ", end="") print("")
def update_constants(constants: dict[str, Any]) -> dict[str, Any]: if "types" in constants: del constants["types"] dotted_constants = DottedCollection.factory(constants) updated_constants = DottedDict() for key, type_ in TYPES.items(): try: # do not write "key in .keys()", it doesn't check for dotted keys. if dotted_constants.get(key, _MARKER) is not _MARKER: value = dotted_constants[key] elif key in TYPES.keys(): value = get_constant(key) else: value = default_value(type_) except KeyError: value = default_value(type_) try: value = coerce(value, type_) except TypeError: msg = "Wrong type for key: {}, value{} " raise TypeError(msg.format(key, value)) check_type(key, value, type_) updated_constants[key] = value return updated_constants.to_python()
def get_constant(path: str, default: object = _MARKER) -> Any: """Return this constant's value from a dotted path. Raises a KeyError if the path is illegal. - path: a dotted key (str) (example: "convention.REMUNERATION") - returns: the value or a default one (of the good type, if specified). """ if path not in TYPES: raise KeyError(path) constants = _get_constants() dotted_constants = DottedCollection.factory(constants) try: value = dotted_constants[path] if isinstance(value, DottedCollection): return dotted_constants[path].to_python() else: return value except KeyError: pass # If a default value is supplied, return it if default != _MARKER: return default # Otherwise, use a default depending on the type type_ = TYPES[path] return default_value(type_)
def test_bad_json(self): with self.assertRaises(ValueError): DottedCollection.factory({"bad.key": "value"}) with self.assertRaises(ValueError): DottedCollection.load_json('{"bad.key": "value"}') with self.assertRaises(ValueError): DottedDict({"bad.key": "value"}) with self.assertRaises(ValueError): DottedList([{}, {"bad.key": "value"}]) with self.assertRaises(ValueError): DottedCollection.load_json('{"key": "value"') with self.assertRaises(ValueError): DottedCollection.load_json('value')
def test_escaped_key(self): """Test keys that contain dots that are not separators""" json_value = '{"facets": {' \ ' "color": ["red", "white"], ' \ ' "d\\\\.o\\\\. origen": [' \ ' "rioja", ' \ ' "ribera del duero", ' \ ' "d.o. bierzo"' \ ' ]' \ '}}' data = DottedCollection.load_json(json_value) self.assertIsInstance(data, DottedDict) self.assertEqual(repr(data["facets"]["d\.o\. origen"]), repr([u"rioja", u"ribera del duero", u"d.o. bierzo"])) self.assertEqual(repr(data["facets.d\.o\. origen"]), repr([u"rioja", u"ribera del duero", u"d.o. bierzo"])) self.assertEqual(data["facets.d\.o\. origen.0"], u"rioja") self.assertEqual(data["facets.d\.o\. origen.2"], u"d.o. bierzo") data["do\.not\.split"] = True self.assertTrue(data["do\.not\.split"]) data["split.this\.not"] = False self.assertEqual(data["split.this\.not"], False) self.assertEqual(data["split"]["this\.not"], False)
def dot(value): """Converts a value into a DottedCollection""" return DottedCollection.factory(value)
def dot_json(json_value): """Creates a DottedCollection from a JSON string""" return DottedCollection.load_json(json_value)
def test_all(self): """Power Tests""" json_value = ( '{"product": [' '{"label": "Categoría", "name":"categories", ' ' "es_definition": {"terms": {"field": "categories_facet", ' ' "size":20}}},' '{"label": "Marca", "name":"brand", ' ' "es_definition": {"terms": {"field": "brand_facet", "size":20}}},' '{"label": "Precio", "name":"price", ' ' "es_definition": {"range": {"ranges": [{"from": 0}], ' ' "field": "price"}}},' '{"label": "Color", "name":"color", ' ' "es_definition": {"terms": {"field": "color_facet", "size": 20}}}' ']}') facets = DottedCollection.load_json(json_value) self.assertIsInstance(facets['product.0.es_definition.terms'], DottedDict) self.assertEqual(facets['product.0.es_definition.terms.size'], 20) self.assertIsInstance(facets['product.2.es_definition.range.ranges'], DottedList) self.assertEqual(facets['product.2.es_definition.range.ranges.0.from'], 0) # Some properties won't be accesible if they are Python reserved words. # This cannot be tested because it raises a SyntaxError # # tmp = facets.product[2].es_definition.range.ranges[0].from self.assertEqual(facets['product.2.es_definition.range.field'], 'price') self.assertEqual(facets.product[2].es_definition.range.field, 'price') facets['product.3.label'] = "Mi Color" facets['product.3.es_definition.terms.size'] = 30 self.assertEqual( facets['product'][3]['es_definition']['terms']['size'], 30) self.assertEqual(facets.product[3].es_definition.terms.size, 30) json_value = ( '{"product": {' ' "url": "http://www.mainada.es/feeds/doofinder/feed.xml",' ' "content_digest": "470550604637aac0d8ce899ade5b7ed5"' '}}') feed = DottedCollection.load_json(json_value) self.assertIsInstance(feed['product'], DottedDict) self.assertIsInstance(feed.product, DottedDict) self.assertEqual(feed.product.url, 'http://www.mainada.es/feeds/doofinder/feed.xml') # Testing JSON correctness normal_object = json.loads(json_value) self.assertReprsEqual(feed.to_json(), json.dumps(normal_object)) # Testing to_python() method python_object = feed.to_python() self.assertReprsEqual(repr(python_object), repr(feed)) self.assertReprsEqual(repr(python_object), repr(normal_object)) self.assertIsInstance(python_object, dict) self.assertIsInstance(python_object['product'], dict)
def test_dottedcollection(self): """ DottedCollection Tests """ with self.assertRaisesRegexp( TypeError, "Can't instantiate abstract class DottedCollection with " "abstract methods __delitem__, __getitem__, __setitem__," " to_python"): obj = DottedCollection() # DottedCollection.factory obj = DottedCollection.factory([1, 2, {'hi': 'world', '3': [4, 5, 6]}]) self.assertReprsEqual(repr(obj), "[1, 2, {'3': [4, 5, 6], 'hi': 'world'}]") self.assertIsInstance(obj, DottedCollection) self.assertIsInstance(obj, DottedList) self.assertIsInstance(obj[2], DottedDict) self.assertIsInstance(obj[2]['3'], DottedList) self.assertIsInstance(obj[2]['3'][0], int) self.assertIsInstance(obj[2]['hi'], str) obj = DottedCollection.factory({'hi': [1, 2, {'3': 4}], 'world': 5}) self.assertReprsEqual(repr(obj), "{'world': 5, 'hi': [1, 2, {'3': 4}]}") self.assertIsInstance(obj, DottedCollection) self.assertIsInstance(obj, DottedDict) self.assertIsInstance(obj['hi'], DottedList) self.assertIsInstance(obj['hi'][2], DottedDict) self.assertIsInstance(obj['hi'][0], int) self.assertIsInstance(obj['world'], int) self.assertEqual(DottedCollection.factory(1), 1) self.assertEqual(DottedCollection.factory(None), None) # DottedCollection.load_json json_value = '[1, 2, {"test": [], "hello": "world"}]' obj = DottedCollection.load_json(json_value) self.assertReprsEqual(repr(obj), "[1, 2, {u'test': [], u'hello': u'world'}]") self.assertIsInstance(obj, DottedList) self.assertIsInstance(obj[0], int) self.assertIsInstance(obj[1], int) self.assertIsInstance(obj[2], DottedDict) self.assertIsInstance(obj[2]['test'], DottedList) self.assertIsInstance(obj[2]['hello'], text_type) # JSON uses unicode json_value = '{"test": [1, 2, {}], "hello": "world"}' obj = DottedCollection.load_json(json_value) self.assertReprsEqual(repr(obj), "{u'test': [1, 2, {}], u'hello': u'world'}") self.assertIsInstance(obj, DottedDict) self.assertIsInstance(obj['test'], DottedList) self.assertIsInstance(obj['test'][0], int) self.assertIsInstance(obj['test'][1], int) self.assertIsInstance(obj['test'][2], DottedDict) self.assertIsInstance(obj['hello'], text_type) json_value = "Hi everybody!" obj = DottedCollection.load_json(json_value) self.assertReprsEqual(repr(obj), "'Hi everybody!'") self.assertIsInstance(obj, string_types) # DottedCollection._factory_by_index obj = DottedCollection._factory_by_index(1) self.assertIsInstance(obj, DottedList) obj = DottedCollection._factory_by_index('1') self.assertIsInstance(obj, DottedList) obj = DottedCollection._factory_by_index('1.1') self.assertIsInstance(obj, DottedList) obj = DottedCollection._factory_by_index('1.something') self.assertIsInstance(obj, DottedList) obj = DottedCollection._factory_by_index('1.something.1') self.assertIsInstance(obj, DottedList) obj = DottedCollection._factory_by_index('something') self.assertIsInstance(obj, DottedDict) obj = DottedCollection._factory_by_index('something.1') self.assertIsInstance(obj, DottedDict) obj = DottedCollection._factory_by_index('something.something') self.assertIsInstance(obj, DottedDict) obj = DottedCollection._factory_by_index(None) self.assertIsInstance(obj, DottedDict) # DottedCollection.to_json obj = DottedCollection.factory([]) self.assertReprsEqual(obj.to_json(), '[]') obj = DottedCollection.factory( [1, 2, { 'a': 'b', 'c': [3, 4, { '5': 6 }] }]) self.assertReprsEqual(obj.to_json(), '[1, 2, {"a": "b", "c": [3, 4, {"5": 6}]}]') obj = DottedCollection.factory({}) self.assertReprsEqual(obj.to_json(), '{}') obj = DottedCollection.factory({ 'a': 'b', 'c': [1, 2, { 'd': [3, 4, [5]] }] }) self.assertReprsEqual(obj.to_json(), '{"a": "b", "c": [1, 2, {"d": [3, 4, [5]]}]}') self.assertEqual(obj['c'].to_json(), '[1, 2, {"d": [3, 4, [5]]}]') self.assertEqual(obj['c'][2].to_json(), '{"d": [3, 4, [5]]}') self.assertEqual(obj['c'][2]['d'].to_json(), '[3, 4, [5]]') self.assertEqual(obj['c'][2]['d'][2].to_json(), '[5]') with self.assertRaisesRegexp( AttributeError, "'int' object has no attribute 'to_json'"): obj['c'][2]['d'][2][0].to_json()
def test_all(self): """Power Tests""" json_value = ( '{"product": [' '{"label": "Categoría", "name":"categories", ' ' "es_definition": {"terms": {"field": "categories_facet", ' ' "size":20}}},' '{"label": "Marca", "name":"brand", ' ' "es_definition": {"terms": {"field": "brand_facet", "size":20}}},' '{"label": "Precio", "name":"price", ' ' "es_definition": {"range": {"ranges": [{"from": 0}], ' ' "field": "price"}}},' '{"label": "Color", "name":"color", ' ' "es_definition": {"terms": {"field": "color_facet", "size": 20}}}' ']}' ) facets = DottedCollection.load_json(json_value) self.assertIsInstance(facets['product.0.es_definition.terms'], DottedDict) self.assertEqual(facets['product.0.es_definition.terms.size'], 20) self.assertIsInstance(facets['product.2.es_definition.range.ranges'], DottedList) self.assertEqual(facets['product.2.es_definition.range.ranges.0.from'], 0) # Some properties won't be accesible if they are Python reserved words. # This cannot be tested because it raises a SyntaxError # # tmp = facets.product[2].es_definition.range.ranges[0].from self.assertEqual(facets['product.2.es_definition.range.field'], 'price') self.assertEqual(facets.product[2].es_definition.range.field, 'price') facets['product.3.label'] = "Mi Color" facets['product.3.es_definition.terms.size'] = 30 self.assertEqual(facets['product'][3]['es_definition']['terms']['size'], 30) self.assertEqual(facets.product[3].es_definition.terms.size, 30) json_value = ( '{"product": {' ' "url": "http://www.mainada.es/feeds/doofinder/feed.xml",' ' "content_digest": "470550604637aac0d8ce899ade5b7ed5"' '}}' ) feed = DottedCollection.load_json(json_value) self.assertIsInstance(feed['product'], DottedDict) self.assertIsInstance(feed.product, DottedDict) self.assertEqual( feed.product.url, 'http://www.mainada.es/feeds/doofinder/feed.xml' ) # Testing JSON correctness normal_object = json.loads(json_value) self.assertReprsEqual(feed.to_json(), json.dumps(normal_object)) # Testing to_python() method python_object = feed.to_python() self.assertReprsEqual(repr(python_object), repr(feed)) self.assertReprsEqual(repr(python_object), repr(normal_object)) self.assertIsInstance(python_object, dict) self.assertIsInstance(python_object['product'], dict)
def test_dottedcollection(self): """ DottedCollection Tests """ with self.assertRaisesRegexp( TypeError, "Can't instantiate abstract class DottedCollection with " "abstract methods __delitem__, __getitem__, __setitem__," " to_python"): obj = DottedCollection() # DottedCollection.factory obj = DottedCollection.factory([1, 2, {'hi': 'world', '3': [4, 5, 6]}]) self.assertReprsEqual(repr(obj), "[1, 2, {'3': [4, 5, 6], 'hi': 'world'}]") self.assertIsInstance(obj, DottedCollection) self.assertIsInstance(obj, DottedList) self.assertIsInstance(obj[2], DottedDict) self.assertIsInstance(obj[2]['3'], DottedList) self.assertIsInstance(obj[2]['3'][0], int) self.assertIsInstance(obj[2]['hi'], str) obj = DottedCollection.factory({'hi': [1, 2, {'3': 4}], 'world': 5}) self.assertReprsEqual(repr(obj), "{'world': 5, 'hi': [1, 2, {'3': 4}]}") self.assertIsInstance(obj, DottedCollection) self.assertIsInstance(obj, DottedDict) self.assertIsInstance(obj['hi'], DottedList) self.assertIsInstance(obj['hi'][2], DottedDict) self.assertIsInstance(obj['hi'][0], int) self.assertIsInstance(obj['world'], int) self.assertEqual(DottedCollection.factory(1), 1) self.assertEqual(DottedCollection.factory(None), None) # DottedCollection.load_json json_value = '[1, 2, {"test": [], "hello": "world"}]' obj = DottedCollection.load_json(json_value) self.assertReprsEqual(repr(obj), "[1, 2, {u'test': [], u'hello': u'world'}]") self.assertIsInstance(obj, DottedList) self.assertIsInstance(obj[0], int) self.assertIsInstance(obj[1], int) self.assertIsInstance(obj[2], DottedDict) self.assertIsInstance(obj[2]['test'], DottedList) self.assertIsInstance(obj[2]['hello'], text_type) # JSON uses unicode json_value = '{"test": [1, 2, {}], "hello": "world"}' obj = DottedCollection.load_json(json_value) self.assertReprsEqual(repr(obj), "{u'test': [1, 2, {}], u'hello': u'world'}") self.assertIsInstance(obj, DottedDict) self.assertIsInstance(obj['test'], DottedList) self.assertIsInstance(obj['test'][0], int) self.assertIsInstance(obj['test'][1], int) self.assertIsInstance(obj['test'][2], DottedDict) self.assertIsInstance(obj['hello'], text_type) # DottedCollection._factory_by_index obj = DottedCollection._factory_by_index(1) self.assertIsInstance(obj, DottedList) obj = DottedCollection._factory_by_index('1') self.assertIsInstance(obj, DottedList) obj = DottedCollection._factory_by_index('1.1') self.assertIsInstance(obj, DottedList) obj = DottedCollection._factory_by_index('1.something') self.assertIsInstance(obj, DottedList) obj = DottedCollection._factory_by_index('1.something.1') self.assertIsInstance(obj, DottedList) obj = DottedCollection._factory_by_index('something') self.assertIsInstance(obj, DottedDict) obj = DottedCollection._factory_by_index('something.1') self.assertIsInstance(obj, DottedDict) obj = DottedCollection._factory_by_index('something.something') self.assertIsInstance(obj, DottedDict) obj = DottedCollection._factory_by_index(None) self.assertIsInstance(obj, DottedDict) # DottedCollection.to_json obj = DottedCollection.factory([]) self.assertReprsEqual(obj.to_json(), '[]') obj = DottedCollection.factory( [1, 2, {'a': 'b', 'c': [3, 4, {'5': 6}]}] ) self.assertReprsEqual(obj.to_json(), '[1, 2, {"a": "b", "c": [3, 4, {"5": 6}]}]') obj = DottedCollection.factory({}) self.assertReprsEqual(obj.to_json(), '{}') obj = DottedCollection.factory( {'a': 'b', 'c': [1, 2, {'d': [3, 4, [5]]}]} ) self.assertReprsEqual(obj.to_json(), '{"a": "b", "c": [1, 2, {"d": [3, 4, [5]]}]}') self.assertEqual(obj['c'].to_json(), '[1, 2, {"d": [3, 4, [5]]}]') self.assertEqual(obj['c'][2].to_json(), '{"d": [3, 4, [5]]}') self.assertEqual(obj['c'][2]['d'].to_json(), '[3, 4, [5]]') self.assertEqual(obj['c'][2]['d'][2].to_json(), '[5]') with self.assertRaisesRegexp( AttributeError, "'int' object has no attribute 'to_json'"): obj['c'][2]['d'][2][0].to_json()
dotted_arr[len(dotted_arr)] = 12 print(dotted_arr) dotted_dict = DottedDict({'hello': {'world': {'python': '3'}}}) print(dotted_dict['hello']) print(dotted_dict['hello.world']) print(dotted_dict['hello.world.python']) print(dotted_dict.hello) print(dotted_dict.hello.world) print(dotted_dict.hello.world.python) dotted_dict2 = DottedCollection.factory( {'hello': [{ 'world': { 'python': ['3', '7', '3'] } }]}) print(dotted_dict2['hello'][0]['world']['python'][0]) print(dotted_dict2.hello[0].world.python[0]) print(dotted_dict2.hello[0].world['python'][0]) print(dotted_dict2.hello[0].world['python.0']) print(dotted_dict2.hello['0.world'].python[0]) print(dotted_dict2['hello.0.world.python.0']) dotted_dict2['c++.path'] = {'hello': 'world'} dotted_dict2['java.path'] = ['hello'] print(dotted_dict2) dot_obj = dot({'hello': 'world'}) print(dot_obj)