Batasan Field dan Rentang Nilai
Field request (C→S)
| Field | Tipe | Rentang valid | Arti | Saat dilanggar |
|---|---|---|---|---|
op | ASCII 1B | A(0x41) · R(0x52) | Jenis request | E bad_op |
wait | u8 | 0–255 (detik) | 0 mencoba langsung tanpa antrean; 1..255 membatasi waktu tunggu acquire | — (selalu valid karena tipe) |
lease | u8 | 1–250 (detik) | Lease; 0 dan 251..255 ditolak/reserved | E bad_lease |
owner | u64 BE | 0 – 2^64-1 seluruhnya | Penanda percobaan acquire (dibuat klien) | — (server tidak memeriksanya) |
token | u64 BE | nilai yang diterbitkan server | Menentukan apa yang dirilis (khusus R) | N jika tidak cocok |
key | UTF-8 | 1 – 128 byte | Nama lock. Tidak boleh spasi (0x20) atau newline (0x0A) | E bad_key |
- Tidak ada wait/lease tanpa batas. Klien resmi membulatkan pecahan detik ke atas, memvalidasi rentang, dan mengembalikan error input eksplisit sebelum mengirim tanpa clamp. Lease default adalah 30 detik.
- Dalam API client resmi,
waitadalah batas keseluruhan acquire sejak pemanggilan dimulai, mencakup local queue, retry koneksi yang pasti belum terkirim, write, dan respons. Satu monotonic operation deadline dibuat sekali saja; tepat sebelum benar-benar mengirim, writer memasukkan pembulatan ke atas u8 dari detik tersisa kewaitpada frame. Karena itu, koneksi yang terlambat atau failover yang pasti belum terkirim tidak dapat memulai ulang server wait. Saat deadline, request yang masih di queue berakhir timeout dan pasti belum terkirim; jika satu byte saja mungkin telah terkirim, session yang tepat itu ditutup dan hasilnyaIndeterminate. Hanyawait=0asli yang memakai wire0, dan percobaan langsung ini memiliki I/O deadline terbatas tersendiri agar transport yang macet tidak ditunggu selamanya. JikaAyang telah berkorelasi tepat sebelum deadline baru ditemukan di gate penyerahan Ticket, server waiter sudah selesai: session tetap terbuka, exact token yang diketahui dilepas sebagai kompensasi, dan hasilnyaIndeterminate.T/Byang berkorelasi tetap merupakan kegagalan memperoleh lock yang definitif. - Untuk
wait=0asli, perilaku wire dan server tetap satu percobaan langsung tanpa queue. Dalam transport deadline lima detik yang terpisah, kegagalan yang pasti belum terkirim boleh memilih koneksi lain dan retry dengan owner yang sama. Setelah satu byte saja mungkin telah terkirim, acquire tidak pernah dikirim ulang. - API klien resmi mewajibkan
min_work_budgetyang tidak ada di wire. Nilai ini mencakupcritical work + perkiraan pause + penyelesaian DB commit/rollback, berada di0..250detik, dan tidak melebihi lease ternormalisasi. Pelanggaran gagal sebelum kirim dengan error kelasUnsupportedDuration/InsufficientLease. - Panjang key dihitung dalam byte, bukan karakter — aksara Korea memakai 3 byte per karakter di UTF-8, jadi maksimal 42 karakter.
ownerhanya ID korelasi respons, bukan otoritas. Memakai ulang nilainya tidak mengembalikan active token atau memperbarui lease. Request in-flight bersamaan dari satu klien harus memakai nilai nonzero berbeda; saat counter menjadi 0 atau wrap, klien resmi fail-closed.- Release eksplisit dan kompensasi untuk token yang sudah diketahui memiliki 5 detik absolut sejak call/enqueue, termasuk reconnect dan retry.
Rmemastikan sukses;Nberarti sudah hilang atau bukan token saat ini. Tanpa respons tidak pernah dianggap sukses; antrean kompensasi terbatas yang penuh bergantung pada lease expiry. bad_keymencakup key kosong, lebih dari 128 byte, mengandung spasi atau newline, dan UTF-8 yang tidak valid, semuanya sama. Klien resmi juga tidak pernah mengirim\r— key yang diakhiri\rakan diam-diam menjadi key yang berbeda.
Field respons (S→C)
| Field | Tipe | Rentang | Muncul pada |
|---|---|---|---|
token | u64 BE | 1 atau lebih, naik setiap penerbitan | A (penerbitan baru) · R/N (echo request) |
owner | u64 BE | persis nilai request | A · T · B (echo request) |
key | UTF-8 | persis nilai request (1–128 B) | A · T · B · R · N |
addr | UTF-8 | host:port | M · L |
reason | ASCII | 8 nilai yang ditetapkan | E |
Server tidak pernah menerbitkan token 0. Single memakai counter selama process lifetime saat ini; cluster memakai counter yang direplikasi konsensus dan fail-closed sebelum overflow. Wall clock atau acak tidak menjamin monotonisitas setelah restart.
Panjang header tetap
Bagian biner berpanjang tetap yang mengikuti op. Byte-byte ini bisa mengandung 0x0A, jadi parser harus mengonsumsi panjang ini sebelum mencari newline.
| Arah | op | Header tetap | Susunan |
|---|---|---|---|
| C→S | A | 10 B | wait(1) + lease(1) + owner(8) |
| C→S | R | 8 B | token(8) |
| S→C | A | 16 B | token(8) + owner(8) |
| S→C | T · B | 8 B | owner(8) |
| S→C | R · N | 8 B | token(8) |
| S→C | M · L · E | 0 B | tidak ada (teks langsung setelah op) |
Jika byte-nya kurang, hasilnya E bad_request.
Ukuran frame
| Item | Nilai |
|---|---|
Batas frame (tanpa \n) | 192 byte — jika lebih: E line_too_long |
Request A maksimum | 1 + 10 + 128 + 1 = 140 B |
Request R maksimum | 1 + 8 + 128 + 1 = 138 B |
Respons A maksimum | 1 + 16 + 128 + 1 = 146 B |
Frame kosong (hanya \n) | keep-alive — diabaikan server |
Batas 192B di atas frame terbesar (146B), sehingga klien patuh tidak akan mencapainya. Setelah frame cacat struktur atau oversized, framing tidak lagi dipercaya dan koneksi ditutup.
Auth handshake
| Item | Nilai |
|---|---|
| Hash | SHA-256 (dicantumkan di baris challenge) |
| nonce | 8 karakter base64url |
| Digest respons | 43 karakter base64url (tanpa padding) |
| Batas baris | 256 byte |
| Batas waktu | 10 detik (termasuk negosiasi TLS) — lewat dari itu koneksi ditutup |
Prosedur lengkapnya ada di Auth handshake.
Batas sisi server
Nilai ini tidak disetel langsung oleh klien, tetapi memengaruhi perilakunya.
| Item | Default | Setelan | Saat terlampaui |
|---|---|---|---|
| Waiter per key | 2048 (batas 16384) | MAX_WAITERS | B (busy) |
| Total waiter | 16384 (batas 65536) | MAX_TOTAL_WAITERS | B untuk acquire |
| Koneksi client bersamaan | 1024 (batas 8192) | MAX_CONNECTIONS | Koneksi langsung ditutup |
| Reply tertunda per koneksi | 256 | compile-time | Koneksi lambat ditutup |
| Acquire in-flight global | 4096 | compile-time | B untuk acquire |
| Release in-flight global | 512, lane terpisah | compile-time | Menunggu terbatas sampai koneksi tutup |
| Key aktif cluster | 65536 | compile-time | B untuk key baru |
Read buffer (4096B), batch respons (64), progress timeout frame client yang dimulai (5 detik), dan single expiry sweep (5 detik) adalah konstanta compile-time. Cluster expiry memakai deadline min-heap yang memvalidasi token, bukan scan penuh. Lihat Konfigurasi.
Admission semua acquire, key baru, dan semua waiter ditutup pada 90% hard limit dan baru dibuka setelah turun di bawah 75%. Karena itu acquire baru dapat menerima B sebelum batas; capacity cadangan untuk release dan pemulihan Raft terpisah dari hysteresis ini.
Ringkasan pelanggaran → respons
| Situasi | Respons | Koneksi |
|---|---|---|
| op tidak dikenal | E bad_op | ditutup |
| Header tetap kurang | E bad_request | ditutup |
lease = 0 atau 251..255 | E bad_lease | ditutup |
| Key kosong / lebih dari 128 B / mengandung spasi atau newline / bukan UTF-8 | E bad_key | ditutup |
| Frame lebih dari 192 B | E line_too_long | ditutup |
| Digest auth tidak cocok | E auth_failed | ditutup |
| Antrean penuh | B + owner + key | tetap |
| Token rilis tidak cocok | N + token + key | tetap |
Daftar lengkap alasan error dan penanganan koneksinya ada di Response · Error E.