fastapi/flask/nodejs 中查询参数的方括号

Square bracket along query params in fastapi/flask/nodejs

如果这是一个重复的问题,我很抱歉,但除了这个网站,我几乎看不到它。本网站最初帮助人们通过 REST API 在 Google Sheet 中进行查询。他们的链接如下所示:

spreadsheetID/sheetName?filter[ColumnName]=aiman

我只是想知道如何在 FastAPI 中做到这一点,尤其是对于参数 filter[columnName]。 columnName 也是一个根据列名的变量。我已经读过 this 但不太明白。我也欣赏任何语言。

FastAPI 中没有内置任何东西来实现这一点,但我们可以编写它! 我们需要解析参数的函数:

import re

def parse_param(param, value):
    regex = r"(?P<op>.*)\[(?P<col>.*)\]"
    if m := re.search(r, param):
        return {"op": m.group("op"), "col": m.group("col"), "val": value}
    return {param: value}

现在是时候使用它了,最简单的方法是使用底层 Starlete 请求并解析 url

from fastapi import Request

@app.get("/sheetName")
def endpoint(r: Request):
    k, v = next(iter(r.query_params.items())) # Assuming there is only one parameter
    print(parse_param(k, v))

如果你想要一些 FastAPI 魔法,你还有另外两个选择

  1. The middleware
@app.middleware("http")
async def preprocess(request: Request, call_next):
    k, v = next(iter(request.query_params.items()))
    request._query_params = QueryParams(parse_param(k, v))
    request.scope["query_string"] = str(request._query_params).encode("ascii")
    response = await call_next(request)
    return response
  1. Custom request
from fastapi.routing import APIRoute
from starlette.datastructures import QueryParams

class BracketRequest(Request):
    @property
    def query_params(self):
        k, v = next(iter(super().query_params.items()))
        return QueryParams(parse_param(k, v))


class BracketRoute(APIRoute):
    def get_route_handler(self):
        original_route_handler = super().get_route_handler()

        async def custom_route_handler(request: Request):
            request = BracketRequest(request.scope, request.receive)
            return await original_route_handler(request)

        return custom_route_handler

app.router.route_class = BracketRoute

第二种解决方案允许您仅为特定路由器分配此类逻辑。 在这两种情况下,您现在都可以在 FastAPI 验证的帮助下使用您的端点:

@app.get("/sheetName")
def endpoint(op: str, col: str, val: Any):
    print(op, col, val)

这种方法有局限性(比如如果可以有更多的参数怎么办?或者更多带括号的参数?),具体的解决方案取决于具体的需求,但它们应该让你有足够的洞察力来解决这些问题。