def get_schema_operation_parameters(self, auto_schema, *args, **kwargs): model = get_view_model(auto_schema.view) if not model: return [] filterset_class = self.target.get_filterset_class( auto_schema.view, model.objects.none()) if not filterset_class: return [] result = [] with add_trace_message(filterset_class.__name__): for field_name, filter_field in filterset_class.base_filters.items( ): result += self.resolve_filter_field(auto_schema, model, filterset_class, field_name, filter_field) return result
def parse(self, input_request, public): """ Iterate endpoints generating per method path operations. """ result = {} self._initialise_endpoints() endpoints = self._get_paths_and_endpoints( None if public else input_request) if spectacular_settings.SCHEMA_PATH_PREFIX is None: # estimate common path prefix if none was given. only use it if we encountered more # than one view to prevent emission of erroneous and unnecessary fallback names. non_trivial_prefix = len( set([view.__class__ for _, _, _, view in endpoints])) > 1 if non_trivial_prefix: path_prefix = os.path.commonpath( [path for path, _, _, _ in endpoints]) else: path_prefix = '/' else: path_prefix = spectacular_settings.SCHEMA_PATH_PREFIX if not path_prefix.startswith('^'): path_prefix = '^' + path_prefix # make sure regex only matches from the start for path, path_regex, method, view in endpoints: if not self.has_view_permissions(path, method, view): continue if input_request: request = input_request else: # mocked request to allow certain operations in get_queryset and get_serializer[_class] # without exceptions being raised due to no request. request = spectacular_settings.GET_MOCK_REQUEST( method, path, view, input_request) view.request = request if view.versioning_class and not is_versioning_supported( view.versioning_class): warn( f'using unsupported versioning class "{view.versioning_class}". view will be ' f'processed as unversioned view.') elif view.versioning_class: version = ( self.api_version # generator was explicitly versioned or getattr(request, 'version', None) # incoming request was versioned or view.versioning_class.default_version # fallback ) if not version: continue path = modify_for_versioning(self.inspector.patterns, method, path, view, version) if not operation_matches_version(view, version): continue assert isinstance(view.schema, AutoSchema), ( f'Incompatible AutoSchema used on View {view.__class__}. Is DRF\'s ' f'DEFAULT_SCHEMA_CLASS pointing to "drf_spectacular.openapi.AutoSchema" ' f'or any other drf-spectacular compatible AutoSchema?') with add_trace_message(getattr(view, '__class__', view).__name__): operation = view.schema.get_operation(path, path_regex, path_prefix, method, self.registry) # operation was manually removed via @extend_schema if not operation: continue if spectacular_settings.SCHEMA_PATH_PREFIX_TRIM: path = re.sub(pattern=path_prefix, repl='', string=path, flags=re.IGNORECASE) if not path.startswith('/'): path = '/' + path if spectacular_settings.CAMELIZE_NAMES: path, operation = camelize_operation(path, operation) result.setdefault(path, {}) result[path][method.lower()] = operation return result
def parse(self, input_request, public): """ Iterate endpoints generating per method path operations. """ result = {} self._initialise_endpoints() for path, path_regex, method, view in self._get_paths_and_endpoints( None if public else input_request): if not self.has_view_permissions(path, method, view): continue if input_request: request = input_request else: # mocked request to allow certain operations in get_queryset and get_serializer[_class] # without exceptions being raised due to no request. request = spectacular_settings.GET_MOCK_REQUEST( method, path, view, input_request) view.request = request if view.versioning_class and not is_versioning_supported( view.versioning_class): warn( f'using unsupported versioning class "{view.versioning_class}". view will be ' f'processed as unversioned view.') elif view.versioning_class: version = ( self.api_version # generator was explicitly versioned or getattr(request, 'version', None) # incoming request was versioned or view.versioning_class.default_version # fallback ) if not version: continue path = modify_for_versioning(self.inspector.patterns, method, path, view, version) if not operation_matches_version(view, version): continue assert isinstance(view.schema, AutoSchema), ( f'Incompatible AutoSchema used on View {view.__class__}. Is DRF\'s ' f'DEFAULT_SCHEMA_CLASS pointing to "drf_spectacular.openapi.AutoSchema" ' f'or any other drf-spectacular compatible AutoSchema?') if hasattr(view, '__class__'): trace_message = view.__class__.__name__ elif hasattr(view, '__name__'): trace_message = view.__name__ else: trace_message = None with add_trace_message(trace_message): operation = view.schema.get_operation(path, path_regex, method, self.registry) # operation was manually removed via @extend_schema if not operation: continue # Normalise path for any provided mount url. if path.startswith('/'): path = path[1:] path = urljoin(self.url or '/', path) if spectacular_settings.CAMELIZE_NAMES: path, operation = camelize_operation(path, operation) result.setdefault(path, {}) result[path][method.lower()] = operation return result