Handling Conflict with Reference Constraint When Deleting a Record

I am trying to find the best way to provide a message to the user that a record cannot be deleted because it is being referenced in another Entity.

Entities Example:

Entity A 

Id

Name

Entity B

Id

Name

EntityAId


Currently, an exception will be thrown if delete is attempted to a record on Entity A that is being referenced on Entity B. Using the Protect rule, which is the rule that I need. However, that exception is not user-friendly and most users will not understand what the issue is. 

I am thinking of performing a query to the database to see if the record is being referenced on any other tables and then raising a custom exception on a "Delete" Serve Action inside the producer module that will contain a message like "Record X cannot be deleted because it is being referenced from record Y on Entity B".

Are there any issues with that approach? or is there a better way to handle this situation?

I am looking forward to hearing what everyone else thinks.

Solution

Hi Spiros,

speaking as a user, I prefer to see in advance that it is futile to try and delete something.


You could retrieve information about any related B entities in the Aggregate that retrieves the A entity.  If for example you have a screen with a table records showing A records, and a delete button in each row, you could either disable the delete button or style it differently, so that a habitual user of your app immediately understands that he can't delete it.  If possible add info about the reason why it can't be deleted so the less frequent users of your application also get it.


So I had a quick try, let's say your A is my Person entity and your B is my Request entity, what I did :

I have a list of people, in the aggregate, instead of just retrieving Person, I joined with Request, grouped by all Person attributes, and added the count of request id.  (make sure the join is a "with or without", you want all persons showing up, even if they don't have requests)

I have a column in the table records for the delete button with an IF widget in that column, with condition 


PersonTable.List.Current.Count = 0



In the True branch goes the Delete button, in the False Branche goes whatever you want to show for a person that can't be deleted.  For this i just went for an empty button, with a balloon on the hover, explaining why that person can't be deleted, and a link that will take the user to the requests that are preventing the delete.


Result looks like this :

And when hovering over the button in Paul's row the balloon shows the reason + a link to go and deal with those 3 requests :


Personally, I think those empty buttons look odd, but this was just a quick test, the point is to give a visual cue to the user that he shouldn't even attempt to try a delete on that person.  A balans has to be struck between giving enough information versus not overcrowding your screen with stuff that is irrelevant to anybody using the screen for other reasons that to delete people.


Hope this gives you some ideas to play around with,

Dorine

Solution

Thanks Dorine! 

That is a good idea, I was thinking of something like that, but I thought I had to do an extra call to the database as part of the validation before submitting the request. I didn't know you can pull the count on the same call/aggregate.  Pretty cool.