File tree Expand file tree Collapse file tree 3 files changed +53
-1
lines changed Expand file tree Collapse file tree 3 files changed +53
-1
lines changed Original file line number Diff line number Diff line change @@ -71,7 +71,8 @@ django-timezone-field
7171
7272# A REST API framework for Django projects
7373# https://www.django-rest-framework.org/community/release-notes/
74- djangorestframework
74+ # TODO: Re-evaluate the monkey-patch of get_unique_validators() before upgrading
75+ djangorestframework==3.16.1
7576
7677# Sane and flexible OpenAPI 3 schema generation for Django REST framework.
7778# https://github.com/tfranzel/drf-spectacular/blob/master/CHANGELOG.rst
Original file line number Diff line number Diff line change 1+ from django .db .models import UniqueConstraint
2+ from rest_framework .utils .field_mapping import get_unique_error_message
3+ from rest_framework .validators import UniqueValidator
4+
5+ __all__ = (
6+ 'get_unique_validators' ,
7+ )
8+
9+
10+ def get_unique_validators (field_name , model_field ):
11+ """
12+ Extend Django REST Framework's get_unique_validators() function to attach a UniqueValidator to a field *only* if the
13+ associated UniqueConstraint does NOT have a condition which references another field. See bug #19302.
14+ """
15+ field_set = {field_name }
16+ conditions = {
17+ c .condition
18+ for c in model_field .model ._meta .constraints
19+ if isinstance (c , UniqueConstraint ) and set (c .fields ) == field_set
20+ }
21+
22+ # START custom logic
23+ conditions = {
24+ cond for cond in conditions
25+ if cond .referenced_base_fields == field_set
26+ }
27+ # END custom logic
28+
29+ if getattr (model_field , 'unique' , False ):
30+ conditions .add (None )
31+ if not conditions :
32+ return
33+ unique_error_message = get_unique_error_message (model_field )
34+ queryset = model_field .model ._default_manager
35+ for condition in conditions :
36+ yield UniqueValidator (
37+ queryset = queryset if condition is None else queryset .filter (condition ),
38+ message = unique_error_message
39+ )
Original file line number Diff line number Diff line change 1111from django .core .validators import URLValidator
1212from django .utils .module_loading import import_string
1313from django .utils .translation import gettext_lazy as _
14+ from rest_framework .utils import field_mapping
1415
1516from core .exceptions import IncompatiblePluginError
1617from netbox .config import PARAMS as CONFIG_PARAMS
2021import storages .utils # type: ignore
2122from utilities .release import load_release_data
2223from utilities .string import trailing_slash
24+ from .monkey import get_unique_validators
25+
26+
27+ #
28+ # Monkey-patching
29+ #
30+
31+ # TODO: Remove this once #20547 has been implemented
32+ # Override DRF's get_unique_validators() function with our own (see bug #19302)
33+ field_mapping .get_unique_validators = get_unique_validators
34+
2335
2436#
2537# Environment setup
You can’t perform that action at this time.
0 commit comments