Fix ModelViewSet Nested bug (#65)

* Add todo repro app
* Add explicit test against model named "Nested"
* Force serializers named NestedSerializer to be output as inline models
* Allow ref_name to rescue a NestedSerializer
* Add tests and documentation
This commit is contained in:
Cristi Vîjdea
2018-02-22 03:46:16 +02:00
committed by GitHub
parent 10c7e22940
commit d5073081d9
15 changed files with 326 additions and 11 deletions
+2 -1
View File
@@ -234,7 +234,8 @@ class FieldInspector(BaseInspector):
if default is not None:
instance_kwargs['default'] = default
instance_kwargs.setdefault('title', title)
if instance_kwargs.get('type', None) != openapi.TYPE_ARRAY:
instance_kwargs.setdefault('title', title)
instance_kwargs.setdefault('description', description)
instance_kwargs.update(kwargs)
+15 -2
View File
@@ -1,3 +1,4 @@
import logging
import operator
from collections import OrderedDict
from decimal import Decimal
@@ -12,6 +13,8 @@ from ..errors import SwaggerGenerationError
from ..utils import decimal_as_float, filter_none
from .base import FieldInspector, NotHandled, SerializerInspector
logger = logging.getLogger(__name__)
class InlineSerializerInspector(SerializerInspector):
"""Provides serializer conversions using :meth:`.FieldInspector.field_to_swagger_object`."""
@@ -54,10 +57,14 @@ class InlineSerializerInspector(SerializerInspector):
serializer = field
serializer_meta = getattr(serializer, 'Meta', None)
serializer_name = type(serializer).__name__
if hasattr(serializer_meta, 'ref_name'):
ref_name = serializer_meta.ref_name
elif serializer_name == 'NestedSerializer' and isinstance(serializer, serializers.ModelSerializer):
logger.debug("Forcing inline output for ModelSerializer named 'NestedSerializer': " + str(serializer))
ref_name = None
else:
ref_name = type(serializer).__name__
ref_name = serializer_name
if ref_name.endswith('Serializer'):
ref_name = ref_name[:-len('Serializer')]
@@ -77,11 +84,17 @@ class InlineSerializerInspector(SerializerInspector):
if child.required:
required.append(property_name)
return SwaggerType(
result = SwaggerType(
type=openapi.TYPE_OBJECT,
properties=properties,
required=required or None,
)
if not ref_name:
# on an inline model, the title is derived from the field name
# but is visually displayed like the model named, which is confusing
# it is better to just remove title from inline models
del result.title
return result
if not ref_name or not use_references:
return make_schema_definition()