Bagaimana cara mengkonfigurasi nginx untuk mengembalikan kode 429 http ketika pembatasan tarif?

11

Bagaimana cara mengkonfigurasi nginx untuk mengembalikan kode status http 429 (Terlalu Banyak Permintaan) alih-alih 503 default (Layanan Tidak Tersedia) ketika pembatasan / pembatasan kecepatan?

FYI, saya menggunakan nginx sebagai proxy terbalik dengan HttpLimitReqModule. Draf spesifikasi untuk kode status 429 adalah RFC6585 .

Pertanyaan (tertutup) ini pada stackexchanged menunjukkan bahwa dimungkinkan untuk menggunakan direktif error_page . Namun, saya tidak ingin mengembalikan 429 jika memang ada masalah server (bukan pelanggan memukul kami terlalu banyak) dan server harus mengembalikan 503 Layanan Tidak Tersedia.

Ada saran?

adambrod
sumber
FYI, saya telah membuat permintaan tambahan untuk fitur ini karena tidak mungkin tanpa memetakan semua 503 ke 429.
adambrod

Jawaban:

19

Berita baik, dengan Versi 1.3.15 http://mailman.nginx.org/pipermail/nginx/2013-March/038306.html

kami memiliki arahan "limit_req_status" dan "limit_conn_status". Saya baru saja mengujinya di Gentoo Linux (perhatikan bahwa Anda perlu mengompilasi module limit_req dan limit_con).

Dengan pengaturan ini saya pikir Anda dapat mencapai apa yang Anda minta:

limit_req_status 429;
limit_conn_status 429;

Saya telah memverifikasi ini dengan cepat:

ab2 -n 100000 -c 55 "http://127.0.0.1/api/v1

Di mana sebagian besar permintaan gagal setelah mengaktifkan arahan karena tingginya tingkat permintaan dan batas yang dikonfigurasi di nginx:

limit_req zone=api burst=15 nodelay;
vantome
sumber
1
..apa itu "ab2"?
XXL
abadalah alat dari apache2-utils. di ubuntu itu abtetapi di bawah CentOS itu ab2.
diet
1

Berdasarkan tanggapan VBart dan komentar lainnya, jelas bahwa opsi terbaik adalah memetakan 503 kesalahan ke 429s.

error_page 503 = 429 /too-many-requests.html

Karena nginx (1.3.x) hanya menggunakan 503 kode status untuk limit_req dan limit_conn, ini harus menjadi pendekatan yang bagus.

adambrod
sumber
ini bukan pilihan terbaik. 429 adalah kasus penggunaan khusus, memetakan semua potensi 503 (layanan tidak tersedia) untuk mengembalikan 429 menyesatkan dan tidak valid bagi pengguna. Misalnya, klien mungkin melihat 429 dan menggunakan logika coba kembali mundur, tetapi jika 503 tidak terkait dengan pelambatan itu tidak membantu.
Eddie
0

Nginx sendiri tidak pernah mengembalikan 503 dalam kasus selain limit_req dan limit_conn.

VBart
sumber
1
Ah, itu menarik. Jadi Anda mengatakan bahwa jika saya mengganti 503 dengan 429 menggunakan error_page, saya tidak akan pernah memberi tahu pelanggan Terlalu Banyak Permintaan kecuali mereka benar-benar mengirim terlalu banyak permintaan?
adambrod
Ya, benar, tetapi hanya dengan satu pengecualian, bahwa Anda tidak (proxy/factcgi/scgi/uwsgi)_intercept_errorsmengaktifkannya. nginx.org/r/proxy_intercept_errors
VBart
Mungkin juga aplikasi yang dilayani oleh nginx akan mengembalikan 503, yang menyulitkan klien untuk melihat apakah itu batas koneksi dari nginx atau kesalahan server dari aplikasi.
bbaja42