Validating a Django model field based on another field's value?
I dug around codebase of drf a little bit. You can get values of all fields using following approach, though it is not mentioned in docs. Doing so, you can throw serialization error as
{'my_field':'error message}
instead of {'non_field_error':'error message'}
.
def validate_myfield(self, value):
data = self.get_initial() # data for all the fields
#do your validation
The validation per-field doesn't get sent any information about other fields, when it is defined like this:
def validate_myfield(self, value):
...
However, if you have a method defined like this:
def validate(self, data):
...
Then you get all the data in a dict, and you can do cross-field validation.
You can use the required package for your cross-field validation. It allows you to express your validation rules declaratively in python. You would have something like this with DRF:
class MySerializer(serializers.Serializer):
REQUIREMENTS = (
Requires("end_date", "start_date") +
Requires("end_date", R("end_date") > R("start_date")) +
Requires("end_date", R("end_date") < today.date() + one_year) +
Requires("start_date", R("start_date") < today.date() + one_year)
)
start_date = serializers.DateField(required=False, null=True, blank=True)
end_date = serializers.DateField(required=False, null=True, blank=True)
def validate(self, data):
self.REQUIREMENTS.validate(data) # handle validation error
You could put the REQUIREMENTS
on your Model and have both your DRF and Django Form validate your data using it.
Here is a blog post explaining more