Skip to content

[BUG] CBV interaction with url_for #133

Description

@dp-rufus

I've just run into this issue in the wild. It's not a bug as such, but perhaps there's a way to prevent it catching people out like it did me?

Consider this example:

fromfastapiimportAPIRouter, FastAPI, Requestfromfastapi_utils.cbvimportcbvrouter=APIRouter()
@cbv(router)classFoo:
@router.get("/foo")asyncdefexample(self, request: Request):
returnrequest.url_for("example")
@cbv(router)classBar:
@router.get("/bar")asyncdefexample(self, request: Request):
returnrequest.url_for("example")
app=FastAPI()
app.include_router(router)

Both of the url_for("example") calls return "/foo", whereas the expected behaviour might be for the second one to return "/bar" instead.

Without CBVs, IDEs and linters would warn about the function example being redefined, but it obviously doesn't when they're in two different classes. So the problem goes unnoticed until runtime, at which point the 'wrong' path is used.

If we made a change like this to cbv.py...

forrouteincbv_routes:
router.routes.remove(route)
_update_cbv_route_endpoint_signature(cls, route)
route.name=cls.__name__+'.'+route.name# <-------------- this line is newcbv_router.routes.append(route)
router.include_router(cbv_router)
returncls

...then we could do url_for("Foo.example") or url_for("Bar.example").

However:

  • It would need to be backwards compatible, although I don't see any immediate problem with inserting the same route twice with two different names
  • It wouldn't stop the problem happening if two different modules both had CBVs with the same name, each containing a method with the same name
  • It wouldn't play nicely with from x import Y as Z, if this matters - it would still use the name Y.whatever

Do you think this is worth addressing somehow? Thanks!

Metadata

Metadata

Assignees

No one assigned

    Labels

    bugSomething isn't working

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions