Combining OnValidate and OnBeforePost?
As example, I have a form with a DBNavigator and a few DBEdits.
I want to achive the following:
- When the user enters something wrong in the DBEdit and wants to switch to another control, a warning should be displayed, but he can continue working.
- When the user wants to post the dataset, the post will be rejected, and the warning will be displayed again.
The problem is, that OnValidate is just a TFieldNotifyEvent and therefore cannot tell the application if the edit was valid, so there is no way to check if everything was valid before you post.
I have tried following:
Idea 1: Let OnBeforePost validate and throw an Exception
- Pro:
- Invalid data will not be posted
- The user can continue working and revert the changes using the DBNavigator if he cannot complete the form.
- Contra:
- No warning is displayed when the user leaves the DBEdit
- (Low priority) All validations have to be in one single point. Better Object Orientated would be if the validate is done directly in the TField.
Idea 2: Throw an Exception in OnValidate
- Pro:
- It is impossible to post invalid data.
- Contra:
- The user might stay in an endless loop if he is unable to enter something valid (e.g. because he doesn't know what to enter), and he cannot even press the "Revert" button on the DBNavigator! In this case, he has to kill the Application using the task manager, which is a worst-case-scenario in regards to user-friendliness.
Idea 3: Show a (non-Exception) warning in OnValidate, and validate again in OnBeforePost (and throw an Exception)
- Pro:
- Warning is possible, and invalid data cannot be posted.
- Contra:
- The check has to implemented twice (even if outsourced into a function), and there is the risk that the developer might forget 1 of these 2 checks. Also, for big projects with many fields to validate, it gets quickly confusing.
- When the user clicks the Post-Button while being in the DBEdit, he gets the message twice (one warning for leaving the DBEdit, and one Exception because the post fails)
- In case the data is already wrong in the database, when the dataset was loaded (e.g. because of an older program version which didn't check the value), the post will be allowed (if the user didn't edit the value in this session)
Is there a better way?
Answers (2)
It seems to me, that you are mixing business logic (data validation) with UI (OnValidate). Split them. Place all business logic in to separate functions or object. Probably it is even worth to implement MVC pattern. But in this case you will have to replace DB-controls with ORM framework + LiveBindings.