Skip to content

Conversation

@YuriiMotov
Copy link
Member

@YuriiMotov YuriiMotov commented Nov 16, 2025

Currently if we declare Query or Header parameters as model with extra="allow" and then pass extra parameter with multiple values, only last value of such parameter will be passed to model validator:

from fastapi import FastAPI, Query
from fastapi.testclient import TestClient
from pydantic import BaseModel

app = FastAPI()


class Model(BaseModel):
    param: str

    model_config = {"extra": "allow"}


@app.get("/")
async def model_with_extra(data: Model = Query()):
    return data


def test_pass_extra_list():
    client = TestClient(app)
    resp = client.get(
        "/",
        params={
            "param": "123",
            "param2": ["456", "789"],  # Pass a list of values as extra parameter
        },
    )
    assert resp.status_code == 200
    assert resp.json() == {
        "param": "123",
        "param2": ["456", "789"],
    }

# AssertionError: assert
# {'param': '123', 'param2': '789'} == {'param': '123', 'param2': ['456', '789']}

The reason is the same as with Form parameters. See #14303
There is also a note about implementation described in #14303. It's also relevant to this PR.

As for Cookies:
As far as I understand the spec, you can't pass multiple Cookie parameters with the same name (only last value will be used). The only way to pass a list of values is to pass them comma-separated, but it's not currently supported by Starlette

@YuriiMotov YuriiMotov added the bug Something isn't working label Nov 16, 2025
@YuriiMotov YuriiMotov marked this pull request as draft November 16, 2025 19:18
@YuriiMotov YuriiMotov force-pushed the fix-extra-non-body-param-parsing branch from 2392034 to c9a8008 Compare November 16, 2025 19:22
@YuriiMotov YuriiMotov marked this pull request as ready for review November 16, 2025 19:28
Copy link
Member

@svlandeg svlandeg left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks good! The implementation is slightly more convoluted here than in #14303 because the type of received_params is Union[Mapping[str, Any], QueryParams, Headers]. The code in this PR addresses all the possibilities, as far as I can see.

Copy link
Member

@tiangolo tiangolo left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Excellent job, thank you @YuriiMotov! 🙌

And thanks @svlandeg for the review! 🍰

This will be available in FastAPI 0.123.2, in the next few hours. 🎉

@tiangolo tiangolo merged commit de5bec6 into fastapi:master Dec 2, 2025
31 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

bug Something isn't working

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants