@@ -488,17 +488,21 @@ def _create_collection(self, model):
488488 # Unencrypted path
489489 db .create_collection (db_table )
490490
491- def _get_encrypted_fields (self , model , create_data_keys = False , key_alt_name = None ):
491+ def _get_encrypted_fields (
492+ self , model , create_data_keys = False , key_alt_name = None , parent_model = None
493+ ):
492494 """
493495 Recursively collect encryption schema data for only encrypted fields in a model.
494496 Returns None if no encrypted fields are found anywhere in the model hierarchy.
495497
496- key_alt_name is the base path for this level, typically model._meta.db_table.
498+ key_alt_name is the base path used for keyAltNames.
499+ parent_model is the dot-notated path inside the document for schema mapping.
497500 """
498501 connection = self .connection
499502 client = connection .connection
500503 fields = model ._meta .fields
501504 key_alt_name = key_alt_name or model ._meta .db_table
505+ parent_model = parent_model or ""
502506
503507 options = client ._options
504508 auto_encryption_opts = getattr (options , "auto_encryption_opts" , None )
@@ -515,49 +519,51 @@ def _get_encrypted_fields(self, model, create_data_keys=False, key_alt_name=None
515519 field_list = []
516520
517521 for field in fields :
518- new_path = f"{ key_alt_name } .{ field .column } "
522+ new_key_alt_name = f"{ key_alt_name } .{ field .column } "
523+ new_parent_model = f"{ parent_model } .{ field .column } " if parent_model else field .column
519524
520525 # --- EmbeddedModelField ---
521526 if isinstance (field , EmbeddedModelField ):
522527 if getattr (field , "encrypted" , False ):
523- # Entire sub-object is encrypted
528+ # Entire sub-object encrypted
524529 if create_data_keys :
525530 if not client_encryption :
526531 raise ImproperlyConfigured ("client_encryption is not configured." )
527532 data_key = client_encryption .create_data_key (
528533 kms_provider = kms_provider ,
529534 master_key = master_key ,
530- key_alt_names = [new_path ],
535+ key_alt_names = [new_key_alt_name ],
531536 )
532537 else :
533538 if key_vault_collection is None :
534539 raise ImproperlyConfigured (
535- f"Encrypted field { new_path } detected but no key vault configured"
540+ f"Encrypted field { new_key_alt_name } detected "
541+ "but no key vault configured"
536542 )
537- key_doc = key_vault_collection .find_one ({"keyAltNames" : new_path })
543+ key_doc = key_vault_collection .find_one ({"keyAltNames" : new_key_alt_name })
538544 if not key_doc :
539545 raise ValueError (
540- f"No key found in keyvault for keyAltName={ new_path } . "
546+ f"No key found in keyvault for keyAltName={ new_key_alt_name } . "
541547 "Run with '--create-data-keys' to create missing keys."
542548 )
543549 data_key = key_doc ["_id" ]
544550
545551 field_dict = {
546552 "bsonType" : "object" ,
547- "path" : field . column ,
553+ "path" : new_parent_model ,
548554 "keyId" : data_key ,
549555 }
550556 if getattr (field , "queries" , False ):
551557 field_dict ["queries" ] = field .queries
552558
553559 field_list .append (field_dict )
554560 else :
555- # Not encrypting whole object — recurse first then
556- # conditionally extend field list
561+ # Recurse into embedded model
557562 embedded_result = self ._get_encrypted_fields (
558563 field .embedded_model ,
559564 create_data_keys = create_data_keys ,
560- key_alt_name = new_path ,
565+ key_alt_name = new_key_alt_name ,
566+ parent_model = new_parent_model ,
561567 )
562568 if embedded_result and embedded_result .get ("fields" ):
563569 field_list .extend (embedded_result ["fields" ])
@@ -571,24 +577,25 @@ def _get_encrypted_fields(self, model, create_data_keys=False, key_alt_name=None
571577 data_key = client_encryption .create_data_key (
572578 kms_provider = kms_provider ,
573579 master_key = master_key ,
574- key_alt_names = [new_path ],
580+ key_alt_names = [new_key_alt_name ],
575581 )
576582 else :
577583 if key_vault_collection is None :
578584 raise ImproperlyConfigured (
579- f"Encrypted field { new_path } detected but no key vault configured"
585+ f"Encrypted field { new_key_alt_name } detected "
586+ "but no key vault configured"
580587 )
581- key_doc = key_vault_collection .find_one ({"keyAltNames" : new_path })
588+ key_doc = key_vault_collection .find_one ({"keyAltNames" : new_key_alt_name })
582589 if not key_doc :
583590 raise ValueError (
584- f"No key found in keyvault for keyAltName={ new_path } . "
591+ f"No key found in keyvault for keyAltName={ new_key_alt_name } . "
585592 "Run with '--create-data-keys' to create missing keys."
586593 )
587594 data_key = key_doc ["_id" ]
588595
589596 field_dict = {
590597 "bsonType" : field .db_type (connection ),
591- "path" : field . column ,
598+ "path" : new_parent_model ,
592599 "keyId" : data_key ,
593600 }
594601 if getattr (field , "queries" , False ):
0 commit comments