If data changes in the database, and I load it again, and it violates some rules set at that point, it also did that when it was in the database. So modifying rules means also modifying data in the database, or am I mistaken?
Also what to do when the rules are violated when the entity is loaded? To me, the entity's data is then not usable and should be modified or deleted, as the entity can't be used by the system.
Not really. What we are doing is implementing a rules manager (or more accurately a BrokenRules collection) for every entity. A property in the entity (IsValid) flags the presence of any broken rules in the entity's broken rules collection. It goes something like this:
1- a call to entity's (Validate) method would populate the BrokenRules collection instead of throwing an exception
2- a call to an entity's (Validate) should also recursively call the (Validate) method of any contained child Entity (1:1) or any contained child collections (1:n)
3- The entity would behave and live normally. The only stipulation is that if an attempt to save (or in some cases Delete) the entity while its (IsValid) is false, then we would throw an exception
This provides great flexibility for the UI developer. In the UI, when an entity is retrieved from the DB, the BL validates it (call its Validate) and its BrokenRules collection gets populated (because it is NOT valid under the recently modified business rules).
A UI list-control binded to the entity's BrokenRules collection would show any broken rules for this entity (much better than displaying a long messagebox that must be dismissed before the user can edit the entity to adhere to the new rules)
If the UI still attempts a save for this entity, the exception thrown by the BL layer would buble up and show in the UI.
We have even extended this framework to include TypeOfBrokenRule (DenySave, DenyDelete, Warning, Information) and overloaded both (Validate) and (IsValid) properties so that the CRUD operations could validate and check:
- Save: Validate(TypeOfBrokenRule.DenySave) then check
IsValid(TypeOfBrokenRule.DenySave) before saving
- Delete: Validate(TypeOfBrokenRule.DenyDelete) then check
IsValid(TypeOfBrokenRule.DenyDelete) before deleting
This gave us the flexibility of adapting to changing BusinessRules and knowing that all future edits would adhere to these changes...
OMAR