Set up a brand new FastAPI venv:
virtualenv venv
source venv/bin/activate
pip install fastapi[all] pytest
Copy/paste example from the testing docs at https://fastapi.tiangolo.com/tutorial/testing/:
from fastapi import FastAPI
from fastapi.testclient import TestClient
app = FastAPI()
@app.get("/")
async def read_main():
return {"msg": "Hello World"}
client = TestClient(app)
def test_read_main():
response = client.get("/")
assert response.status_code == 200
assert response.json() == {"msg": "Hello World"}
Observe that the tests take 30s to run. If you add another .get call, they take 60s.
On Mac with new install of FastAPI, every call to TestClient.get() takes exactly 30s to complete. The response is correct.
Python version:
Python version: 3.6
Experimenting with this test code, I haven't seen these performance issues.
All using macOS 10.15.5 on a Mac Mini, FastAPI 0.56.1, pytest 5.4.3, requests 2.23.0:
| Python | Time (s)|
|--------|---------|
| CPython 3.8.2 | 0.01 |
| CPython 3.7.7 | 0.01
| CPython 3.6.10 | 0.01 |
That is executing with pytest. If I just run the same code directly (not with pytest) it's even faster. Can you provide the exact command you're using to run this?
Hmm my command is just pytest. Running the code directly produces the same result.
It must be something odd about my setup. I'm on a Macbook Pro 10.13.6, FastAPI 0.56.1, pytest 5.4.3, requests 2.23.0, so identical to you.
My full pip freeze output:
packages.txt
If you send me yours, I'll reproduce your venv exactly and see if it still happens.
30s seems suspiciously close to the timeout for starlette workers, but I don't know enough about starlette to comment more.
Using CPython 3.6.10 installed via pyenv I:
python -m venv venv to create a new virtual environmentsource venv/bin/activate to enter this new clean venvpip install -r packages.txt using the frozen file you provided abovepytest test.py twiceThis is the content of test.py
from fastapi import FastAPI
from fastapi.testclient import TestClient
app = FastAPI()
@app.get("/")
async def read_main():
return {"msg": "Hello World"}
def test_read_main():
client = TestClient(app)
response = client.get("/")
assert response.status_code == 200
assert response.json() == {"msg": "Hello World"}
So it must not be the dependencies causing the issue. I doubt small variations in Python versions would cause the issue, nor differences in the OS. Would you run a profiler to try and narrow down exactly what's taking so long?
Something like this:
import cProfile
prof = cProfile.Profile()
prof.enable()
response = client.get("/")
prof.dump_stats("stats.prof")
You can then analyze that file with something like snakeviz to see where the program is getting hung up. I'm not sure that will get us to the solution but it might help narrow down the problem.
Also, just fishing for more information that might lead us in the right direction:
requests like requests.get("/"), is that slow as well? Or is that normal speed?Duplicating those exact steps you did, I still see the error.
I've made a repo at https://github.com/charlesbaynham/fastapi_mwe which contains the exact code I'm using. Running the profiler in this repo produces:

The full profile output is in the repo and also here (renamed, to appease github):
For your other questions:
Alright, well at least we've narrowed down the issue to TestClient and Starlette. I don't have any other ideas right now but I'll follow the other ticket in case I think of something. Hopefully someone with a better grasp on the inner workings of Starlette will be able to make more progress 馃槄.
Thanks for the help here @dbanty ! :clap: :bow:
@charlesbaynham could you try on another macOS, or another OS (maybe on a VM)?
Also maybe inside of Docker.
It seems very weird, and like it could be something strange related to your environment.
You could also try another installation, e.g. miniconda, with another Python version, just to try and narrow the environment of the issue.
Hi @tiangolo, I don't have another mac available I'm afraid. I've also tried on Windows, but it works fine. I'll continue looking at this but in the starlette issue (https://github.com/encode/starlette/issues/974) since it doesn't seem to be a fastapi problem.
Assuming the original issue was solved, it will be automatically closed now. But feel free to add more comments or create new issues.
Most helpful comment
Experimenting with this test code, I haven't seen these performance issues.
All using macOS 10.15.5 on a Mac Mini, FastAPI 0.56.1, pytest 5.4.3, requests 2.23.0:
| Python | Time (s)|
|--------|---------|
| CPython 3.8.2 | 0.01 |
| CPython 3.7.7 | 0.01
| CPython 3.6.10 | 0.01 |
That is executing with pytest. If I just run the same code directly (not with pytest) it's even faster. Can you provide the exact command you're using to run this?