运行在 Google 云 运行 上使用 FastAPI(Docker 图片)

Running FastAPI on Google Cloud Run (Docker Image)

我希望构建一个 Docker 图像到 运行 FastAPI on Google Cloud Run. FastAPI uses Uvicorn as an ASGI server and Uvicorn recommend using Gunicorn with the Uvicorn worker class for production deployments. FastAPI themselves also have some excellent documentation on using Gunicorn with Uvicorn。我什至看到 FastAPI 提供了结合两者的官方图像( uvicorn-gunicorn-fastapi-docker) but this comes with a warning:

You are probably using Kubernetes or similar tools. In that case, you probably don't need this image (or any other similar base image). You are probably better off building a Docker image from scratch

这个警告基本上解释了复制将在 集群级别 处理,不需要在 进程级别 处理.这是有道理的。但是我不太确定 Cloud 运行 是否属于这一类?本质上,它是一种抽象和托管的 Knative 服务,因此 运行 在 Kubernetes 上。

我的问题是,我是否应该在我的 Docker 文件中安装 Gunicorn 和 Uvicorn 并在进程级别处理复制?沿着:

CMD ["gunicorn", "app.main:app", "-w", "4", "-k", "uvicorn.workers.UvicornWorker", "--bind", "0.0.0.0:80"]

或者我应该坚持使用单一进程 Uvicorn,让 Cloud 运行 (Kubernetes) 在集群级别处理复制?例如

CMD ["uvicorn", "app.main:app", "--host", "0.0.0.0", "--port", "80"]

一个。先说大尺度吧

在撰写本文时,Cloud 运行 实例最多可设置为 1000 concurrency requests。并且CPU可以设置为4个vCPU。

稍微回到基础。 Cloud 运行 将跨越许多实例,每个实例都将单独工作,并且每个实例都可以处理允许的最大并发数,因此每个实例可以处理 1000 个请求。如果你设置多CPU你需要处理多进程

当我们谈论这么大的数字时,我们需要谨慎。如果您的容器在 CPU/Memory 方面足够大以处理此流量,您可能希望使用进程管理器(gunicorn)启动多个 Uvicorn 线程(worker),就像您引用的图像一样。所以你可以使用 docker 容器。

乙。小规模。

另一方面,如果您设置 1 个 vCPU 并为单线程,则不需要 gunicorn 作为进程管理器。您仍然可以启用并发,但不是在顶层,也许在较低级别,这适合您的 1 个 vCPU 模型,例如 80 个并发请求。在这种情况下,您将拥有大量流量,许多实例由 Cloud 运行 启动,并且您依赖 Cloud 运行 根据需要生成尽可能多的实例,这确实很好。它就像是简单容器之上的 Kubernetes。

我建议从单进程开始,构建一个不使用引用容器的容器,并且只将 B 交换到版本 A,当您知道拥有更大的实例有好处(成本明智)时。