Hi! I need a feature to have the module delete referenced entities when field items are removed. I can supply a patch against latest 7.x-1.x-dev. See what you think, would be great if it could be committed in one way or another, but perhaps it needs some more work. Seems to do the job for me, but with some limitations (like not checking for other possible references to the referenced entity before deleting).

Comments

gnucifer’s picture

gnucifer’s picture

Oh, failed with the patch. Here is a working one.

gnucifer’s picture

Missed adding default value for setting and fixed a bug that caused all references to be deleted on insert, new patch:

JvE’s picture

I would like to know the purpose of this functionality. Can you provide a use case scenario?

I can imagine having directory and file entities where the directory references its files.
Then you want the file entity to be deleted when the reference to it is removed from the directory entity?

Should your patch then also trigger this deletion when the entity holding the references is being deleted? To use the dir/file example: should it delete the file entities being referenced by the directory entity when deleting the directory entity?

Shouldn't you also check if the user that removes the reference has permission to delete the referenced entity?
And what if the reference is to a user, or even the current user?

If I had need of this functionality then I would design the file entities to hold a reference to the directory in stead.
Or use hook_cron to delete file entities that have no references to them.

damien tournoud’s picture

That sounds good, but please implement this as a behavior.

gnucifer’s picture

Ok, new patch as behavior (against the 7.x-1.x-extended-behaviors branch). JvE: Yes there are some pretty serious security implications for this functionality, and it should perhaps be fixed/looked at, but perhaps its up to the user. Myself I need only the current functionality for an admittedly quite obscure user-case (importing and creating references with feeds that need to be cleaned up after the referencing entity is deleted). Could be managed through a cron-job as well, but with all this database-agnosticism floating around it seems a bit hard to do. Sure, one could managed some kind of reference counting on the field-hooks, but this was the simplest solution for me.

damien tournoud’s picture

Status: Active » Needs work

Looking at the patch, I don't understand why you are trying to do.

Usually, "cascade on delete" means:

If an entity is deleted, delete all the entities that reference it.

This is required to ensure referential integrity (ie. you never reference an entity that does not exist).

You seem to have implemented it the other way around:

If an entity is deleted, delete all the entities it references.

You are going to need to implement a hook_entity_delete() that does:

  • look at all the entityreference fields that reference the entity type of the entity being deleted and have the cascade behavior enabled
  • for each of those fields, do a EFQ to find the entities that references the entity being deleted and delete them
JvE’s picture

Damien, the patch does not

If an entity is deleted, delete all the entities it references.

but

if a value is removed from an entityreference field, delete the entity that that value was referencing.

which is why I raised some questions about this functionality.

gnucifer’s picture

Usually, "cascade on delete" means:

If an entity is deleted, delete all the entities that reference it.

Yes, you are correct in that its basically a reverse "on delete cascade", so calling it delete on cascade is probably the worst description imaginable. :) "Delete referenced entities" or something is what it should have been named. In my user case there will always be a many-to-one relation between referenced entities and the entity containing the field, so that's why I got confused about the terminology. In this case the field really should be placed on the entity now being referenced to through a multiple-values entityreference-field and limited to one value to ensure this relation, but because of real-world limitations it had to be the other way around.

I will try to fix the patch and perhaps add the "real" on cascade delete as well.

gmclelland’s picture

This looks really interesting. Would this be similar to how plone handles references when deleting the parent node?
See this image:
http://dev.plone.org/raw-attachment/ticket/11992/linktegrity-non-ascii-t...

JvE’s picture

Title: Cascade on delete » Delete entity when a referencing field value is removed.

@gmclelland: No, what this patch does is:

if a value is removed from an entityreference field, delete the entity that that value was referencing.

An example:
You have a node of type "account" which has an entityreference field "projects" set to contain multiple values.
For a certain account node, the "projects" field contains references to project nodes A, B and C.
If you edit this account node and empty the reference to B so that the field only holds A and C then this patch will delete project node B.

@gnucifer: I'm changing the title to more accurately reflect the nature of this ticket. Hope you don't mind.

gnucifer’s picture

Np, I actually made a "real" on delete cascade the day after my last post in this thread, containing both variants, but there where some minor things left and I have not had time to fix them since. If you have some patience I will submit the module in this thread as soon as I can.

jordanmagnuson’s picture

Just wanted to add my voice in saying that I think this is a really vital feature for this module.

sprocketman’s picture

I have just released a new module that attempts to accommodate cascade deletion for entity references. If interested, please check out Entity Reference Cascade Delete.

JvE’s picture

Title: Delete entity when a referencing field value is removed. » Delete entity when another entity stops referencing it.

I think a maintainer can mark this issue "closed (won't fix)" since it is extremely unlikely that this functionality will ever go into Entityreference.

I also think a lot of people are confused about this ticket and think it is about taking action when an entity (either referencing or referenced) is deleted. It is not.

gettysburger’s picture

Nodeone has a great video showing how this can be done with Rules.

http://nodeone.se/sv/node/761

Check out "Using the delete entity action"

dave reid’s picture

I also added http://drupal.org/project/field_referenced_delete.

I would also agree this out of place for entityreference functionality.

JvE’s picture

Status: Needs work » Closed (won't fix)
JvE’s picture

Issue summary: View changes

Some spelling and grammar.