फ़ील्ड बाधाएँ और मान सीमाएँ
अनुरोध फ़ील्ड (C→S)
| फ़ील्ड | प्रकार | मान्य सीमा | अर्थ | उल्लंघन पर |
|---|---|---|---|---|
op | ASCII 1B | A(0x41) · R(0x52) | अनुरोध का प्रकार | E bad_op |
wait | u8 | 0–255 (सेकंड) | 0 बिना queue तत्काल प्रयास; 1..255 acquire प्रतीक्षा सीमा | — (टाइप से हमेशा मान्य) |
lease | u8 | 1–250 (सेकंड) | Lease; 0 और 251..255 अस्वीकृत/reserved | E bad_lease |
owner | u64 BE | 0 – 2^64-1 पूरा | अधिग्रहण प्रयास का पहचानकर्ता (क्लाइंट द्वारा निर्मित) | — (सर्वर इसकी जाँच नहीं करता) |
token | u64 BE | सर्वर द्वारा जारी मान | क्या रिलीज़ करना है यह तय करता है (केवल R) | मेल न खाने पर N |
key | UTF-8 | 1 – 128 बाइट | लॉक का नाम। स्पेस (0x20) या नई लाइन (0x0A) नहीं | E bad_key |
- अनंत wait/lease नहीं है। आधिकारिक क्लाइंट उप-सेकंड मान को ऊपर round करके range जाँचते हैं और clamp या send करने के बजाय पहले स्पष्ट input error देते हैं। Default lease 30 सेकंड है।
- आधिकारिक client API में
wait, call शुरू होने से local queue, निश्चित रूप से unsent connection retry और write होते हुए response तक का पूरा acquire limit है। केवल एक monotonic operation deadline बनती है; वास्तविक send से ठीक पहले writer बचा समय u8 सेकंड में ऊपर round करके frame केwaitमें डालता है। इसलिए देर से उपलब्ध connection या निश्चित unsent failover server wait को शुरू से फिर नहीं चला सकता। deadline पर request अभी queue में हो तो वह निश्चित unsent timeout है; यदि एक byte भी भेजा गया हो सकता है तो उसी exact session को बंद करके परिणामIndeterminateहोता है। केवल मूलwait=0wire0इस्तेमाल करता है, और इस immediate attempt के लिए भी अलग finite I/O deadline है ताकि रुका transport अनंत समय तक न रोके। यदि deadline से ठीक पहले correlatedATicket delivery gate पर देर से मिले, तो server waiter पहले ही समाप्त हो चुका है: session खुला रखा जाता है, ज्ञात exact token का compensating release किया जाता है और परिणामIndeterminateरहता है। CorrelatedT/Bनिश्चित non-acquisition हैं। - मूल
wait=0के लिए wire और server व्यवहार बिना queue का केवल एक immediate attempt ही रहता है। इसकी अलग 5-सेकंड transport deadline में, निश्चित unsent failure दूसरी connection चुनकर उसी owner से retry कर सकता है। एक byte भी भेजा गया हो सकता है, उसके बाद acquire कभी retransmit नहीं होता। - आधिकारिक client API में wire पर न मौजूद
min_work_budgetअनिवार्य है। यहcritical work + अपेक्षित pause + DB commit/rollback completionको कवर करे,0..250सेकंड हो और normalized lease से अधिक न हो। उल्लंघन send से पहलेUnsupportedDuration/InsufficientLeaseवर्ग की error देता है। - कुंजी की लंबाई अक्षरों में नहीं, बाइट में गिनी जाती है — कोरियाई अक्षर UTF-8 में प्रति अक्षर 3 बाइट लेते हैं, इसलिए अधिकतम 42 अक्षर।
ownerकेवल response correlation ID है, authority नहीं। वही मान फिर भेजने से active token नहीं लौटता और lease renew नहीं होता। एक client के concurrent in-flight requests में अलग nonzero values चाहिए; counter 0 या wrap होने पर official clients fail-closed होते हैं।- ज्ञात token के explicit और compensating release में call/enqueue से reconnect/retry सहित पूर्ण 5 सेकंड होते हैं।
Rसफलता,Nपहले से हटे या current token न होने को बताता है। बिना response सफलता नहीं मानी जाती; bounded compensation queue भरने पर lease expiry safety net है। bad_keyएक खाली कुंजी, 128 बाइट से अधिक, स्पेस या नई लाइन वाली, और अमान्य UTF-8 — इन सभी को कवर करता है। आधिकारिक क्लाइंट इसके अतिरिक्त कभी भी\rनहीं भेजते —\rपर समाप्त होने वाली कुंजी चुपचाप एक अलग कुंजी बन जाएगी।
प्रतिक्रिया फ़ील्ड (S→C)
| फ़ील्ड | प्रकार | सीमा | किन प्रतिक्रियाओं में |
|---|---|---|---|
token | u64 BE | 1 या अधिक, हर जारी होने पर बढ़ता | A (नया जारी) · R/N (अनुरोध की प्रतिध्वनि) |
owner | u64 BE | अनुरोध का मान ज्यों-का-त्यों | A · T · B (अनुरोध की प्रतिध्वनि) |
key | UTF-8 | अनुरोध का मान ज्यों-का-त्यों (1–128 B) | A · T · B · R · N |
addr | UTF-8 | host:port | M · L |
reason | ASCII | निर्धारित 8 | E |
सर्वर token 0 कभी जारी नहीं करता। Single वर्तमान process lifetime का counter उपयोग करता है; cluster consensus-replicated counter उपयोग करता है और overflow से पहले fail-closed होता है। Wall clock या randomness restart के बाद monotonicity की गारंटी नहीं हैं।
फ़िक्स्ड हेडर की लंबाई
op के ठीक बाद आने वाला निश्चित लंबाई का बाइनरी खंड। इन बाइट्स में 0x0A हो सकता है, इसलिए पार्सर को नई लाइन खोजने से पहले ठीक इतनी लंबाई पढ़ लेनी चाहिए।
| दिशा | op | फ़िक्स्ड हेडर | संरचना |
|---|---|---|---|
| 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 | कोई नहीं (op के तुरंत बाद टेक्स्ट) |
बाइट कम पड़ने पर E bad_request मिलता है।
फ़्रेम आकार
| मद | मान |
|---|---|
फ़्रेम की ऊपरी सीमा (\n को छोड़कर) | 192 बाइट — इससे अधिक पर E line_too_long |
अधिकतम A अनुरोध | 1 + 10 + 128 + 1 = 140 B |
अधिकतम R अनुरोध | 1 + 8 + 128 + 1 = 138 B |
अधिकतम A प्रतिक्रिया | 1 + 16 + 128 + 1 = 146 B |
खाली फ़्रेम (सिर्फ \n) | keep-alive — सर्वर इसे अनदेखा करता है |
192B सीमा अधिकतम frame (146B) से बड़ी है, इसलिए compliant client इसे नहीं छूता। संरचनात्मक रूप से malformed या oversized frame के बाद framing पर भरोसा नहीं किया जाता और connection बंद होता है।
प्रमाणीकरण हैंडशेक
| मद | मान |
|---|---|
| हैश | SHA-256 (challenge लाइन में दर्ज) |
| nonce | base64url के 8 अक्षर |
| प्रतिक्रिया डाइजेस्ट | base64url के 43 अक्षर (बिना पैडिंग) |
| लाइन की ऊपरी सीमा | 256 बाइट |
| समय सीमा | 10 सेकंड (TLS वार्ता सहित) — इससे अधिक होने पर कनेक्शन बंद |
विस्तृत प्रक्रिया के लिए प्रमाणीकरण हैंडशेक देखें।
सर्वर-साइड सीमाएँ
क्लाइंट इन्हें सीधे सेट नहीं करता, पर ये व्यवहार प्रभावित करती हैं।
| आइटम | डिफ़ॉल्ट | सेटिंग | सीमा पार होने पर |
|---|---|---|---|
| प्रति key waiter | 2048 (hard cap 16384) | MAX_WAITERS | B (busy) |
| कुल waiter | 16384 (hard cap 65536) | MAX_TOTAL_WAITERS | उस acquire को B |
| concurrent client connections | 1024 (hard cap 8192) | MAX_CONNECTIONS | तुरंत बंद |
| प्रति connection pending replies | 256 | compile-time | धीमा connection बंद |
| global in-flight acquire | 4096 | compile-time | उस acquire को B |
| global in-flight release | 512, अलग lane | compile-time | connection close तक bounded wait |
| cluster active keys | 65536 | compile-time | नई key acquire को B |
Read buffer (4096B), response batch (64), शुरू client frame progress timeout (5 सेकंड) और single expiry sweep (5 सेकंड) compile-time constants हैं। Cluster expiry full scan के बजाय token-जाँच वाला deadline min-heap उपयोग करता है। कॉन्फ़िगरेशन देखें।
सभी acquire, नई key और सभी waiter का admission hard limit के 90% पर बंद और usage 75% से कम होने पर दोबारा खुलता है। इसलिए limit से पहले भी नया acquire B पा सकता है; release और Raft recovery की reserved capacity इस hysteresis से अलग है।
उल्लंघन → प्रतिक्रिया सारांश
| स्थिति | प्रतिक्रिया | कनेक्शन |
|---|---|---|
| अज्ञात op | E bad_op | बंद |
| फ़िक्स्ड हेडर कम | E bad_request | बंद |
lease = 0 या 251..255 | E bad_lease | बंद |
| कुंजी खाली / 128 B से अधिक / स्पेस या नई लाइन वाली / UTF-8 नहीं | E bad_key | बंद |
| फ़्रेम 192 B से अधिक | E line_too_long | बंद |
| प्रमाणीकरण डाइजेस्ट मेल नहीं खाता | E auth_failed | बंद |
| प्रतीक्षा कतार भरी | B + owner + key | बना रहता है |
| रिलीज़ टोकन मेल नहीं खाता | N + token + key | बना रहता है |
सभी त्रुटि कारण और कनेक्शन का व्यवहार प्रतिक्रिया · त्रुटि E में देखें।