Browse Source

add test, arrange codes, fix bug

pull/4573/head
jujumilk3 3 years ago
parent
commit
318834ea0d
  1. 16
      fastapi/dependencies/utils.py
  2. 178
      tests/test_dependency_schema_query.py

16
fastapi/dependencies/utils.py

@ -247,17 +247,21 @@ def is_scalar_sequence_field(field: ModelField) -> bool:
def get_typed_signature(call: Callable[..., Any]) -> inspect.Signature: def get_typed_signature(call: Callable[..., Any]) -> inspect.Signature:
signature = inspect.signature(call) signature = inspect.signature(call)
globalns = getattr(call, "__globals__", {}) globalns = getattr(call, "__globals__", {})
if inspect.isclass(call): fields = getattr(call, "__fields__", {})
from fastapi import Query if len(fields):
parameters = {} query_extra_info = dict()
fields = getattr(call, '__fields__', {})
for param in fields: for param in fields:
parameters[param] = dict((fields[param].field_info.__repr_args__())) query_extra_info[param] = dict((fields[param].field_info.__repr_args__()))
query_extra_info[param]["default"] = (
Required
if getattr(fields[param], "required", False)
else fields[param].default
)
typed_params = [ typed_params = [
inspect.Parameter( inspect.Parameter(
name=param.name, name=param.name,
kind=param.kind, kind=param.kind,
default=Query(parameters[param.name].get("default"), description=parameters[param.name].get("description")), default=params.Param(**query_extra_info[param.name]),
annotation=get_typed_annotation(param, globalns), annotation=get_typed_annotation(param, globalns),
) )
for param in signature.parameters.values() for param in signature.parameters.values()

178
tests/test_dependency_schema_query.py

@ -0,0 +1,178 @@
from typing import Optional
from fastapi import FastAPI, Depends, Query
from fastapi.testclient import TestClient
from pydantic import BaseModel
app = FastAPI()
class Item(BaseModel):
name_required_with_default: str = Query(
"name default", description="This is a name_required_with_default field."
)
name_required_without_default: str = Query(
None, description="This is a name_required_without_default field."
)
optional_int: Optional[int] = Query(
None, description="This is a optional_int field"
)
optional_str: Optional[str] = Query(
"default_exists", description="This is a optional_str field"
)
model: str
manufacturer: str
price: float
tax: float
@app.get("/item")
async def item_with_query_dependency(item: Item = Depends()):
return item
client = TestClient(app)
openapi_schema = {
"openapi": "3.0.2",
"info": {"title": "FastAPI", "version": "0.1.0"},
"paths": {
"/item": {
"get": {
"summary": "Item With Query Dependency",
"operationId": "item_with_query_dependency_item_get",
"parameters": [
{
"description": "This is a name_required_with_default field.",
"required": False,
"schema": {
"title": "Name Required With Default",
"type": "string",
"description": "This is a name_required_with_default field.",
"default": "name default",
"extra": {},
},
"name": "name_required_with_default",
"in": "query",
},
{
"description": "This is a name_required_without_default field.",
"required": False,
"schema": {
"title": "Name Required Without Default",
"type": "string",
"description": "This is a name_required_without_default field.",
"extra": {},
},
"name": "name_required_without_default",
"in": "query",
},
{
"description": "This is a optional_int field",
"required": False,
"schema": {
"title": "Optional Int",
"type": "integer",
"description": "This is a optional_int field",
"extra": {},
},
"name": "optional_int",
"in": "query",
},
{
"description": "This is a optional_str field",
"required": False,
"schema": {
"title": "Optional Str",
"type": "string",
"description": "This is a optional_str field",
"default": "default_exists",
"extra": {},
},
"name": "optional_str",
"in": "query",
},
{
"required": True,
"schema": {"title": "Model", "type": "string", "extra": {}},
"name": "model",
"in": "query",
},
{
"required": True,
"schema": {
"title": "Manufacturer",
"type": "string",
"extra": {},
},
"name": "manufacturer",
"in": "query",
},
{
"required": True,
"schema": {"title": "Price", "type": "number", "extra": {}},
"name": "price",
"in": "query",
},
{
"required": True,
"schema": {"title": "Tax", "type": "number", "extra": {}},
"name": "tax",
"in": "query",
},
],
"responses": {
"200": {
"description": "Successful Response",
"content": {"application/json": {"schema": {}}},
},
"422": {
"description": "Validation Error",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/HTTPValidationError"
}
}
},
},
},
}
}
},
"components": {
"schemas": {
"HTTPValidationError": {
"title": "HTTPValidationError",
"type": "object",
"properties": {
"detail": {
"title": "Detail",
"type": "array",
"items": {"$ref": "#/components/schemas/ValidationError"},
}
},
},
"ValidationError": {
"title": "ValidationError",
"required": ["loc", "msg", "type"],
"type": "object",
"properties": {
"loc": {
"title": "Location",
"type": "array",
"items": {"anyOf": [{"type": "string"}, {"type": "integer"}]},
},
"msg": {"title": "Message", "type": "string"},
"type": {"title": "Error Type", "type": "string"},
},
},
}
},
}
def test_openapi_schema_with_query_dependency():
response = client.get("/openapi.json")
assert response.status_code == 200, response.text
assert response.json() == openapi_schema
Loading…
Cancel
Save