gunicorn uvicorn worker.py bagaimana menghormati pengaturan limit_concurrency
FastAPI menggunakan gunicorn untuk meluncurkan pekerja uvicorn seperti yang dijelaskan di https://www.uvicorn.org/settings/
Namun gunicorn tidak mengizinkan untuk meluncurkan uvicorn dengan pengaturan khusus seperti yang juga disebutkan di https://github.com/encode/uvicorn/issues/343
Masalah ini menyarankan untuk mengganti config_kwargs di file sumber seperti https://github.com/encode/uvicorn/blob/master/uvicorn/workers.py
Kami mencobanya tetapi uvicorn tidak mengikuti pengaturan limit_concurrency
di beberapa file uvicorn di sumbernya:
https://github.com/encode/uvicorn/blob/master/uvicorn/workers.py
# fail
config_kwargs = {
"app": None,
"log_config": None,
"timeout_keep_alive": self.cfg.keepalive,
"timeout_notify": self.timeout,
"callback_notify": self.callback_notify,
"limit_max_requests": self.max_requests, "limit_concurrency": 10000,
"forwarded_allow_ips": self.cfg.forwarded_allow_ips,
}
https://github.com/encode/uvicorn/blob/master/uvicorn/main.py
# fail
kwargs = {
"app": app,
"host": host,
"port": port,
"uds": uds,
"fd": fd,
"loop": loop,
"http": http,
"ws": ws,
"lifespan": lifespan,
"env_file": env_file,
"log_config": LOGGING_CONFIG if log_config is None else log_config,
"log_level": log_level,
"access_log": access_log,
"interface": interface,
"debug": debug,
"reload": reload,
"reload_dirs": reload_dirs if reload_dirs else None,
"workers": workers,
"proxy_headers": proxy_headers,
"forwarded_allow_ips": forwarded_allow_ips,
"root_path": root_path,
"limit_concurrency": 10000,
"backlog": backlog,
"limit_max_requests": limit_max_requests,
"timeout_keep_alive": timeout_keep_alive,
"ssl_keyfile": ssl_keyfile,
"ssl_certfile": ssl_certfile,
"ssl_version": ssl_version,
"ssl_cert_reqs": ssl_cert_reqs,
"ssl_ca_certs": ssl_ca_certs,
"ssl_ciphers": ssl_ciphers,
"headers": list([header.split(":") for header in headers]),
"use_colors": use_colors,
}
Bagaimana uvicorn bisa dipaksa untuk menghormati pengaturan ini? Kami masih mendapatkan kesalahan 503 dari FastAPI
------- UPDATE ----------- pengaturan gunicorn --worker-connections 1000
masih menyebabkan 503 saat membuat 100 permintaan paralel yang didistribusikan ke banyak pekerja.
Namun, saya yakin ini adalah masalah yang sedikit lebih rumit: endpoint API kami melakukan banyak beban kerja yang berat, biasanya membutuhkan waktu 5 detik untuk menyelesaikannya.
Uji stres dengan 2 inti, 2 pekerja:
- A. 100+ permintaan bersamaan, beban berat titik akhir - koneksi-pekerja 1
- B. 100+ permintaan bersamaan, beban berat titik akhir - koneksi-pekerja 1000
- C. 100+ permintaan serentak, beban rendah titik akhir - koneksi-pekerja 1
- D.100+ permintaan serentak, beban rendah titik akhir - koneksi-pekerja 1000
Kedua eksperimen A dan B menghasilkan 503 respons, jadi dengan asumsi setelan koneksi pekerja berfungsi, terlalu banyak koneksi simultan tampaknya tidak menyebabkan kesalahan 503 kami.
Kami bingung tentang perilaku ini, karena kami berharap gunicorn / uvicorn mengantrekan pekerjaan dan tidak menampilkan kesalahan 503.
Jawaban
Dari dokumen gunicorn
worker-connections
Jumlah maksimum klien simultan.
dan dari uvicorn doc
limit-concurrency
Jumlah maksimum koneksi atau tugas bersamaan yang diizinkan, sebelum memberikan respons HTTP 503.
Menurut info ini, kedua variabel pengaturan melakukan hal yang sama. Begitu
uvicorn --limit-concurrency 100 application:demo_app
hampir sama dengan
gunicorn --worker-connections 100 -k uvicorn.workers.UvicornWorker application:demo_app
Catatan: Saya belum melakukan tes nyata apa pun tentang ini, harap perbaiki saya jika saya salah.
Juga, Anda dapat menyetel limit-concurrency
(atau limit_concurrency
) dengan membuat subclass uvicorn.workers.UvicornWorker
kelas
from uvicorn.workers import UvicornWorker
class CustomUvicornWorker(UvicornWorker):
CONFIG_KWARGS = {
"loop": "uvloop",
"http": "httptools",
"limit_concurrency": 100
}
dan sekarang gunakan ini CustomUvicornWorker
dengan gunicorn
perintah sebagai,
gunicorn -k path.to.custom_worker.CustomUvicornWorker application:demo_app
Catatan: Anda dapat memeriksa self.config.limit_concurrency
di CustomUvicornWorker
kelas untuk memastikan nilai telah disetel dengan benar.