FastApi and VueJS routing

I started building a hobby project with FastApi backend and VueJS frontend. The frontend should be served with the uvicorn service of the backend. But how to allow the vuejs-router to be used.

My solution for the moment is to use the 404-handler of FastApi to route all 404s to VueJS and let the vuejs-router handle the remaining requests.

The frontend is build this way:

vite build --outDir ../app/dist --emptyOutDir

The outDir is in the the FastApi app folder, is mounted as StaticFolder and in the 404-handler.

A minimal working main.py example:

from pathlib import Path

from fastapi import FastAPI, Request
from fastapi.exceptions import HTTPException
from fastapi.responses import HTMLResponse
from fastapi.staticfiles import StaticFiles

app = FastAPI()

@app.get("/ping")
async def ping():
    return "pong"

@app.exception_handler(404)
async def redirect_all_requests_to_frontend(request: Request, exc: HTTPException):
    return HTMLResponse(open(Path(__file__).parent / "dist/index.html").read())

app.mount(
    "/assets",
    StaticFiles(directory=Path(__file__).parent / "dist/assets"),
    name="assets",
)

All routes of the FastApi app have precedence, everything else is handled by the 404-handler and routed to the VueJS app. Real 404s should be handled within the vuejs-router. For example like this:

{
  path: '/:catchAll(.*)',
  component: () => import('./components/notfound.vue')
}

The order in the vuejs-router matters, so putting the notfound route at the end should do the trick.