Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Ability to customize SCHEMA_PATH_PREFIX per schema instance #365

Closed
jalaziz opened this issue Apr 14, 2021 · 6 comments
Closed

Ability to customize SCHEMA_PATH_PREFIX per schema instance #365

jalaziz opened this issue Apr 14, 2021 · 6 comments

Comments

@jalaziz
Copy link
Contributor

jalaziz commented Apr 14, 2021

Today, SCHEMA_PATH_PREFIX is a global setting that applies to all instances of the schema view.

This behavior can be pretty limiting when using custom urlconfs with SpectacularAPIView.

For example, let's say we have the following urls:

/v1/serviceA/foo
/v1/serviceA/bar
/v1/serviceB/foo
/v1/serviceB/bar
/v2/serviceC/foo

In this case, a custom DRF versioning class is being used, so we can essentially ignore the version prefix.

If we then introduce three schema views to offer different groupings, such as:

/schema                  ->  All service endpoints
/v1/serviceA/schema  ->  Just service A endpoints
/v1/serviceB/schema  ->  Just service B endpoints

It becomes nearly impossible to have sensible groupings in the swagger UI.

If we use the default behavior, /schema will have /v1 and /v2 groups. While the other two endpoints will be grouped sensibly.

If we specify SCHEMA_PATH_PREFIX to be /v\d+/, then /schema would be grouped sensibly, but the other two endpoints would have a single group each.

Being able to pass the path prefix individually to SpectacularAPIView.as_view would solve this problem and allow full control over groupings when exposing subpath schemas.

@tfranzel
Copy link
Owner

hi @jalaziz, sry for the delayed response. as you correctly noted, the settings are global and initially i did not anticipate that settings may vary like that. this seems like a reasonable (even though not that common) thing to ask.

i have been thinking about a way to address your and previously raised related issues. just so you know it is being worked on.

@axieum
Copy link

axieum commented Aug 10, 2021

Any update on this? I think a more flexible addition would be to add the SPECTACULAR_SETTINGS config dict as an argument to the SpectacularAPIView and the like. For example:

SpectacularAPIView.as_view(conf=settings.SPECTACULAR_SETTINGS)

In my scenario, I have a Django project which houses a collection of Django apps. Each app within the project should maintain its own API version and hence schema, e.g. /api/my-app/v1/schema and /api/other-app/v2/schema. I worked around this, by assigning a SCHEMA_PATH_PREFIX of..

^/api/(?P<app>[^/]+)(?:/(?P<version>v\d+))?

..and SCHEMA_PATH_PREFIX_TRIM = True. Then using a post-processing hook, to filter the app namespace and manipulate the resulting schema:

def postprocess_schema_metadata(
    result: dict, generator: "SchemaGenerator", request: Request, public: bool
) -> dict:
    """A DRF Spectacular postprocessing hook that sets metadata per namespaced app"""

    # Find all namespaces this request relates to
    namespaces: List[str] = request.resolver_match.namespaces

    # Determine which schema metadata to use for each detected app
    metadata: Optional[dict] = None
    servers: Optional[dict] = None
    if "my-app" in namespaces:
        metadata = settings.MY_APP_SPECTACULAR_METADATA
        servers = settings.MY_APP_SPECTACULAR_SERVERS
    elif "other-app" in namespaces:
        pass

    # Adjust the schema to fit
    if metadata:
        result["info"].update(metadata)
    if servers:
        result["servers"] = servers

    return result

This may or may not work for everyone's use-case so adjust where you see fit.

@gabbork
Copy link

gabbork commented Dec 16, 2021

Hi, any news on this? Thanks

@niccolomineo
Copy link

Hi @tfranzel, do you foresee to add this kind of flexibility in the near future? Having to work around this is quite limiting at the moment.

@tfranzel
Copy link
Owner

due to popular demand I had a look. the settings were never designed to be scoped and that makes this a bit tricky.

I believe this PR should do the trick without refactoring the whole codebase. One caveat would be that it is currently not thread-safe, but we do not make guarantees there anyway.

please test & review: #615

@jalaziz
Copy link
Contributor Author

jalaziz commented Dec 28, 2021

I tested the latest release and I can indeed customize SCHEMA_PATH_PREFIX on a per instance basis now, thank you!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

5 participants