Improve Reverse Delete Rules#2765
Conversation
|
mm i guess its not working : ) will come back to this later. |
| f.document_type.register_delete_rule( | ||
| new_class, field.name, delete_rule |
There was a problem hiding this comment.
In the ideal world I would cut out document_type here and just make fields responsible for implementing register_delete_rule.
However, when I tried this I realized that it would break the interface for how to register delete rules and thus any users dynamically setting delete rules would be upset.
| Use the `reverse_delete_rule` to handle what should happen if the document | ||
| the field is referencing is deleted. EmbeddedDocuments, DictFields and | ||
| MapFields does not support reverse_delete_rule and an `InvalidDocumentError` | ||
| will be raised if trying to set on one of these Document / Field types. | ||
|
|
||
| The options are: | ||
|
|
||
| * DO_NOTHING (0) - don't do anything (default). | ||
| * NULLIFY (1) - Updates the reference to null. | ||
| * CASCADE (2) - Deletes the documents associated with the reference. | ||
| * DENY (3) - Prevent the deletion of the reference object. | ||
| * PULL (4) - Pull the reference from a :class:`~mongoengine.fields.ListField` of references | ||
|
|
||
| Alternative syntax for registering delete rules | ||
|
|
||
| .. code-block:: python | ||
|
|
||
| class Org(Document): | ||
| owner = ReferenceField('User') | ||
|
|
||
| class User(Document): | ||
| org = ReferenceField('Org', reverse_delete_rule=CASCADE) | ||
|
|
||
| User.register_delete_rule(Org, 'owner', DENY) | ||
|
|
There was a problem hiding this comment.
This wasn't showing up in sphinx when I ran make html-readthedocs, not sure why?
| """ | ||
|
|
||
| def __init__(self, *args, **kwargs): | ||
| def __init__(self, *args, reverse_delete_rule=DO_NOTHING, **kwargs): |
There was a problem hiding this comment.
Would like to call this param out in the GenericReferenceField docs but I couldn't seem to get it to show up properly, I'd make a docstring for the init but it wouldn't populate to the docs 🤷
|
@bagerard I know you're busy, anything more I need to do to get this merged in? Fixed a couple issues - just need a bit of help with the sphinx formatting. |
Fixes issues #2764 and #2308, implements lazy delete rules and delete rules on GenericReferenceFields.
To implement lazy delete rules:
When delete rules are assigned to a Document that doesn't exist yet, I store them in a global dict. Whenever a new Document class is defined, it checks said global dict for any outstanding delete rules that it needs to assign on itself.
To implement delete rules on GenericReferenceFields:
GenericReferenceField is now smart enough to register delete rules on many documents when its asked to. It does this by employing a helper class which provides a
register_delete_rulefunction that actually can register delete rules on many documents, not just one. It exposes this class by defining adocument_typeproperty, which is kind of lying in a sense since this really is only intended to exposeregister_delete_ruleand not handle any other functionality expected ofdocument_type.This is a little janky but I can't think of a way to do it "right" without changing which class is responsible for
register_delete_ruleand thus making a breaking change.