Add security requirements handling (#54)
* Add security requirements handling * Update swagger-ui to 3.9.2, ReDoc to 1.20.0 Closes #39.openapi3
parent
f18ff60ae7
commit
fc35d9043e
65
README.rst
65
README.rst
|
|
@ -185,71 +185,8 @@ c. ``SWAGGER_SETTINGS`` and ``REDOC_SETTINGS``
|
||||||
----------------------------------------------
|
----------------------------------------------
|
||||||
|
|
||||||
Additionally, you can include some more settings in your ``settings.py`` file.
|
Additionally, you can include some more settings in your ``settings.py`` file.
|
||||||
The possible settings and their default values are as follows:
|
See https://drf-yasg.readthedocs.io/en/stable/settings.html for details.
|
||||||
|
|
||||||
.. code:: python
|
|
||||||
|
|
||||||
SWAGGER_SETTINGS = {
|
|
||||||
# default inspector classes, see advanced documentation
|
|
||||||
'DEFAULT_AUTO_SCHEMA_CLASS': 'drf_yasg.inspectors.SwaggerAutoSchema',
|
|
||||||
'DEFAULT_FIELD_INSPECTORS': [
|
|
||||||
'drf_yasg.inspectors.CamelCaseJSONFilter',
|
|
||||||
'drf_yasg.inspectors.ReferencingSerializerInspector',
|
|
||||||
'drf_yasg.inspectors.RelatedFieldInspector',
|
|
||||||
'drf_yasg.inspectors.ChoiceFieldInspector',
|
|
||||||
'drf_yasg.inspectors.FileFieldInspector',
|
|
||||||
'drf_yasg.inspectors.DictFieldInspector',
|
|
||||||
'drf_yasg.inspectors.SimpleFieldInspector',
|
|
||||||
'drf_yasg.inspectors.StringDefaultFieldInspector',
|
|
||||||
],
|
|
||||||
'DEFAULT_FILTER_INSPECTORS': [
|
|
||||||
'drf_yasg.inspectors.CoreAPICompatInspector',
|
|
||||||
],
|
|
||||||
'DEFAULT_PAGINATOR_INSPECTORS': [
|
|
||||||
'drf_yasg.inspectors.DjangoRestResponsePagination',
|
|
||||||
'drf_yasg.inspectors.CoreAPICompatInspector',
|
|
||||||
],
|
|
||||||
|
|
||||||
# default api Info if none is otherwise given; should be an import string to an openapi.Info object
|
|
||||||
'DEFAULT_INFO': None,
|
|
||||||
# default API url if none is otherwise given
|
|
||||||
'DEFAULT_API_URL': None,
|
|
||||||
|
|
||||||
'USE_SESSION_AUTH': True, # add Django Login and Django Logout buttons, CSRF token to swagger UI page
|
|
||||||
'LOGIN_URL': getattr(django.conf.settings, 'LOGIN_URL', None), # URL for the login button
|
|
||||||
'LOGOUT_URL': getattr(django.conf.settings, 'LOGOUT_URL', None), # URL for the logout button
|
|
||||||
|
|
||||||
# Swagger security definitions to include in the schema;
|
|
||||||
# see https://github.com/OAI/OpenAPI-Specification/blob/master/versions/2.0.md#security-definitions-object
|
|
||||||
'SECURITY_DEFINITIONS': {
|
|
||||||
'basic': {
|
|
||||||
'type': 'basic'
|
|
||||||
}
|
|
||||||
},
|
|
||||||
|
|
||||||
# url to an external Swagger validation service; defaults to 'http://online.swagger.io/validator/'
|
|
||||||
# set to None to disable the schema validation badge in the UI
|
|
||||||
'VALIDATOR_URL': '',
|
|
||||||
|
|
||||||
# swagger-ui configuration settings, see https://github.com/swagger-api/swagger-ui/blob/112bca906553a937ac67adc2e500bdeed96d067b/docs/usage/configuration.md#parameters
|
|
||||||
'OPERATIONS_SORTER': None,
|
|
||||||
'TAGS_SORTER': None,
|
|
||||||
'DOC_EXPANSION': 'list',
|
|
||||||
'DEEP_LINKING': False,
|
|
||||||
'SHOW_EXTENSIONS': True,
|
|
||||||
'DEFAULT_MODEL_RENDERING': 'model',
|
|
||||||
'DEFAULT_MODEL_DEPTH': 3,
|
|
||||||
}
|
|
||||||
|
|
||||||
.. code:: python
|
|
||||||
|
|
||||||
REDOC_SETTINGS = {
|
|
||||||
# ReDoc UI configuration settings, see https://github.com/Rebilly/ReDoc#redoc-tag-attributes
|
|
||||||
'LAZY_RENDERING': True,
|
|
||||||
'HIDE_HOSTNAME': False,
|
|
||||||
'EXPAND_RESPONSES': 'all',
|
|
||||||
'PATH_IN_MIDDLE': False,
|
|
||||||
}
|
|
||||||
|
|
||||||
3. Caching
|
3. Caching
|
||||||
==========
|
==========
|
||||||
|
|
|
||||||
|
|
@ -9,158 +9,6 @@ Custom schema generation
|
||||||
If the default spec generation does not quite match what you were hoping to achieve, ``drf-yasg`` provides some
|
If the default spec generation does not quite match what you were hoping to achieve, ``drf-yasg`` provides some
|
||||||
custom behavior hooks by default.
|
custom behavior hooks by default.
|
||||||
|
|
||||||
*********************
|
|
||||||
Swagger spec overview
|
|
||||||
*********************
|
|
||||||
|
|
||||||
This library generates OpenAPI 2.0 documents. The authoritative specification for this document's structure will always
|
|
||||||
be the official documentation over at `swagger.io <https://swagger.io/>`__ and the `OpenAPI 2.0 specification
|
|
||||||
page <https://github.com/OAI/OpenAPI-Specification/blob/master/versions/2.0.md>`__.
|
|
||||||
|
|
||||||
Beause the above specifications are a bit heavy and convoluted, here is a general overview of how the specification
|
|
||||||
is structured, starting from the root ``Swagger`` object.
|
|
||||||
|
|
||||||
* :class:`.Swagger` object
|
|
||||||
+ ``info``, ``schemes``, ``securityDefinitions`` and other informative attributes
|
|
||||||
+ ``paths``: :class:`.Paths` object
|
|
||||||
A list of all the paths in the API in the form of a mapping
|
|
||||||
|
|
||||||
- ``{path}``: :class:`.PathItem` - each :class:`.PathItem` has multiple operations keyed by method
|
|
||||||
* ``{http_method}``: :class:`.Operation`
|
|
||||||
Each operation is thus uniquely identified by its ``(path, http_method)`` combination,
|
|
||||||
e.g. ``GET /articles/``, ``POST /articles/``, etc.
|
|
||||||
* ``parameters``: [:class:`.Parameter`] - and a list of path parameters
|
|
||||||
+ ``definitions``: named Models
|
|
||||||
A list of all the named models in the API in the form of a mapping
|
|
||||||
|
|
||||||
- ``{ModelName}``: :class:`.Schema`
|
|
||||||
|
|
||||||
* :class:`.Operation` contains the following information about each operation:
|
|
||||||
+ ``parameters``: [:class:`.Parameter`]
|
|
||||||
A list of all the *query*, *header* and *form* parameters accepted by the operation.
|
|
||||||
|
|
||||||
- there can also be **at most one** body parameter whose structure is represented by a
|
|
||||||
:class:`.Schema` or a reference to one (:class:`.SchemaRef`)
|
|
||||||
+ ``responses``: :class:`.Responses`
|
|
||||||
A list of all the possible responses the operation is expected to return. Each response can optionally have a
|
|
||||||
:class:`.Schema` which describes the structure of its body.
|
|
||||||
|
|
||||||
- ``{status_code}``: :class:`.Response` - mapping of status code to response definition
|
|
||||||
|
|
||||||
+ ``operationId`` - should be unique across all operations
|
|
||||||
+ ``tags`` - used to group operations in the listing
|
|
||||||
|
|
||||||
It is interesting to note the main differences between :class:`.Parameter` and :class:`.Schema` objects:
|
|
||||||
|
|
||||||
+----------------------------------------------------------+-----------------------------------------------------------+
|
|
||||||
| :class:`.Schema` | :class:`.Parameter` |
|
|
||||||
+==========================================================+===========================================================+
|
|
||||||
| Can nest other Schemas | Cannot nest other Parameters |br| |
|
|
||||||
| | Can only nest a Schema if the parameter is ``in: body`` |
|
|
||||||
+----------------------------------------------------------+-----------------------------------------------------------+
|
|
||||||
| Cannot describe file uploads |br| | Can describe file uploads via ``type`` = ``file``, |br| |
|
|
||||||
| - ``file`` is not permitted as a value for ``type`` | but only as part of a form :class:`.Operation` [#formop]_ |
|
|
||||||
+----------------------------------------------------------+-----------------------------------------------------------+
|
|
||||||
| Can be used in :class:`.Response`\ s | Cannot be used in :class:`.Response`\ s |
|
|
||||||
+----------------------------------------------------------+-----------------------------------------------------------+
|
|
||||||
| Cannot be used in form :class:`.Operation`\ s [#formop]_ | Can be used in form :class:`.Operation`\ s [#formop]_ |
|
|
||||||
+----------------------------------------------------------+-----------------------------------------------------------+
|
|
||||||
| Can only describe request or response bodies | Can describe ``query``, ``form``, ``header`` or ``path`` |
|
|
||||||
| | parameters |
|
|
||||||
+----------------------------------------------------------+-----------------------------------------------------------+
|
|
||||||
|
|
||||||
.. [#formop] a form Operation is an :class:`.Operation` that consumes ``multipart/form-data`` or
|
|
||||||
``application/x-www-form-urlencoded`` content
|
|
||||||
|
|
||||||
* a form Operation cannot have ``body`` parameters
|
|
||||||
* a non-form operation cannot have ``form`` parameters
|
|
||||||
|
|
||||||
****************
|
|
||||||
Default behavior
|
|
||||||
****************
|
|
||||||
|
|
||||||
This section describes where information is sourced from when using the default generation process.
|
|
||||||
|
|
||||||
* :class:`.Paths` are generated by exploring the patterns registered in your default ``urlconf``, or the ``patterns``
|
|
||||||
and ``urlconf`` you specified when constructing :class:`.OpenAPISchemaGenerator`; only views inheriting from Django
|
|
||||||
Rest Framework's ``APIView`` are looked at, all other views are ignored
|
|
||||||
* ``path`` :class:`.Parameter`\ s are generated by looking in the URL pattern for any template parameters; attempts are
|
|
||||||
made to guess their type from the views ``queryset`` and ``lookup_field``, if applicable. You can override path
|
|
||||||
parameters via ``manual_parameters`` in :ref:`@swagger_auto_schema <custom-spec-swagger-auto-schema>`.
|
|
||||||
* ``query`` :class:`.Parameter`\ s - i.e. parameters specified in the URL as ``/path/?query1=value&query2=value`` -
|
|
||||||
are generated from your view's ``filter_backends`` and ``paginator``, if any are declared. Additional parameters can
|
|
||||||
be specified via the ``query_serializer`` and ``manual_parameters`` arguments of
|
|
||||||
:ref:`@swagger_auto_schema <custom-spec-swagger-auto-schema>`
|
|
||||||
* The request body is only generated for the HTTP ``POST``, ``PUT`` and ``PATCH`` methods, and is sourced from the
|
|
||||||
view's ``serializer_class``. You can also override the request body using the ``request_body`` argument of
|
|
||||||
:ref:`@swagger_auto_schema <custom-spec-swagger-auto-schema>`.
|
|
||||||
|
|
||||||
- if the view represents a form request (that is, all its parsers are of the ``multipart/form-data`` or
|
|
||||||
``application/x-www-form-urlencoded`` media types), the request body will be output as ``form``
|
|
||||||
:class:`.Parameter`\ s
|
|
||||||
- if it is not a form request, the request body will be output as a single ``body`` :class:`.Parameter` wrapped
|
|
||||||
around a :class:`.Schema`
|
|
||||||
|
|
||||||
* ``header`` :class:`.Parameter`\ s are supported by the OpenAPI specification but are never generated by this library;
|
|
||||||
you can still add them using ``manual_parameters``.
|
|
||||||
* :class:`.Responses` are generated as follows:
|
|
||||||
|
|
||||||
+ if ``responses`` is provided to :ref:`@swagger_auto_schema <custom-spec-swagger-auto-schema>` and contains at least
|
|
||||||
one success status code (i.e. any `2xx` status code), no automatic response is generated and the given response
|
|
||||||
is used as described in the :func:`@swagger_auto_schema documentation <.swagger_auto_schema>`
|
|
||||||
+ otherwise, an attempt is made to generate a default response:
|
|
||||||
|
|
||||||
- the success status code is assumed to be ``204` for ``DELETE`` requests, ``201`` for ``POST`` requests, and
|
|
||||||
``200`` for all other request methods
|
|
||||||
- if the view has a request body, the same ``Serializer`` or :class:`.Schema` as in the request body is used
|
|
||||||
in generating the :class:`.Response` schema; this is inline with the default ``GenericAPIView`` and
|
|
||||||
``GenericViewSet`` behavior
|
|
||||||
- if the view has no request body, its ``serializer_class`` is used to generate the :class:`.Response` schema
|
|
||||||
- if the view is a list view (as defined by :func:`.is_list_view`), the response schema is wrapped in an array
|
|
||||||
- if the view is also paginated, the response schema is then wrapped in the appropriate paging response structure
|
|
||||||
- the description of the response is left blank
|
|
||||||
|
|
||||||
* :class:`.Response` headers are supported by the OpenAPI specification but not currently supported by this library;
|
|
||||||
you can still add them manually by providing an `appropriately structured dictionary
|
|
||||||
<https://github.com/OAI/OpenAPI-Specification/blob/master/versions/2.0.md#headersObject>`_
|
|
||||||
to the ``headers`` property of a :class:`.Response` object
|
|
||||||
* *descriptions* for :class:`.Operation`\ s, :class:`.Parameter`\ s and :class:`.Schema`\ s are picked up from
|
|
||||||
docstrings and ``help_text`` attributes in the same manner as the `default DRF SchemaGenerator
|
|
||||||
<http://www.django-rest-framework.org/api-guide/schemas/#schemas-as-documentation>`_
|
|
||||||
* .. _custom-spec-base-url:
|
|
||||||
|
|
||||||
The base URL for the API consists of three values - the ``host``, ``schemes`` and ``basePath`` attributes
|
|
||||||
* The host name and scheme are determined, in descending order of priority:
|
|
||||||
|
|
||||||
+ from the ``url`` argument passed to :func:`.get_schema_view` (more specifically, to the underlying
|
|
||||||
:class:`.OpenAPISchemaGenerator`)
|
|
||||||
+ from the :ref:`DEFAULT_API_URL setting <default-swagger-settings>`
|
|
||||||
+ inferred from the request made to the schema endpoint
|
|
||||||
|
|
||||||
For example, an url of ``https://www.example.com:8080/some/path`` will populate the ``host`` and ``schemes``
|
|
||||||
attributes with ``www.example.com:8080`` and ``['https']``, respectively. The path component will be ignored.
|
|
||||||
* The base path is determined as the concatenation of two variables:
|
|
||||||
|
|
||||||
#. the `SCRIPT_NAME`_ wsgi environment variable; this is set, for example, when serving the site from a
|
|
||||||
sub-path using web server url rewriting
|
|
||||||
|
|
||||||
.. Tip::
|
|
||||||
|
|
||||||
The Django `FORCE_SCRIPT_NAME`_ setting can be used to override the `SCRIPT_NAME`_ or set it when it's
|
|
||||||
missing from the environment.
|
|
||||||
|
|
||||||
#. the longest common path prefix of all the urls in your API - see :meth:`.determine_path_prefix`
|
|
||||||
|
|
||||||
* When using API versioning with ``NamespaceVersioning`` or ``URLPathVersioning``, versioned endpoints that do not
|
|
||||||
match the version used to access the ``SchemaView`` will be excluded from the endpoint list - for example,
|
|
||||||
``/api/v1.0/endpoint`` will be shown when viewing ``/api/v1.0/swagger/``, while ``/api/v2.0/endpoint`` will not
|
|
||||||
|
|
||||||
Other versioning schemes are not presently supported.
|
|
||||||
|
|
||||||
|
|
||||||
.. versionadded:: 1.2
|
|
||||||
Base path and versioning support.
|
|
||||||
|
|
||||||
.. _custom-spec-swagger-auto-schema:
|
.. _custom-spec-swagger-auto-schema:
|
||||||
|
|
||||||
**************************************
|
**************************************
|
||||||
|
|
@ -430,6 +278,3 @@ A second example, of a :class:`~.inspectors.FieldInspector` that removes the ``t
|
||||||
This means that you should generally avoid view or method-specific ``FieldInspector``\ s if you are dealing with
|
This means that you should generally avoid view or method-specific ``FieldInspector``\ s if you are dealing with
|
||||||
references (a.k.a named models), because you can never know which view will be the first to generate the schema
|
references (a.k.a named models), because you can never know which view will be the first to generate the schema
|
||||||
for a given serializer.
|
for a given serializer.
|
||||||
|
|
||||||
.. _SCRIPT_NAME: https://www.python.org/dev/peps/pep-0333/#environ-variables
|
|
||||||
.. _FORCE_SCRIPT_NAME: https://docs.djangoproject.com/en/2.0/ref/settings/#force-script-name
|
|
||||||
|
|
|
||||||
|
|
@ -12,6 +12,8 @@ drf-yasg
|
||||||
|
|
||||||
readme.rst
|
readme.rst
|
||||||
rendering.rst
|
rendering.rst
|
||||||
|
openapi.rst
|
||||||
|
security.rst
|
||||||
custom_spec.rst
|
custom_spec.rst
|
||||||
custom_ui.rst
|
custom_ui.rst
|
||||||
settings.rst
|
settings.rst
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,163 @@
|
||||||
|
.. |br| raw:: html
|
||||||
|
|
||||||
|
<br />
|
||||||
|
|
||||||
|
**********************
|
||||||
|
Functional overview
|
||||||
|
**********************
|
||||||
|
|
||||||
|
|
||||||
|
------------------------------
|
||||||
|
OpenAPI specification overview
|
||||||
|
------------------------------
|
||||||
|
|
||||||
|
This library generates OpenAPI 2.0 documents. The authoritative specification for this document's structure will always
|
||||||
|
be the official documentation over at `swagger.io <https://swagger.io/>`__ and the `OpenAPI 2.0 specification
|
||||||
|
page <https://github.com/OAI/OpenAPI-Specification/blob/master/versions/2.0.md>`__.
|
||||||
|
|
||||||
|
Beause the above specifications are a bit heavy and convoluted, here is a general overview of how the specification
|
||||||
|
is structured, starting from the root ``Swagger`` object.
|
||||||
|
|
||||||
|
* :class:`.Swagger` object
|
||||||
|
+ ``info``, ``schemes``, ``securityDefinitions`` and other informative attributes
|
||||||
|
+ ``paths``: :class:`.Paths` object
|
||||||
|
A list of all the paths in the API in the form of a mapping
|
||||||
|
|
||||||
|
- ``{path}``: :class:`.PathItem` - each :class:`.PathItem` has multiple operations keyed by method
|
||||||
|
* ``{http_method}``: :class:`.Operation`
|
||||||
|
Each operation is thus uniquely identified by its ``(path, http_method)`` combination,
|
||||||
|
e.g. ``GET /articles/``, ``POST /articles/``, etc.
|
||||||
|
* ``parameters``: [:class:`.Parameter`] - and a list of path parameters
|
||||||
|
+ ``definitions``: named Models
|
||||||
|
A list of all the named models in the API in the form of a mapping
|
||||||
|
|
||||||
|
- ``{ModelName}``: :class:`.Schema`
|
||||||
|
|
||||||
|
* :class:`.Operation` contains the following information about each operation:
|
||||||
|
+ ``parameters``: [:class:`.Parameter`]
|
||||||
|
A list of all the *query*, *header* and *form* parameters accepted by the operation.
|
||||||
|
|
||||||
|
- there can also be **at most one** body parameter whose structure is represented by a
|
||||||
|
:class:`.Schema` or a reference to one (:class:`.SchemaRef`)
|
||||||
|
+ ``responses``: :class:`.Responses`
|
||||||
|
A list of all the possible responses the operation is expected to return. Each response can optionally have a
|
||||||
|
:class:`.Schema` which describes the structure of its body.
|
||||||
|
|
||||||
|
- ``{status_code}``: :class:`.Response` - mapping of status code to response definition
|
||||||
|
|
||||||
|
+ ``operationId`` - should be unique across all operations
|
||||||
|
+ ``tags`` - used to group operations in the listing
|
||||||
|
|
||||||
|
It is interesting to note the main differences between :class:`.Parameter` and :class:`.Schema` objects:
|
||||||
|
|
||||||
|
+----------------------------------------------------------+-----------------------------------------------------------+
|
||||||
|
| :class:`.Schema` | :class:`.Parameter` |
|
||||||
|
+==========================================================+===========================================================+
|
||||||
|
| Can nest other Schemas | Cannot nest other Parameters |br| |
|
||||||
|
| | Can only nest a Schema if the parameter is ``in: body`` |
|
||||||
|
+----------------------------------------------------------+-----------------------------------------------------------+
|
||||||
|
| Cannot describe file uploads |br| | Can describe file uploads via ``type`` = ``file``, |br| |
|
||||||
|
| - ``file`` is not permitted as a value for ``type`` | but only as part of a form :class:`.Operation` [#formop]_ |
|
||||||
|
+----------------------------------------------------------+-----------------------------------------------------------+
|
||||||
|
| Can be used in :class:`.Response`\ s | Cannot be used in :class:`.Response`\ s |
|
||||||
|
+----------------------------------------------------------+-----------------------------------------------------------+
|
||||||
|
| Cannot be used in form :class:`.Operation`\ s [#formop]_ | Can be used in form :class:`.Operation`\ s [#formop]_ |
|
||||||
|
+----------------------------------------------------------+-----------------------------------------------------------+
|
||||||
|
| Can only describe request or response bodies | Can describe ``query``, ``form``, ``header`` or ``path`` |
|
||||||
|
| | parameters |
|
||||||
|
+----------------------------------------------------------+-----------------------------------------------------------+
|
||||||
|
|
||||||
|
.. [#formop] a form Operation is an :class:`.Operation` that consumes ``multipart/form-data`` or
|
||||||
|
``application/x-www-form-urlencoded`` content
|
||||||
|
|
||||||
|
* a form Operation cannot have ``body`` parameters
|
||||||
|
* a non-form operation cannot have ``form`` parameters
|
||||||
|
|
||||||
|
----------------
|
||||||
|
Default behavior
|
||||||
|
----------------
|
||||||
|
|
||||||
|
This section describes where information is sourced from when using the default generation process.
|
||||||
|
|
||||||
|
* :class:`.Paths` are generated by exploring the patterns registered in your default ``urlconf``, or the ``patterns``
|
||||||
|
and ``urlconf`` you specified when constructing :class:`.OpenAPISchemaGenerator`; only views inheriting from Django
|
||||||
|
Rest Framework's ``APIView`` are looked at, all other views are ignored
|
||||||
|
* ``path`` :class:`.Parameter`\ s are generated by looking in the URL pattern for any template parameters; attempts are
|
||||||
|
made to guess their type from the views ``queryset`` and ``lookup_field``, if applicable. You can override path
|
||||||
|
parameters via ``manual_parameters`` in :ref:`@swagger_auto_schema <custom-spec-swagger-auto-schema>`.
|
||||||
|
* ``query`` :class:`.Parameter`\ s - i.e. parameters specified in the URL as ``/path/?query1=value&query2=value`` -
|
||||||
|
are generated from your view's ``filter_backends`` and ``paginator``, if any are declared. Additional parameters can
|
||||||
|
be specified via the ``query_serializer`` and ``manual_parameters`` arguments of
|
||||||
|
:ref:`@swagger_auto_schema <custom-spec-swagger-auto-schema>`
|
||||||
|
* The request body is only generated for the HTTP ``POST``, ``PUT`` and ``PATCH`` methods, and is sourced from the
|
||||||
|
view's ``serializer_class``. You can also override the request body using the ``request_body`` argument of
|
||||||
|
:ref:`@swagger_auto_schema <custom-spec-swagger-auto-schema>`.
|
||||||
|
|
||||||
|
- if the view represents a form request (that is, all its parsers are of the ``multipart/form-data`` or
|
||||||
|
``application/x-www-form-urlencoded`` media types), the request body will be output as ``form``
|
||||||
|
:class:`.Parameter`\ s
|
||||||
|
- if it is not a form request, the request body will be output as a single ``body`` :class:`.Parameter` wrapped
|
||||||
|
around a :class:`.Schema`
|
||||||
|
|
||||||
|
* ``header`` :class:`.Parameter`\ s are supported by the OpenAPI specification but are never generated by this library;
|
||||||
|
you can still add them using ``manual_parameters``.
|
||||||
|
* :class:`.Responses` are generated as follows:
|
||||||
|
|
||||||
|
+ if ``responses`` is provided to :ref:`@swagger_auto_schema <custom-spec-swagger-auto-schema>` and contains at least
|
||||||
|
one success status code (i.e. any `2xx` status code), no automatic response is generated and the given response
|
||||||
|
is used as described in the :func:`@swagger_auto_schema documentation <.swagger_auto_schema>`
|
||||||
|
+ otherwise, an attempt is made to generate a default response:
|
||||||
|
|
||||||
|
- the success status code is assumed to be ``204` for ``DELETE`` requests, ``201`` for ``POST`` requests, and
|
||||||
|
``200`` for all other request methods
|
||||||
|
- if the view has a request body, the same ``Serializer`` or :class:`.Schema` as in the request body is used
|
||||||
|
in generating the :class:`.Response` schema; this is inline with the default ``GenericAPIView`` and
|
||||||
|
``GenericViewSet`` behavior
|
||||||
|
- if the view has no request body, its ``serializer_class`` is used to generate the :class:`.Response` schema
|
||||||
|
- if the view is a list view (as defined by :func:`.is_list_view`), the response schema is wrapped in an array
|
||||||
|
- if the view is also paginated, the response schema is then wrapped in the appropriate paging response structure
|
||||||
|
- the description of the response is left blank
|
||||||
|
|
||||||
|
* :class:`.Response` headers are supported by the OpenAPI specification but not currently supported by this library;
|
||||||
|
you can still add them manually by providing an `appropriately structured dictionary
|
||||||
|
<https://github.com/OAI/OpenAPI-Specification/blob/master/versions/2.0.md#headersObject>`_
|
||||||
|
to the ``headers`` property of a :class:`.Response` object
|
||||||
|
* *descriptions* for :class:`.Operation`\ s, :class:`.Parameter`\ s and :class:`.Schema`\ s are picked up from
|
||||||
|
docstrings and ``help_text`` attributes in the same manner as the `default DRF SchemaGenerator
|
||||||
|
<http://www.django-rest-framework.org/api-guide/schemas/#schemas-as-documentation>`_
|
||||||
|
* .. _custom-spec-base-url:
|
||||||
|
|
||||||
|
The base URL for the API consists of three values - the ``host``, ``schemes`` and ``basePath`` attributes
|
||||||
|
* The host name and scheme are determined, in descending order of priority:
|
||||||
|
|
||||||
|
+ from the ``url`` argument passed to :func:`.get_schema_view` (more specifically, to the underlying
|
||||||
|
:class:`.OpenAPISchemaGenerator`)
|
||||||
|
+ from the :ref:`DEFAULT_API_URL setting <default-swagger-settings>`
|
||||||
|
+ inferred from the request made to the schema endpoint
|
||||||
|
|
||||||
|
For example, an url of ``https://www.example.com:8080/some/path`` will populate the ``host`` and ``schemes``
|
||||||
|
attributes with ``www.example.com:8080`` and ``['https']``, respectively. The path component will be ignored.
|
||||||
|
* The base path is determined as the concatenation of two variables:
|
||||||
|
|
||||||
|
#. the `SCRIPT_NAME`_ wsgi environment variable; this is set, for example, when serving the site from a
|
||||||
|
sub-path using web server url rewriting
|
||||||
|
|
||||||
|
.. Tip::
|
||||||
|
|
||||||
|
The Django `FORCE_SCRIPT_NAME`_ setting can be used to override the `SCRIPT_NAME`_ or set it when it's
|
||||||
|
missing from the environment.
|
||||||
|
|
||||||
|
#. the longest common path prefix of all the urls in your API - see :meth:`.determine_path_prefix`
|
||||||
|
|
||||||
|
* When using API versioning with ``NamespaceVersioning`` or ``URLPathVersioning``, versioned endpoints that do not
|
||||||
|
match the version used to access the ``SchemaView`` will be excluded from the endpoint list - for example,
|
||||||
|
``/api/v1.0/endpoint`` will be shown when viewing ``/api/v1.0/swagger/``, while ``/api/v2.0/endpoint`` will not
|
||||||
|
|
||||||
|
Other versioning schemes are not presently supported.
|
||||||
|
|
||||||
|
|
||||||
|
.. versionadded:: 1.2
|
||||||
|
Base path and versioning support.
|
||||||
|
|
||||||
|
.. _SCRIPT_NAME: https://www.python.org/dev/peps/pep-0333/#environ-variables
|
||||||
|
.. _FORCE_SCRIPT_NAME: https://docs.djangoproject.com/en/2.0/ref/settings/#force-script-name
|
||||||
|
|
@ -0,0 +1,49 @@
|
||||||
|
*********************************
|
||||||
|
Describing authentication schemes
|
||||||
|
*********************************
|
||||||
|
|
||||||
|
When using the `swagger-ui` frontend, it is possible to interact with the API described by your Swagger document.
|
||||||
|
This interaction might require authentication, which you will have to describe in order to make `swagger-ui` work
|
||||||
|
with it.
|
||||||
|
|
||||||
|
|
||||||
|
--------------------
|
||||||
|
Security definitions
|
||||||
|
--------------------
|
||||||
|
|
||||||
|
The first step that you have to do is add a :ref:`SECURITY_DEFINITIONS <security-definitions-settings>` setting
|
||||||
|
to declare all authentication schemes supported by your API.
|
||||||
|
|
||||||
|
For example, the definition for a simple API accepting HTTP basic auth and `Authorization` header API tokens would be:
|
||||||
|
|
||||||
|
.. code-block:: python
|
||||||
|
|
||||||
|
SWAGGER_SETTINGS = {
|
||||||
|
'SECURITY_DEFINITIONS': {
|
||||||
|
'Basic': {
|
||||||
|
'type': 'basic'
|
||||||
|
},
|
||||||
|
'Bearer': {
|
||||||
|
'type': 'apiKey',
|
||||||
|
'name': 'Authorization',
|
||||||
|
'in': 'header'
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
---------------------
|
||||||
|
Security requirements
|
||||||
|
---------------------
|
||||||
|
|
||||||
|
The second step is specifying, for each endpoint, which authentication mechanism can be used for interacting with it.
|
||||||
|
See https://github.com/OAI/OpenAPI-Specification/blob/master/versions/2.0.md#security-requirement-object for details.
|
||||||
|
|
||||||
|
By default, a top-level `security` that accepts all the declared security definitions is generated.
|
||||||
|
For the example above, that would be :code:`[{'Basic': []}, {'Bearer': []}]`. This can be overriden using the
|
||||||
|
:ref:`SECURITY_REQUIREMENTS <security-definitions-settings>` setting.
|
||||||
|
|
||||||
|
Operation-level overrides can be added using the ``security`` parameter of
|
||||||
|
:ref:`@swagger_auto_schema <custom-spec-swagger-auto-schema>`.
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -140,6 +140,9 @@ URL for the Django Logout action when using `USE_SESSION_AUTH`_.
|
||||||
|
|
||||||
**Default**: :python:`django.conf.settings.LOGOUT_URL`
|
**Default**: :python:`django.conf.settings.LOGOUT_URL`
|
||||||
|
|
||||||
|
.. _security-definitions-settings:
|
||||||
|
|
||||||
|
|
||||||
SECURITY_DEFINITIONS
|
SECURITY_DEFINITIONS
|
||||||
--------------------
|
--------------------
|
||||||
|
|
||||||
|
|
@ -154,6 +157,14 @@ See https://github.com/OAI/OpenAPI-Specification/blob/master/versions/2.0.md#sec
|
||||||
'type': 'basic'
|
'type': 'basic'
|
||||||
}
|
}
|
||||||
|
|
||||||
|
SECURITY_REQUIREMENTS
|
||||||
|
---------------------
|
||||||
|
|
||||||
|
Global security requirements. If :python:`None`, all schemes in ``SECURITY_DEFINITIONS`` are accepted. |br|
|
||||||
|
See https://github.com/OAI/OpenAPI-Specification/blob/master/versions/2.0.md#securityRequirementObject.
|
||||||
|
|
||||||
|
**Default**: :python:`None`
|
||||||
|
|
||||||
.. _swagger-ui-settings:
|
.. _swagger-ui-settings:
|
||||||
|
|
||||||
Swagger UI settings
|
Swagger UI settings
|
||||||
|
|
|
||||||
|
|
@ -38,9 +38,9 @@
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"commander": {
|
"commander": {
|
||||||
"version": "2.12.2",
|
"version": "2.13.0",
|
||||||
"resolved": "https://registry.npmjs.org/commander/-/commander-2.12.2.tgz",
|
"resolved": "https://registry.npmjs.org/commander/-/commander-2.13.0.tgz",
|
||||||
"integrity": "sha512-BFnaq5ZOGcDN7FlrtBT4xxkgIToalIIxwjxLWVJ8bGTpe1LroqMiqQXdA7ygc7CRvaYS+9zfPGFnJqFSayx+AA==",
|
"integrity": "sha512-MVuS359B+YzaWqjCL/c+22gfryv+mCBPHAv3zyVI2GN8EY6IRP8VwtasXn8jyyhvvq84R4ImN1OKRtcbIasjYA==",
|
||||||
"optional": true
|
"optional": true
|
||||||
},
|
},
|
||||||
"core-js": {
|
"core-js": {
|
||||||
|
|
@ -73,9 +73,9 @@
|
||||||
"integrity": "sha1-8TyUAhQdoJ50rfTmN5jXkiBEOPI="
|
"integrity": "sha1-8TyUAhQdoJ50rfTmN5jXkiBEOPI="
|
||||||
},
|
},
|
||||||
"es6-promise": {
|
"es6-promise": {
|
||||||
"version": "4.1.1",
|
"version": "4.2.2",
|
||||||
"resolved": "https://registry.npmjs.org/es6-promise/-/es6-promise-4.1.1.tgz",
|
"resolved": "https://registry.npmjs.org/es6-promise/-/es6-promise-4.2.2.tgz",
|
||||||
"integrity": "sha512-OaU1hHjgJf+b0NzsxCg7NdIYERD6Hy/PEmFLTjw+b65scuisG3Kt4QoTvJ66BBkPZ581gr0kpoVzKnxniM8nng=="
|
"integrity": "sha512-LSas5vsuA6Q4nEdf9wokY5/AJYXry98i0IzXsv49rYsgDGDNDPbqAYR1Pe23iFxygfbGZNR/5VrHXBCh2BhvUQ=="
|
||||||
},
|
},
|
||||||
"esprima": {
|
"esprima": {
|
||||||
"version": "4.0.0",
|
"version": "4.0.0",
|
||||||
|
|
@ -145,9 +145,9 @@
|
||||||
"requires": {
|
"requires": {
|
||||||
"call-me-maybe": "1.0.1",
|
"call-me-maybe": "1.0.1",
|
||||||
"debug": "3.1.0",
|
"debug": "3.1.0",
|
||||||
"es6-promise": "4.1.1",
|
"es6-promise": "4.2.2",
|
||||||
"js-yaml": "3.10.0",
|
"js-yaml": "3.10.0",
|
||||||
"ono": "4.0.2",
|
"ono": "4.0.3",
|
||||||
"z-schema": "3.19.0"
|
"z-schema": "3.19.0"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
@ -166,15 +166,20 @@
|
||||||
"resolved": "https://registry.npmjs.org/lunr/-/lunr-1.0.0.tgz",
|
"resolved": "https://registry.npmjs.org/lunr/-/lunr-1.0.0.tgz",
|
||||||
"integrity": "sha1-XJJ2ySyRrDWpJBtQGNRnI9kuL18="
|
"integrity": "sha1-XJJ2ySyRrDWpJBtQGNRnI9kuL18="
|
||||||
},
|
},
|
||||||
|
"mark.js": {
|
||||||
|
"version": "8.11.1",
|
||||||
|
"resolved": "https://registry.npmjs.org/mark.js/-/mark.js-8.11.1.tgz",
|
||||||
|
"integrity": "sha1-GA8fnr74sOY45BZq1S24eb6y/8U="
|
||||||
|
},
|
||||||
"ms": {
|
"ms": {
|
||||||
"version": "2.0.0",
|
"version": "2.0.0",
|
||||||
"resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz",
|
"resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz",
|
||||||
"integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g="
|
"integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g="
|
||||||
},
|
},
|
||||||
"ono": {
|
"ono": {
|
||||||
"version": "4.0.2",
|
"version": "4.0.3",
|
||||||
"resolved": "https://registry.npmjs.org/ono/-/ono-4.0.2.tgz",
|
"resolved": "https://registry.npmjs.org/ono/-/ono-4.0.3.tgz",
|
||||||
"integrity": "sha512-EFXJFoeF+KkZW4lwmcPMKHp2ZU7o6CM+ccX2nPbEJKiJIdyqbIcS1v6pmNgeNJ6x4/vEYn0/8oz66qXSPnnmSQ==",
|
"integrity": "sha512-7QIxG4UB00H7CR7fhXC/U7VhB5DK9wsYLwaYBui1JmQoXtLkhIBn3fbuk6FgAP+ctWeBsWVTM+R/bThvUZN+ww==",
|
||||||
"requires": {
|
"requires": {
|
||||||
"format-util": "1.0.3"
|
"format-util": "1.0.3"
|
||||||
}
|
}
|
||||||
|
|
@ -190,9 +195,9 @@
|
||||||
"integrity": "sha512-RNC5tX/JMRYR+qVdJTEAWnRxw0Yf9lvbO8lTuAOvgDODkiA8lveTSkvrNMhmaGKEyimJpJl+myb/syVS9YyPuw=="
|
"integrity": "sha512-RNC5tX/JMRYR+qVdJTEAWnRxw0Yf9lvbO8lTuAOvgDODkiA8lveTSkvrNMhmaGKEyimJpJl+myb/syVS9YyPuw=="
|
||||||
},
|
},
|
||||||
"prismjs": {
|
"prismjs": {
|
||||||
"version": "1.9.0",
|
"version": "1.10.0",
|
||||||
"resolved": "https://registry.npmjs.org/prismjs/-/prismjs-1.9.0.tgz",
|
"resolved": "https://registry.npmjs.org/prismjs/-/prismjs-1.10.0.tgz",
|
||||||
"integrity": "sha1-+j4tntw8OIfB8fMJXUHx+bQgDw8=",
|
"integrity": "sha1-d+UYfCrmsyU/zDEwKc8l/lN3hyE=",
|
||||||
"requires": {
|
"requires": {
|
||||||
"clipboard": "1.7.1"
|
"clipboard": "1.7.1"
|
||||||
}
|
}
|
||||||
|
|
@ -217,9 +222,9 @@
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"redoc": {
|
"redoc": {
|
||||||
"version": "1.19.3",
|
"version": "1.20.0",
|
||||||
"resolved": "https://registry.npmjs.org/redoc/-/redoc-1.19.3.tgz",
|
"resolved": "https://registry.npmjs.org/redoc/-/redoc-1.20.0.tgz",
|
||||||
"integrity": "sha1-DfPx+6S92G/+nGIAEzBxUjytVec=",
|
"integrity": "sha1-1c16xoQKJ8/7RzvSiYAFUq+CHq8=",
|
||||||
"requires": {
|
"requires": {
|
||||||
"core-js": "2.5.3",
|
"core-js": "2.5.3",
|
||||||
"dropkickjs": "2.1.10",
|
"dropkickjs": "2.1.10",
|
||||||
|
|
@ -228,21 +233,16 @@
|
||||||
"json-pointer": "0.6.0",
|
"json-pointer": "0.6.0",
|
||||||
"json-schema-ref-parser": "3.3.1",
|
"json-schema-ref-parser": "3.3.1",
|
||||||
"lunr": "1.0.0",
|
"lunr": "1.0.0",
|
||||||
"mark.js": "github:julmot/mark.js#714c9523feca999267f1758da8cfd92d077105d0",
|
"mark.js": "8.11.1",
|
||||||
"openapi-sampler": "0.4.3",
|
"openapi-sampler": "0.4.3",
|
||||||
"perfect-scrollbar": "0.8.1",
|
"perfect-scrollbar": "0.8.1",
|
||||||
"prismjs": "1.9.0",
|
"prismjs": "1.10.0",
|
||||||
"remarkable": "1.7.1",
|
"remarkable": "1.7.1",
|
||||||
"scrollparent": "2.0.1",
|
"scrollparent": "2.0.1",
|
||||||
"slugify": "1.2.6",
|
"slugify": "1.2.9",
|
||||||
"stream-http": "2.7.2",
|
"stream-http": "2.8.0",
|
||||||
"ts-helpers": "1.1.2",
|
"ts-helpers": "1.1.2",
|
||||||
"zone.js": "0.8.18"
|
"zone.js": "0.8.20"
|
||||||
},
|
|
||||||
"dependencies": {
|
|
||||||
"mark.js": {
|
|
||||||
"version": "github:julmot/mark.js#714c9523feca999267f1758da8cfd92d077105d0"
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"remarkable": {
|
"remarkable": {
|
||||||
|
|
@ -282,9 +282,9 @@
|
||||||
"optional": true
|
"optional": true
|
||||||
},
|
},
|
||||||
"slugify": {
|
"slugify": {
|
||||||
"version": "1.2.6",
|
"version": "1.2.9",
|
||||||
"resolved": "https://registry.npmjs.org/slugify/-/slugify-1.2.6.tgz",
|
"resolved": "https://registry.npmjs.org/slugify/-/slugify-1.2.9.tgz",
|
||||||
"integrity": "sha512-796YAGnzEnLKQHAFf7H2q1nsjY/9qywSnF9ZkMUbs9he4aZaXO/zFUow0LZ95sBAiQjOX1EmGl23gTYaswiNaQ=="
|
"integrity": "sha512-n0cdJ+kN3slJu8SbZXt/EHjljBqF6MxvMGSg/NPpBzoY7yyXoH38wp/ox20a1JaG1KgmdTN5Lf3aS9+xB2Y2aQ=="
|
||||||
},
|
},
|
||||||
"sprintf-js": {
|
"sprintf-js": {
|
||||||
"version": "1.0.3",
|
"version": "1.0.3",
|
||||||
|
|
@ -292,9 +292,9 @@
|
||||||
"integrity": "sha1-BOaSb2YolTVPPdAVIDYzuFcpfiw="
|
"integrity": "sha1-BOaSb2YolTVPPdAVIDYzuFcpfiw="
|
||||||
},
|
},
|
||||||
"stream-http": {
|
"stream-http": {
|
||||||
"version": "2.7.2",
|
"version": "2.8.0",
|
||||||
"resolved": "https://registry.npmjs.org/stream-http/-/stream-http-2.7.2.tgz",
|
"resolved": "https://registry.npmjs.org/stream-http/-/stream-http-2.8.0.tgz",
|
||||||
"integrity": "sha512-c0yTD2rbQzXtSsFSVhtpvY/vS6u066PcXOX9kBB3mSO76RiUQzL340uJkGBWnlBg4/HZzqiUXtaVA7wcRcJgEw==",
|
"integrity": "sha512-sZOFxI/5xw058XIRHl4dU3dZ+TTOIGJR78Dvo0oEAejIt4ou27k+3ne1zYmCV+v7UucbxIFQuOgnkTVHh8YPnw==",
|
||||||
"requires": {
|
"requires": {
|
||||||
"builtin-status-codes": "3.0.0",
|
"builtin-status-codes": "3.0.0",
|
||||||
"inherits": "2.0.3",
|
"inherits": "2.0.3",
|
||||||
|
|
@ -312,9 +312,9 @@
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"swagger-ui-dist": {
|
"swagger-ui-dist": {
|
||||||
"version": "3.9.1",
|
"version": "3.9.2",
|
||||||
"resolved": "https://registry.npmjs.org/swagger-ui-dist/-/swagger-ui-dist-3.9.1.tgz",
|
"resolved": "https://registry.npmjs.org/swagger-ui-dist/-/swagger-ui-dist-3.9.2.tgz",
|
||||||
"integrity": "sha1-zLjtVjHJY8Q4jCgFxCg0t69u+eo="
|
"integrity": "sha1-XuK7G2IFPC3ydGnlVZDGX8AOidQ="
|
||||||
},
|
},
|
||||||
"tiny-emitter": {
|
"tiny-emitter": {
|
||||||
"version": "2.0.2",
|
"version": "2.0.2",
|
||||||
|
|
@ -362,16 +362,16 @@
|
||||||
"resolved": "https://registry.npmjs.org/z-schema/-/z-schema-3.19.0.tgz",
|
"resolved": "https://registry.npmjs.org/z-schema/-/z-schema-3.19.0.tgz",
|
||||||
"integrity": "sha512-V94f3ODuluBS4kQLLjNhwoMek0dyIXCsvNu/A17dAyJ6sMhT5KkJQwSn07R0naByLIXJWMDk+ruMfI/3G3hS4Q==",
|
"integrity": "sha512-V94f3ODuluBS4kQLLjNhwoMek0dyIXCsvNu/A17dAyJ6sMhT5KkJQwSn07R0naByLIXJWMDk+ruMfI/3G3hS4Q==",
|
||||||
"requires": {
|
"requires": {
|
||||||
"commander": "2.12.2",
|
"commander": "2.13.0",
|
||||||
"lodash.get": "4.4.2",
|
"lodash.get": "4.4.2",
|
||||||
"lodash.isequal": "4.5.0",
|
"lodash.isequal": "4.5.0",
|
||||||
"validator": "9.2.0"
|
"validator": "9.2.0"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"zone.js": {
|
"zone.js": {
|
||||||
"version": "0.8.18",
|
"version": "0.8.20",
|
||||||
"resolved": "https://registry.npmjs.org/zone.js/-/zone.js-0.8.18.tgz",
|
"resolved": "https://registry.npmjs.org/zone.js/-/zone.js-0.8.20.tgz",
|
||||||
"integrity": "sha512-knKOBQM0oea3/x9pdyDuDi7RhxDlJhOIkeixXSiTKWLgs4LpK37iBc+1HaHwzlciHUKT172CymJFKo8Xgh+44Q=="
|
"integrity": "sha512-FXlA37ErSXCMy5RNBcGFgCI/Zivqzr0D19GuvDxhcYIJc7xkFp6c29DKyODJu0Zo+EMyur/WPPgcBh1EHjB9jA=="
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -1,7 +1,7 @@
|
||||||
{
|
{
|
||||||
"name": "drf-yasg",
|
"name": "drf-yasg",
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"redoc": "^1.19.3",
|
"redoc": "^1.20.0",
|
||||||
"swagger-ui-dist": "^3.9.1"
|
"swagger-ui-dist": "^3.9.2"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -31,6 +31,7 @@ SWAGGER_DEFAULTS = {
|
||||||
'type': 'basic'
|
'type': 'basic'
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
'SECURITY_REQUIREMENTS': None,
|
||||||
'LOGIN_URL': getattr(settings, 'LOGIN_URL', None),
|
'LOGIN_URL': getattr(settings, 'LOGIN_URL', None),
|
||||||
'LOGOUT_URL': getattr(settings, 'LOGOUT_URL', None),
|
'LOGOUT_URL': getattr(settings, 'LOGOUT_URL', None),
|
||||||
'VALIDATOR_URL': '',
|
'VALIDATOR_URL': '',
|
||||||
|
|
|
||||||
|
|
@ -94,7 +94,6 @@ class _OpenAPICodec(object):
|
||||||
:return: swagger spec as dict
|
:return: swagger spec as dict
|
||||||
:rtype: OrderedDict
|
:rtype: OrderedDict
|
||||||
"""
|
"""
|
||||||
swagger.security_definitions = swagger_settings.SECURITY_DEFINITIONS
|
|
||||||
return swagger.as_odict()
|
return swagger.as_odict()
|
||||||
|
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -197,10 +197,16 @@ class OpenAPISchemaGenerator(object):
|
||||||
if url is None and request is not None:
|
if url is None and request is not None:
|
||||||
url = request.build_absolute_uri()
|
url = request.build_absolute_uri()
|
||||||
|
|
||||||
return openapi.Swagger(
|
swagger = openapi.Swagger(
|
||||||
info=self.info, paths=paths,
|
info=self.info, paths=paths,
|
||||||
_url=url, _prefix=prefix, _version=self.version, **dict(components)
|
_url=url, _prefix=prefix, _version=self.version, **dict(components)
|
||||||
)
|
)
|
||||||
|
swagger.security_definitions = swagger_settings.SECURITY_DEFINITIONS
|
||||||
|
security_requirements = swagger_settings.SECURITY_REQUIREMENTS
|
||||||
|
if security_requirements is None:
|
||||||
|
security_requirements = [{security_scheme: [] for security_scheme in swagger_settings.SECURITY_DEFINITIONS}]
|
||||||
|
swagger.security = security_requirements
|
||||||
|
return swagger
|
||||||
|
|
||||||
def create_view(self, callback, method, request=None):
|
def create_view(self, callback, method, request=None):
|
||||||
"""Create a view instance from a view callback as registered in urlpatterns.
|
"""Create a view instance from a view callback as registered in urlpatterns.
|
||||||
|
|
|
||||||
|
|
@ -27,6 +27,8 @@ class SwaggerAutoSchema(ViewInspector):
|
||||||
|
|
||||||
operation_id = self.get_operation_id(operation_keys)
|
operation_id = self.get_operation_id(operation_keys)
|
||||||
description = self.get_description()
|
description = self.get_description()
|
||||||
|
security = self.get_security()
|
||||||
|
assert security is None or isinstance(security, list), "security must be a list of securiy requirement objects"
|
||||||
tags = self.get_tags(operation_keys)
|
tags = self.get_tags(operation_keys)
|
||||||
|
|
||||||
responses = self.get_responses()
|
responses = self.get_responses()
|
||||||
|
|
@ -38,6 +40,7 @@ class SwaggerAutoSchema(ViewInspector):
|
||||||
parameters=parameters,
|
parameters=parameters,
|
||||||
consumes=consumes,
|
consumes=consumes,
|
||||||
tags=tags,
|
tags=tags,
|
||||||
|
security=security
|
||||||
)
|
)
|
||||||
|
|
||||||
def get_request_body_parameters(self, consumes):
|
def get_request_body_parameters(self, consumes):
|
||||||
|
|
@ -286,6 +289,16 @@ class SwaggerAutoSchema(ViewInspector):
|
||||||
description = self._sch.get_description(self.path, self.method)
|
description = self._sch.get_description(self.path, self.method)
|
||||||
return description
|
return description
|
||||||
|
|
||||||
|
def get_security(self):
|
||||||
|
"""Return a list of security requirements for this operation.
|
||||||
|
|
||||||
|
Returning an empty list marks the endpoint as unauthenticated (i.e. removes all accepted
|
||||||
|
authentication schemes). Returning ``None`` will inherit the top-level secuirty requirements.
|
||||||
|
|
||||||
|
:return: security requirements
|
||||||
|
:rtype: list"""
|
||||||
|
return self.overrides.get('security', None)
|
||||||
|
|
||||||
def get_tags(self, operation_keys):
|
def get_tags(self, operation_keys):
|
||||||
"""Get a list of tags for this operation. Tags determine how operations relate with each other, and in the UI
|
"""Get a list of tags for this operation. Tags determine how operations relate with each other, and in the UI
|
||||||
each tag will show as a group containing the operations that use it.
|
each tag will show as a group containing the operations that use it.
|
||||||
|
|
|
||||||
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
|
|
@ -13,8 +13,8 @@ no_body = object()
|
||||||
|
|
||||||
|
|
||||||
def swagger_auto_schema(method=None, methods=None, auto_schema=None, request_body=None, query_serializer=None,
|
def swagger_auto_schema(method=None, methods=None, auto_schema=None, request_body=None, query_serializer=None,
|
||||||
manual_parameters=None, operation_id=None, operation_description=None, responses=None,
|
manual_parameters=None, operation_id=None, operation_description=None, security=None,
|
||||||
field_inspectors=None, filter_inspectors=None, paginator_inspectors=None,
|
responses=None, field_inspectors=None, filter_inspectors=None, paginator_inspectors=None,
|
||||||
**extra_overrides):
|
**extra_overrides):
|
||||||
"""Decorate a view method to customize the :class:`.Operation` object generated from it.
|
"""Decorate a view method to customize the :class:`.Operation` object generated from it.
|
||||||
|
|
||||||
|
|
@ -62,6 +62,9 @@ def swagger_auto_schema(method=None, methods=None, auto_schema=None, request_bod
|
||||||
|
|
||||||
:param str operation_id: operation ID override; the operation ID must be unique accross the whole API
|
:param str operation_id: operation ID override; the operation ID must be unique accross the whole API
|
||||||
:param str operation_description: operation description override
|
:param str operation_description: operation description override
|
||||||
|
:param str security: security requirements override; used to specify which authetication mechanism
|
||||||
|
is requried to call this API; an empty list marks the endpoint as unauthenticated (i.e. removes all accepted
|
||||||
|
authentication schemes), and ``None`` will inherit the top-level secuirty requirements
|
||||||
:param dict[str,(.Schema,.SchemaRef,.Response,str,Serializer)] responses: a dict of documented manual responses
|
:param dict[str,(.Schema,.SchemaRef,.Response,str,Serializer)] responses: a dict of documented manual responses
|
||||||
keyed on response status code. If no success (``2xx``) response is given, one will automatically be
|
keyed on response status code. If no success (``2xx``) response is given, one will automatically be
|
||||||
generated from the request body and http method. If any ``2xx`` response is given the automatic response is
|
generated from the request body and http method. If any ``2xx`` response is given the automatic response is
|
||||||
|
|
@ -94,6 +97,7 @@ def swagger_auto_schema(method=None, methods=None, auto_schema=None, request_bod
|
||||||
'manual_parameters': manual_parameters,
|
'manual_parameters': manual_parameters,
|
||||||
'operation_id': operation_id,
|
'operation_id': operation_id,
|
||||||
'operation_description': operation_description,
|
'operation_description': operation_description,
|
||||||
|
'security': security,
|
||||||
'responses': responses,
|
'responses': responses,
|
||||||
'filter_inspectors': list(filter_inspectors) if filter_inspectors else None,
|
'filter_inspectors': list(filter_inspectors) if filter_inspectors else None,
|
||||||
'paginator_inspectors': list(paginator_inspectors) if paginator_inspectors else None,
|
'paginator_inspectors': list(paginator_inspectors) if paginator_inspectors else None,
|
||||||
|
|
|
||||||
|
|
@ -19,13 +19,17 @@ class UserList(APIView):
|
||||||
serializer = UserSerializerrr(queryset, many=True)
|
serializer = UserSerializerrr(queryset, many=True)
|
||||||
return Response(serializer.data)
|
return Response(serializer.data)
|
||||||
|
|
||||||
@swagger_auto_schema(operation_description="apiview post description override", request_body=openapi.Schema(
|
@swagger_auto_schema(
|
||||||
type=openapi.TYPE_OBJECT,
|
operation_description="apiview post description override",
|
||||||
required=['username'],
|
request_body=openapi.Schema(
|
||||||
properties={
|
type=openapi.TYPE_OBJECT,
|
||||||
'username': openapi.Schema(type=openapi.TYPE_STRING)
|
required=['username'],
|
||||||
},
|
properties={
|
||||||
))
|
'username': openapi.Schema(type=openapi.TYPE_STRING)
|
||||||
|
},
|
||||||
|
),
|
||||||
|
security=[]
|
||||||
|
)
|
||||||
def post(self, request):
|
def post(self, request):
|
||||||
serializer = UserSerializerrr(request.data)
|
serializer = UserSerializerrr(request.data)
|
||||||
serializer.is_valid(raise_exception=True)
|
serializer.is_valid(raise_exception=True)
|
||||||
|
|
|
||||||
|
|
@ -412,6 +412,7 @@ paths:
|
||||||
- application/json
|
- application/json
|
||||||
tags:
|
tags:
|
||||||
- users
|
- users
|
||||||
|
security: []
|
||||||
patch:
|
patch:
|
||||||
operationId: users_dummy
|
operationId: users_dummy
|
||||||
description: dummy operation
|
description: dummy operation
|
||||||
|
|
@ -1123,3 +1124,5 @@ definitions:
|
||||||
securityDefinitions:
|
securityDefinitions:
|
||||||
basic:
|
basic:
|
||||||
type: basic
|
type: basic
|
||||||
|
security:
|
||||||
|
- basic: []
|
||||||
|
|
|
||||||
|
|
@ -67,3 +67,15 @@ def test_no_netloc(mock_schema_request):
|
||||||
swagger = generator.get_schema(mock_schema_request, public=True)
|
swagger = generator.get_schema(mock_schema_request, public=True)
|
||||||
assert 'host' not in swagger and 'schemes' not in swagger
|
assert 'host' not in swagger and 'schemes' not in swagger
|
||||||
assert swagger['info']['version'] == 'v2'
|
assert swagger['info']['version'] == 'v2'
|
||||||
|
|
||||||
|
|
||||||
|
def test_securiy_requirements(swagger_settings, mock_schema_request):
|
||||||
|
generator = OpenAPISchemaGenerator(
|
||||||
|
info=openapi.Info(title="Test generator", default_version="v1"),
|
||||||
|
version="v2",
|
||||||
|
url='',
|
||||||
|
)
|
||||||
|
swagger_settings['SECURITY_REQUIREMENTS'] = []
|
||||||
|
|
||||||
|
swagger = generator.get_schema(mock_schema_request, public=True)
|
||||||
|
assert swagger['security'] == []
|
||||||
|
|
|
||||||
|
|
@ -1,10 +1,8 @@
|
||||||
#!/bin/bash
|
#!/bin/bash
|
||||||
set -ev
|
set -ev
|
||||||
npm update
|
npm update
|
||||||
npm install -g --prefix ./node_modules/redoc-alpha redoc@latest
|
|
||||||
|
|
||||||
cp node_modules/redoc/dist/redoc.min.js src/drf_yasg/static/drf-yasg/redoc/
|
cp node_modules/redoc/dist/redoc.min.js src/drf_yasg/static/drf-yasg/redoc/
|
||||||
cp node_modules/redoc-alpha/node_modules/redoc/bundles/redoc.standalone.js src/drf_yasg/static/drf-yasg/redoc-alpha/
|
|
||||||
cp -r node_modules/swagger-ui-dist src/drf_yasg/static/drf-yasg/
|
cp -r node_modules/swagger-ui-dist src/drf_yasg/static/drf-yasg/
|
||||||
pushd src/drf_yasg/static/drf-yasg/swagger-ui-dist/ >/dev/null
|
pushd src/drf_yasg/static/drf-yasg/swagger-ui-dist/ >/dev/null
|
||||||
rm -f package.json .npmignore README.md
|
rm -f package.json .npmignore README.md
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue