Simplified lookup-field method, allowing dynamic lookup for more than two parts
This commit is contained in:
		| @@ -935,6 +935,7 @@ class BaseDocument(object): | |||||||
|         """ |         """ | ||||||
|  |  | ||||||
|         ListField = _import_class("ListField") |         ListField = _import_class("ListField") | ||||||
|  |         DynamicField = _import_class('DynamicField') | ||||||
|  |  | ||||||
|         if not isinstance(parts, (list, tuple)): |         if not isinstance(parts, (list, tuple)): | ||||||
|             parts = [parts] |             parts = [parts] | ||||||
| @@ -944,7 +945,6 @@ class BaseDocument(object): | |||||||
|         for field_name in parts: |         for field_name in parts: | ||||||
|             # Handle ListField indexing: |             # Handle ListField indexing: | ||||||
|             if field_name.isdigit() and isinstance(field, ListField): |             if field_name.isdigit() and isinstance(field, ListField): | ||||||
|                 new_field = field.field |  | ||||||
|                 fields.append(field_name) |                 fields.append(field_name) | ||||||
|                 continue |                 continue | ||||||
|  |  | ||||||
| @@ -956,11 +956,9 @@ class BaseDocument(object): | |||||||
|                 if field_name in cls._fields: |                 if field_name in cls._fields: | ||||||
|                     field = cls._fields[field_name] |                     field = cls._fields[field_name] | ||||||
|                 elif cls._dynamic: |                 elif cls._dynamic: | ||||||
|                     DynamicField = _import_class('DynamicField') |  | ||||||
|                     field = DynamicField(db_field=field_name) |                     field = DynamicField(db_field=field_name) | ||||||
|                 elif cls._meta.get("allow_inheritance", False) or cls._meta.get("abstract", False): |                 elif cls._meta.get("allow_inheritance", False) or cls._meta.get("abstract", False): | ||||||
|                     # 744: in case the field is defined in a subclass |                     # 744: in case the field is defined in a subclass | ||||||
|                     field = None |  | ||||||
|                     for subcls in cls.__subclasses__(): |                     for subcls in cls.__subclasses__(): | ||||||
|                         try: |                         try: | ||||||
|                             field = subcls._lookup_field([field_name])[0] |                             field = subcls._lookup_field([field_name])[0] | ||||||
| @@ -982,6 +980,9 @@ class BaseDocument(object): | |||||||
|                                       '__'.join(parts)) |                                       '__'.join(parts)) | ||||||
|                 if hasattr(getattr(field, 'field', None), 'lookup_member'): |                 if hasattr(getattr(field, 'field', None), 'lookup_member'): | ||||||
|                     new_field = field.field.lookup_member(field_name) |                     new_field = field.field.lookup_member(field_name) | ||||||
|  |                 elif cls._dynamic and (isinstance(field, DynamicField) or | ||||||
|  |                                            getattr(getattr(field, 'document_type'), '_dynamic')): | ||||||
|  |                     new_field = DynamicField(db_field=field_name) | ||||||
|                 else: |                 else: | ||||||
|                     # Look up subfield on the previous field or raise |                     # Look up subfield on the previous field or raise | ||||||
|                     try: |                     try: | ||||||
| @@ -991,17 +992,8 @@ class BaseDocument(object): | |||||||
|                                           'on the field {}'.format( |                                           'on the field {}'.format( | ||||||
|                                               field_name, field.name)) |                                               field_name, field.name)) | ||||||
|                 if not new_field and isinstance(field, ComplexBaseField): |                 if not new_field and isinstance(field, ComplexBaseField): | ||||||
|                     if hasattr(field.field, 'document_type') and cls._dynamic \ |  | ||||||
|                             and field.field.document_type._dynamic: |  | ||||||
|                         DynamicField = _import_class('DynamicField') |  | ||||||
|                         new_field = DynamicField(db_field=field_name) |  | ||||||
|                     else: |  | ||||||
|                     fields.append(field_name) |                     fields.append(field_name) | ||||||
|                     continue |                     continue | ||||||
|                 elif not new_field and hasattr(field, 'document_type') and cls._dynamic \ |  | ||||||
|                         and field.document_type._dynamic: |  | ||||||
|                     DynamicField = _import_class('DynamicField') |  | ||||||
|                     new_field = DynamicField(db_field=field_name) |  | ||||||
|                 elif not new_field: |                 elif not new_field: | ||||||
|                     raise LookUpError('Cannot resolve field "%s"' |                     raise LookUpError('Cannot resolve field "%s"' | ||||||
|                                       % field_name) |                                       % field_name) | ||||||
|   | |||||||
| @@ -129,6 +129,15 @@ class DynamicTest(unittest.TestCase): | |||||||
|  |  | ||||||
|         self.assertEqual(1, self.Person.objects(misc__hello='world').count()) |         self.assertEqual(1, self.Person.objects(misc__hello='world').count()) | ||||||
|  |  | ||||||
|  |     def test_three_level_complex_data_lookups(self): | ||||||
|  |         """Ensure you can query three level document dynamic fields""" | ||||||
|  |         p = self.Person() | ||||||
|  |         p.misc = {'hello': {'hello2': 'world'}} | ||||||
|  |         p.save() | ||||||
|  |         # from pprint import pprint as pp; import pdb; pdb.set_trace(); | ||||||
|  |         print self.Person.objects(misc__hello__hello2='world') | ||||||
|  |         self.assertEqual(1, self.Person.objects(misc__hello__hello2='world').count()) | ||||||
|  |  | ||||||
|     def test_complex_embedded_document_validation(self): |     def test_complex_embedded_document_validation(self): | ||||||
|         """Ensure embedded dynamic documents may be validated""" |         """Ensure embedded dynamic documents may be validated""" | ||||||
|         class Embedded(DynamicEmbeddedDocument): |         class Embedded(DynamicEmbeddedDocument): | ||||||
|   | |||||||
		Reference in New Issue
	
	Block a user