Rename swagger_serializer_method parameter and update docs

openapi3 1.10.0
Cristi Vîjdea 2018-08-08 01:41:54 +03:00
parent afcba582b3
commit 23ebba4207
5 changed files with 49 additions and 41 deletions

View File

@ -159,44 +159,52 @@ Where you can use the :func:`@swagger_auto_schema <.swagger_auto_schema>` decora
Support for SerializerMethodField Support for SerializerMethodField
********************************* *********************************
Schema generation of ``serializers.SerializerMethodField`` supported in two ways: Schema generation of ``serializers.SerializerMethodField`` is supported in two ways:
1) The decorator ``swagger_serializer_method(serializer)`` for the use case where the serializer method 1) The :func:`swagger_serializer_method <.swagger_serializer_method>` decorator for the use case where the serializer
is using a serializer. e.g.: method is using a serializer. e.g.:
.. code-block:: python
from drf_yasg.utils import swagger_serializer_method
class OtherStuffSerializer(serializers.Serializer):
foo = serializers.CharField()
class ParentSerializer(serializers.Serializer):
other_stuff = serializers.SerializerMethodField()
@swagger_serializer_method(serializer_or_field=OtherStuffSerializer)
def get_other_stuff(self, obj):
return OtherStuffSerializer().data
.. code-block:: python Note that the ``serializer_or_field`` parameter can accept either a subclass or an instance of ``serializers.Field``.
from drf_yasg.utils import swagger_serializer_method
class OtherStuffSerializer(serializers.Serializer): 2) For simple cases where the method is returning one of the supported types, `Python 3 type hinting`_ of the
foo = serializers.CharField() serializer method return value can be used. e.g.:
.. code-block:: python
class ParentSerializer(serializers.Serializer): class SomeSerializer(serializers.Serializer):
some_number = serializers.SerializerMethodField()
other_stuff = serializers.SerializerMethodField() def get_some_number(self, obj) -> float:
return 1.0
@swagger_serializer_method(serializer=OtherStuffSerializer) When return type hinting is not supported, the equivalent ``serializers.Field`` subclass can be used with
def get_other_stuff(self, obj): :func:`swagger_serializer_method <.swagger_serializer_method>`:
return OtherStuffSerializer().data
.. code-block:: python
Note that the serializer parameter can be either be a serializer class or instance class SomeSerializer(serializers.Serializer):
some_number = serializers.SerializerMethodField()
@swagger_serializer_method(serializer_or_field=serializers.FloatField)
def get_some_number(self, obj):
return 1.0
2) For simple cases where the method is returning one of the supported types,
`Python 3 type hinting`_ of the serializer method return value can be used. e.g.:
.. code-block:: python
class SomeSerializer(serializers.Serializer):
some_number = serializers.SerializerMethodField()
def get_some_number(self, obj) -> float:
return 1.0
******************************** ********************************
Serializer ``Meta`` nested class Serializer ``Meta`` nested class

View File

@ -459,8 +459,8 @@ def get_basic_type_info_from_hint(hint_class):
class SerializerMethodFieldInspector(FieldInspector): class SerializerMethodFieldInspector(FieldInspector):
"""Provides conversion for SerializerMethodField, optionally using information from the swagger_method_field """Provides conversion for SerializerMethodField, optionally using information from the swagger_serializer_method
decorator decorator.
""" """
def field_to_swagger_object(self, field, swagger_object_type, use_references, **kwargs): def field_to_swagger_object(self, field, swagger_object_type, use_references, **kwargs):

View File

@ -178,18 +178,18 @@ def swagger_auto_schema(method=None, methods=None, auto_schema=unset, request_bo
return decorator return decorator
def swagger_serializer_method(serializer): def swagger_serializer_method(serializer_or_field):
""" """
Decorates the method of a serializers.SerializerMethodField Decorates the method of a serializers.SerializerMethodField
to hint as to how Swagger should be generated for this field. to hint as to how Swagger should be generated for this field.
:param serializer: serializer class or instance :param serializer_or_field: ``Serializer``/``Field`` class or instance
:return: :return:
""" """
def decorator(serializer_method): def decorator(serializer_method):
# stash the serializer for SerializerMethodFieldInspector to find # stash the serializer for SerializerMethodFieldInspector to find
serializer_method._swagger_serializer = serializer serializer_method._swagger_serializer = serializer_or_field
return serializer_method return serializer_method
return decorator return decorator

View File

@ -22,21 +22,21 @@ class MethodFieldExampleSerializer(serializers.Serializer):
hinted_bool = serializers.SerializerMethodField( hinted_bool = serializers.SerializerMethodField(
help_text="the type hint on the method should determine this to be a bool") help_text="the type hint on the method should determine this to be a bool")
@swagger_serializer_method(serializer=serializers.BooleanField) @swagger_serializer_method(serializer_or_field=serializers.BooleanField)
def get_hinted_bool(self, obj): def get_hinted_bool(self, obj):
return True return True
hinted_int = serializers.SerializerMethodField( hinted_int = serializers.SerializerMethodField(
help_text="the type hint on the method should determine this to be an integer") help_text="the type hint on the method should determine this to be an integer")
@swagger_serializer_method(serializer=serializers.IntegerField) @swagger_serializer_method(serializer_or_field=serializers.IntegerField)
def get_hinted_int(self, obj): def get_hinted_int(self, obj):
return 1 return 1
hinted_float = serializers.SerializerMethodField( hinted_float = serializers.SerializerMethodField(
help_text="the type hint on the method should determine this to be a number") help_text="the type hint on the method should determine this to be a number")
@swagger_serializer_method(serializer=serializers.FloatField) @swagger_serializer_method(serializer_or_field=serializers.FloatField)
def get_hinted_float(self, obj): def get_hinted_float(self, obj):
return 1.0 return 1.0
@ -44,28 +44,28 @@ class MethodFieldExampleSerializer(serializers.Serializer):
help_text="the type hint on the method should determine this to be a decimal") help_text="the type hint on the method should determine this to be a decimal")
# note that in this case an instance is required since DecimalField has required arguments # note that in this case an instance is required since DecimalField has required arguments
@swagger_serializer_method(serializer=serializers.DecimalField(max_digits=6, decimal_places=4)) @swagger_serializer_method(serializer_or_field=serializers.DecimalField(max_digits=6, decimal_places=4))
def get_hinted_decimal(self, obj): def get_hinted_decimal(self, obj):
return decimal.Decimal(1) return decimal.Decimal(1)
hinted_datetime = serializers.SerializerMethodField( hinted_datetime = serializers.SerializerMethodField(
help_text="the type hint on the method should determine this to be a datetime") help_text="the type hint on the method should determine this to be a datetime")
@swagger_serializer_method(serializer=serializers.DateTimeField) @swagger_serializer_method(serializer_or_field=serializers.DateTimeField)
def get_hinted_datetime(self, obj): def get_hinted_datetime(self, obj):
return datetime.datetime.now() return datetime.datetime.now()
hinted_date = serializers.SerializerMethodField( hinted_date = serializers.SerializerMethodField(
help_text="the type hint on the method should determine this to be a date") help_text="the type hint on the method should determine this to be a date")
@swagger_serializer_method(serializer=serializers.DateField) @swagger_serializer_method(serializer_or_field=serializers.DateField)
def get_hinted_date(self, obj): def get_hinted_date(self, obj):
return datetime.date.today() return datetime.date.today()
hinted_uuid = serializers.SerializerMethodField( hinted_uuid = serializers.SerializerMethodField(
help_text="the type hint on the method should determine this to be a uuid") help_text="the type hint on the method should determine this to be a uuid")
@swagger_serializer_method(serializer=serializers.UUIDField) @swagger_serializer_method(serializer_or_field=serializers.UUIDField)
def get_hinted_uuid(self, obj): def get_hinted_uuid(self, obj):
return uuid.uuid4() return uuid.uuid4()

View File

@ -26,7 +26,7 @@ class UserSerializerrr(serializers.ModelSerializer):
hint_example = MethodFieldExampleSerializer() hint_example = MethodFieldExampleSerializer()
@swagger_serializer_method(serializer=OtherStuffSerializer) @swagger_serializer_method(serializer_or_field=OtherStuffSerializer)
def get_other_stuff(self, obj): def get_other_stuff(self, obj):
""" """
method_field that uses a serializer internally. method_field that uses a serializer internally.
@ -41,7 +41,7 @@ class UserSerializerrr(serializers.ModelSerializer):
help_text="help text on field is set, so this should appear in swagger" help_text="help text on field is set, so this should appear in swagger"
) )
@swagger_serializer_method(serializer=serializers.IntegerField( @swagger_serializer_method(serializer_or_field=serializers.IntegerField(
help_text="decorated instance help_text shouldn't appear in swagger because field has priority")) help_text="decorated instance help_text shouldn't appear in swagger because field has priority"))
def get_help_text_example_1(self): def get_help_text_example_1(self):
""" """
@ -52,7 +52,7 @@ class UserSerializerrr(serializers.ModelSerializer):
help_text_example_2 = serializers.SerializerMethodField() help_text_example_2 = serializers.SerializerMethodField()
@swagger_serializer_method(serializer=serializers.IntegerField( @swagger_serializer_method(serializer_or_field=serializers.IntegerField(
help_text="instance help_text is set, so should appear in swagger")) help_text="instance help_text is set, so should appear in swagger"))
def get_help_text_example_2(self): def get_help_text_example_2(self):
""" """
@ -63,7 +63,7 @@ class UserSerializerrr(serializers.ModelSerializer):
help_text_example_3 = serializers.SerializerMethodField() help_text_example_3 = serializers.SerializerMethodField()
@swagger_serializer_method(serializer=serializers.IntegerField()) @swagger_serializer_method(serializer_or_field=serializers.IntegerField())
def get_help_text_example_3(self): def get_help_text_example_3(self):
""" """
docstring is set so should appear in swagger as fallback docstring is set so should appear in swagger as fallback