Skip to content

Bug: ERROR Exception inside application: __provides__ #1296

@deirdreamuel

Description

@deirdreamuel

Describe the bug
There is an issue with drf_spectacular's @extend_schema_view that is only happening in production server i.e. Daphne, Gunicorn, Uvicorn. This issue does not happen with python manage.py runserver. The server does start up with daphne after removing all @extend_schema_view decorators.

Sample logs using Daphne:


2024-09-18 03:38:47,738 ERROR    Exception inside application: __provides__
Traceback (most recent call last):
File "/usr/local/lib/python3.12/site-packages/asgiref/sync.py", line 518, in thread_handler
raise exc_info[1]
File "/usr/local/lib/python3.12/site-packages/django/core/handlers/exception.py", line 42, in inner
response = await get_response(request)
^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/usr/local/lib/python3.12/site-packages/django/core/handlers/base.py", line 235, in _get_response_async
callback, callback_args, callback_kwargs = self.resolve_request(request)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/usr/local/lib/python3.12/site-packages/django/core/handlers/base.py", line 313, in resolve_request
resolver_match = resolver.resolve(request.path_info)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/usr/local/lib/python3.12/site-packages/django/urls/resolvers.py", line 686, in resolve
for pattern in self.url_patterns:
^^^^^^^^^^^^^^^^^
File "/usr/local/lib/python3.12/site-packages/django/utils/functional.py", line 47, in __get__
res = instance.__dict__[self.name] = self.func(instance)
^^^^^^^^^^^^^^^^^^^
File "/usr/local/lib/python3.12/site-packages/django/urls/resolvers.py", line 738, in url_patterns
patterns = getattr(self.urlconf_module, "urlpatterns", self.urlconf_module)
^^^^^^^^^^^^^^^^^^^
File "/usr/local/lib/python3.12/site-packages/django/utils/functional.py", line 47, in __get__
res = instance.__dict__[self.name] = self.func(instance)
^^^^^^^^^^^^^^^^^^^
File "/usr/local/lib/python3.12/site-packages/django/urls/resolvers.py", line 731, in urlconf_module
return import_module(self.urlconf_name)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/usr/local/lib/python3.12/importlib/__init__.py", line 90, in import_module
return _bootstrap._gcd_import(name[level:], package, level)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "<frozen importlib._bootstrap>", line 1387, in _gcd_import
File "<frozen importlib._bootstrap>", line 1360, in _find_and_load
File "<frozen importlib._bootstrap>", line 1331, in _find_and_load_unlocked
File "<frozen importlib._bootstrap>", line 935, in _load_unlocked
File "<frozen importlib._bootstrap_external>", line 995, in exec_module
File "<frozen importlib._bootstrap>", line 488, in _call_with_frames_removed
File "/usr/src/api_server/app/urls.py", line 14, in <module>
path("v1.0/", include("core.urls")),
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/usr/local/lib/python3.12/site-packages/django/urls/conf.py", line 39, in include
urlconf_module = import_module(urlconf_module)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/usr/local/lib/python3.12/importlib/__init__.py", line 90, in import_module
return _bootstrap._gcd_import(name[level:], package, level)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "<frozen importlib._bootstrap>", line 1387, in _gcd_import
File "<frozen importlib._bootstrap>", line 1360, in _find_and_load
File "<frozen importlib._bootstrap>", line 1331, in _find_and_load_unlocked
File "<frozen importlib._bootstrap>", line 935, in _load_unlocked
File "<frozen importlib._bootstrap_external>", line 995, in exec_module
File "<frozen importlib._bootstrap>", line 488, in _call_with_frames_removed
File "/usr/src/api_server/core/urls/__init__.py", line 3, in <module>
from core.urls import (
File "/usr/src/api_server/core/urls/organization.py", line 3, in <module>
from core.views import organization
File "/usr/src/api_server/core/views/organization.py", line 17, in <module>
@extend_schema_view(
^^^^^^^^^^^^^^^^^^^
File "/usr/local/lib/python3.12/site-packages/drf_spectacular/utils.py", line 658, in decorator
available_view_methods = get_view_method_names(view)
^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/usr/local/lib/python3.12/site-packages/drf_spectacular/drainage.py", line 183, in get_view_method_names
item for item in dir(view) if callable(getattr(view, item)) and (
^^^^^^^^^^^^^^^^^^^
AttributeError: __provides__. Did you mean: '__providedBy__'?
During handling of the above exception, another exception occurred:
Traceback (most recent call last):
File "/usr/local/lib/python3.12/site-packages/asgiref/sync.py", line 518, in thread_handler
raise exc_info[1]
File "/usr/local/lib/python3.12/site-packages/django/core/handlers/exception.py", line 42, in inner
response = await get_response(request)
^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/usr/local/lib/python3.12/site-packages/django/utils/deprecation.py", line 150, in __acall__
response = response or await self.get_response(request)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/usr/local/lib/python3.12/site-packages/django/core/handlers/exception.py", line 44, in inner
response = await sync_to_async(
^^^^^^^^^^^^^^^^^^^^
File "/usr/local/lib/python3.12/site-packages/asgiref/sync.py", line 468, in __call__
ret = await asyncio.shield(exec_coro)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/usr/local/lib/python3.12/concurrent/futures/thread.py", line 58, in run
result = self.fn(*self.args, **self.kwargs)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/usr/local/lib/python3.12/site-packages/asgiref/sync.py", line 520, in thread_handler
return func(*args, **kwargs)
^^^^^^^^^^^^^^^^^^^^^
File "/usr/local/lib/python3.12/site-packages/django/core/handlers/exception.py", line 140, in response_for_exception
response = handle_uncaught_exception(
^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/usr/local/lib/python3.12/site-packages/django/core/handlers/exception.py", line 184, in handle_uncaught_exception
callback = resolver.resolve_error_handler(500)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/usr/local/lib/python3.12/site-packages/django/urls/resolvers.py", line 752, in resolve_error_handler
callback = getattr(self.urlconf_module, "handler%s" % view_type, None)
^^^^^^^^^^^^^^^^^^^
File "/usr/local/lib/python3.12/site-packages/django/utils/functional.py", line 47, in __get__
res = instance.__dict__[self.name] = self.func(instance)
^^^^^^^^^^^^^^^^^^^
File "/usr/local/lib/python3.12/site-packages/django/urls/resolvers.py", line 731, in urlconf_module
return import_module(self.urlconf_name)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/usr/local/lib/python3.12/importlib/__init__.py", line 90, in import_module
return _bootstrap._gcd_import(name[level:], package, level)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "<frozen importlib._bootstrap>", line 1387, in _gcd_import
File "<frozen importlib._bootstrap>", line 1360, in _find_and_load
File "<frozen importlib._bootstrap>", line 1331, in _find_and_load_unlocked
File "<frozen importlib._bootstrap>", line 935, in _load_unlocked
File "<frozen importlib._bootstrap_external>", line 995, in exec_module
File "<frozen importlib._bootstrap>", line 488, in _call_with_frames_removed
File "/usr/src/api_server/app/urls.py", line 14, in <module>
path("v1.0/", include("core.urls")),
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/usr/local/lib/python3.12/site-packages/django/urls/conf.py", line 39, in include
urlconf_module = import_module(urlconf_module)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/usr/local/lib/python3.12/importlib/__init__.py", line 90, in import_module
return _bootstrap._gcd_import(name[level:], package, level)
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "<frozen importlib._bootstrap>", line 1387, in _gcd_import
File "<frozen importlib._bootstrap>", line 1360, in _find_and_load
File "<frozen importlib._bootstrap>", line 1331, in _find_and_load_unlocked
File "<frozen importlib._bootstrap>", line 935, in _load_unlocked
File "<frozen importlib._bootstrap_external>", line 995, in exec_module
File "<frozen importlib._bootstrap>", line 488, in _call_with_frames_removed
File "/usr/src/api_server/core/urls/__init__.py", line 3, in <module>
from core.urls import (
File "/usr/src/api_server/core/urls/organization.py", line 3, in <module>
from core.views import organization
File "/usr/src/api_server/core/views/organization.py", line 17, in <module>
@extend_schema_view(
^^^^^^^^^^^^^^^^^^^
File "/usr/local/lib/python3.12/site-packages/drf_spectacular/utils.py", line 658, in decorator
available_view_methods = get_view_method_names(view)
^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/usr/local/lib/python3.12/site-packages/drf_spectacular/drainage.py", line 183, in get_view_method_names
item for item in dir(view) if callable(getattr(view, item)) and (
^^^^^^^^^^^^^^^^^^^
AttributeError: __provides__. Did you mean: '__providedBy__'?

To Reproduce
I have something sort of the following for different views under /views dir.

@extend_schema_view(
    list=extend_schema(
        tags=["Task Action"],
        operation_id="Task Action List",
        description="Retrieves a list of all task actions that can be applied.",
    ),
    retrieve=extend_schema(
        tags=["Task Action"],
        operation_id="Task Action Retrieve",
        description="Retrieves a task action data by Public ID.",
    ),
)

Expected behavior
The application should work and start without problems the same way it starts with python manage.py runserver

Metadata

Metadata

Assignees

No one assigned

    Labels

    enhancementNew feature or requestfix confirmation pendingissue has been fixed and confirmation from issue reporter is pending

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions