Project

Profile

Help

Story #6714

[EPIC] drf builtin manage.py 'generateschema' command fails on pulp base viewsets

Added by alikins 4 months ago. Updated 4 months ago.

Status:
NEW
Priority:
Normal
Assignee:
-
Category:
-
Sprint/Milestone:
-
Start date:
Due date:
% Done:

0%

Estimated time:
Platform Release:
Groomed:
No
Sprint Candidate:
No
Tags:
Sprint:
Quarter:

Description

Attempting to use DRF's builtin openapi schema generation tool fails in the base viewsets get_serializer_class().

The get_serializer_class() expects a self.request to exist, but it is None as run by the 'generateschema' command.

(.venv) [newswoop:F31:galaxy_ng (sync_model_46 %)]$ ./compose run --rm api manage generateschema Compose Profile alikins Starting galaxy_ng_redis_1 ... Starting galaxy_ng_redis_1 ... done Installing path django-extensions in editable mode. Installing path alogging in editable mode. Installing path galaxy_ng in editable mode. Installing path pulp_ansible in editable mode. Installing path pulpcore in editable mode. Traceback (most recent call last): File "/venv/bin/django-admin", line 8, in sys.exit(execute_from_command_line()) File "/venv/lib64/python3.6/site-packages/django/core/management/init.py", line 381, in execute_from_command_line utility.execute() File "/venv/lib64/python3.6/site-packages/django/core/management/init.py", line 375, in execute self.fetch_command(subcommand).run_from_argv(self.argv) File "/venv/lib64/python3.6/site-packages/django/core/management/base.py", line 323, in run_from_argv self.execute(*args, **cmd_options) File "/venv/lib64/python3.6/site-packages/django/core/management/base.py", line 364, in execute output = self.handle(*args, **options) File "/venv/lib64/python3.6/site-packages/rest_framework/management/commands/generateschema.py", line 40, in handle schema = generator.get_schema(request=None, public=True) File "/venv/lib64/python3.6/site-packages/rest_framework/schemas/openapi.py", line 64, in get_schema paths = self.get_paths(None if public else request) File "/venv/lib64/python3.6/site-packages/rest_framework/schemas/openapi.py", line 47, in get_paths operation = view.schema.get_operation(path, method) File "/venv/lib64/python3.6/site-packages/rest_framework/schemas/openapi.py", line 104, in get_operation operation['responses'] = self._get_responses(path, method) File "/venv/lib64/python3.6/site-packages/rest_framework/schemas/openapi.py", line 489, in _get_responses serializer = self._get_serializer(path, method) File "/venv/lib64/python3.6/site-packages/rest_framework/schemas/openapi.py", line 446, in _get_serializer return view.get_serializer() File "/venv/lib64/python3.6/site-packages/rest_framework/generics.py", line 108, in get_serializer serializer_class = self.get_serializer_class() File "/src/pulpcore/pulpcore/app/viewsets/task.py", line 86, in get_serializer_class return super().get_serializer_class() File "/src/pulpcore/pulpcore/app/viewsets/base.py", line 105, in get_serializer_class if 'minimal' in self.request.query_params: AttributeError: 'NoneType' object has no attribute 'query_params'

History

#1 Updated by alikins 4 months ago

Better formatted stacktrace:

(.venv) [newswoop:F31:galaxy_ng (sync_model_46 %)]$ ./compose run --rm api manage generateschema
Compose Profile alikins
Starting galaxy_ng_redis_1    ... 
Starting galaxy_ng_redis_1    ... done
Installing path django-extensions in editable mode.
Installing path alogging in editable mode.
Installing path galaxy_ng in editable mode.
Installing path pulp_ansible in editable mode.
Installing path pulpcore in editable mode.
Traceback (most recent call last):
  File "/venv/bin/django-admin", line 8, in <module>
    sys.exit(execute_from_command_line())
  File "/venv/lib64/python3.6/site-packages/django/core/management/__init__.py", line 381, in execute_from_command_line
    utility.execute()
  File "/venv/lib64/python3.6/site-packages/django/core/management/__init__.py", line 375, in execute
    self.fetch_command(subcommand).run_from_argv(self.argv)
  File "/venv/lib64/python3.6/site-packages/django/core/management/base.py", line 323, in run_from_argv
    self.execute(*args, **cmd_options)
  File "/venv/lib64/python3.6/site-packages/django/core/management/base.py", line 364, in execute
    output = self.handle(*args, **options)
  File "/venv/lib64/python3.6/site-packages/rest_framework/management/commands/generateschema.py", line 40, in handle
    schema = generator.get_schema(request=None, public=True)
  File "/venv/lib64/python3.6/site-packages/rest_framework/schemas/openapi.py", line 64, in get_schema
    paths = self.get_paths(None if public else request)
  File "/venv/lib64/python3.6/site-packages/rest_framework/schemas/openapi.py", line 47, in get_paths
    operation = view.schema.get_operation(path, method)
  File "/venv/lib64/python3.6/site-packages/rest_framework/schemas/openapi.py", line 104, in get_operation
    operation['responses'] = self._get_responses(path, method)
  File "/venv/lib64/python3.6/site-packages/rest_framework/schemas/openapi.py", line 489, in _get_responses
    serializer = self._get_serializer(path, method)
  File "/venv/lib64/python3.6/site-packages/rest_framework/schemas/openapi.py", line 446, in _get_serializer
    return view.get_serializer()
  File "/venv/lib64/python3.6/site-packages/rest_framework/generics.py", line 108, in get_serializer
    serializer_class = self.get_serializer_class()
  File "/src/pulpcore/pulpcore/app/viewsets/task.py", line 86, in get_serializer_class
    return super().get_serializer_class()
  File "/src/pulpcore/pulpcore/app/viewsets/base.py", line 105, in get_serializer_class
    if 'minimal' in self.request.query_params:
AttributeError: 'NoneType' object has no attribute 'query_params'

#2 Updated by dkliban@redhat.com 4 months ago

What are you trying to achieve by using this command? I don't understand the use case.

#3 Updated by alikins 4 months ago

'django-manage generatescheme' is a django-rest-framework command that can be used to generate openapi v3 schema using drf's builtin introspect.

Nothing requires it at the moment, but it appears to be the way to automatically generate openapi schema for drf apps in the future since:

  • drf_yasg is somewhat maintained, but isn't actively planning on support the openapi v3 spec

  • drf claims it should be the main way to generate openapi v3 schema

At the moment, drf's 'generateschema' doesn't work at all because of the AttributeError mentioned above.

A fix like:

diff --git pulpcore/app/viewsets/base.py pulpcore/app/viewsets/base.py
index 213cea655..11272e63b 100644
--- pulpcore/app/viewsets/base.py
+++ pulpcore/app/viewsets/base.py
@@ -130,7 +130,7 @@ def get_serializer_class(self):
         minimal_serializer_class = getattr(self, "minimal_serializer_class", None)
 
         if minimal_serializer_class:
-            if hasattr(self, "request"):
+            if hasattr(self, "request") and getattr(self, "request", None):
                 if "minimal" in self.request.query_params:
                     # the query param is a string, and non-empty strings evaluate True,
                     # so we need to do an actual string comparison to 'true'

Is enough for 'generateschema' to run without fatal error. So a step to supporting 'generateschema' and openapi v3.

Caveat: The schema generated by 'generateschema' for pulpcore is currently not very good, and misses some of the stuff the customized drf_yasg schema generation supports. So not really practical at the moment.

#4 Updated by fao89 4 months ago

  • Tracker changed from Issue to Story
  • Subject changed from drf builtin manage.py 'generateschema' command fails on pulp base viewsets to [EPIC] drf builtin manage.py 'generateschema' command fails on pulp base viewsets
  • % Done set to 0

#5 Updated by fao89 4 months ago

I did a PoC on using openapi schema from DRF a while ago, and it felt like their schema generation was not mature yet, for example, they always return 200 on responses: https://github.com/encode/django-rest-framework/blob/3.11.0/rest_framework/schemas/openapi.py#L543-L554 here is the PoC: https://github.com/pulp/pulpcore/compare/master...fao89:openapi3

Please register to edit this issue

Also available in: Atom PDF