Use external sources
Data validation can sometimes rely on external sources, a database, an HTTP API, even a file. Akkurate comes with a mechanic of contextual validation to allow using those external sources during validation.
Remember the code example about Twitter for conditional constraints? We were using the following global variable to query our database:
However, instead of using a global variable, you're probably storing your DAO instance inside a container and injecting it wherever you need.
Akkurate allows you to pass a context to your validator in addition to the validated object. This is done by using
Validator<ContextType, ValueType> to instantiate the validator.
Let's reuse our Twitter example and adapt it with this new feature:
The context type is passed first, then the value type; while the context value is available as the first parameter of the lambda.
Now, when calling our validator, we have to provide an instance of
UserDao before the value to validate:
Keep the same context across multiple validations
You don't need to provide the context for each validation. Especially when you want to provide the context higher in the code hierarchy and let some more specific code provide the object to validate.
You can solve this by currying your validator:
Use multiple contextual objects
When you need to pass multiple objects as a context, create a data class to wrap them:
Use destructuring to write more concise code:
If your external source is asynchronous, like an HTTP API, you have to make your validator suspendable by calling
Let's reuse the contextual validation example based on Twitter and replace the
UserDao interface by
To be able to call the suspendable method
existsByUsername, we have to make our validator suspendable:
Note that suspendable validators can only be called from suspendable functions: