परिचय: Rust में उन्नत HTTP क्लाइंट क्यों महत्वपूर्ण है
\nRust ने उन सिस्टमों के लिए एक भाषा के रूप में प्रतिष्ठा अर्जित की है जहाँ प्रदर्शन और विश्वसनीयता महत्वपूर्ण है। हालाँकि, Rust में HTTP क्लाइंट लिखते समय, कई डेवलपर दस्तावेज़ीकरण के मूल उदाहरणों पर ही रुक जाते हैं। वास्तविक प्रोजेक्ट्स में - माइक्रोसर्विसेज, पार्सर्स, CI/CD टूल्स - एक साधारण reqwest::get() कॉल आलोचना के लायक नहीं है। नेटवर्क त्रुटियों के कारण क्रैश, लंबे उत्तरों के दौरान हैंग होना, कनेक्शन लीक - ये सब सतही दृष्टिकोण के परिणाम हैं।
इस लेख में, हम Rust में HTTP क्लाइंट के साथ काम करने के उन्नत स्तर पर चर्चा करेंगे। आप सीखेंगे कि त्रुटियों को सही तरीके से कैसे संभालें, टाइमआउट कैसे कॉन्फ़िगर करें, पुनः प्रयास (retries) तंत्र को कैसे लागू करें और TLS का प्रबंधन कैसे करें। सभी उदाहरण Rust में क्रेट reqwest और tokio का उपयोग करके लिखे गए हैं - जो एसिंक्रोनस HTTP अनुरोधों के लिए मानक स्टैक है।
1. Rust में HTTP क्लाइंट में त्रुटि प्रबंधन
\nकोई भी नेटवर्क अनुरोध विफल हो सकता है: कनेक्शन टूटना, DNS त्रुटि, गलत प्रतिक्रिया स्थिति। Rust में इसके लिए शक्तिशाली प्रकार प्रणाली Result और Error का उपयोग किया जाता है। उन्नत दृष्टिकोण केवल स्थिति की जाँच करना नहीं है, बल्कि त्रुटियों को लॉग और वर्गीकृत करना है।
संरचित त्रुटि प्रबंधन
\nHTTP क्लाइंट के लिए एक कस्टम त्रुटि प्रकार बनाएँ:
\nuse std::fmt;\nuse reqwest::StatusCode;\n\n#[derive(Debug)]\npub enum HttpClientError {\n NetworkError(reqwest::Error),\n BadStatus(StatusCode),\n Timeout,\n InvalidUrl(String),\n}\n\nimpl fmt::Display for HttpClientError {\n fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {\n match self {\n HttpClientError::NetworkError(e) => write!(f, "नेटवर्क त्रुटि: {}", e),\n HttpClientError::BadStatus(s) => write!(f, "गलत स्थिति: {}", s),\n HttpClientError::Timeout => write!(f, "अनुरोध टाइमआउट"),\n HttpClientError::InvalidUrl(url) => write!(f, "अमान्य URL: {}", url),\n }\n }\n}\n\nimpl From<reqwest::Error> for HttpClientError {\n fn from(e: reqwest::Error) -> Self {\n if e.is_timeout() {\n HttpClientError::Timeout\n } else if e.is_connect() {\n HttpClientError::NetworkError(e)\n } else {\n HttpClientError::NetworkError(e)\n }\n }\n}\n\nअब अनुरोध फ़ंक्शन स्पष्ट रूप से टाइप की गई त्रुटि लौटाता है:
\nasync fn fetch_data(url: &str) -> Result<String, HttpClientError> {\n if !url.starts_with("http") {\n return Err(HttpClientError::InvalidUrl(url.to_string()));\n }\n\n let response = reqwest::get(url).await?;\n\n match response.status() {\n StatusCode::OK => {\n let body = response.text().await?;\n Ok(body)\n }\n status => Err(HttpClientError::BadStatus(status)),\n }\n}\n\nयह दृष्टिकोण कॉल करने वाले कोड को सटीक रूप से जानने की अनुमति देता है कि क्या गलत हुआ, और सही निर्णय लेता है: नेटवर्क त्रुटि पर अनुरोध दोहराएँ, लेकिन 400 Bad Request पर नहीं।
2. टाइमआउट और कनेक्शन प्रबंधन
\nटाइमआउट के बिना, आपका Rust में HTTP क्लाइंट मिनटों तक हैंग हो सकता है। उन्नत कॉन्फ़िगरेशन में तीन स्तर शामिल हैं: कनेक्शन टाइमआउट, रीड टाइमआउट और पूरे अनुरोध का सामान्य टाइमआउट।
\n\nटाइमआउट के साथ क्लाइंट कॉन्फ़िगर करना
\nuse std::time::Duration;\nuse reqwest::Client;\n\nasync fn create_advanced_client() -> Result<Client, reqwest::Error> {\n let client = Client::builder()\n .timeout(Duration::from_secs(30)) // सामान्य टाइमआउट\n .connect_timeout(Duration::from_secs(5)) // कनेक्शन टाइमआउट\n .pool_max_idle_per_host(10) // अधिकतम निष्क्रिय कनेक्शन\n .tcp_keepalive(Duration::from_secs(60)) // keepalive\n .build()?;\n\n Ok(client)\n}\n\nअब वास्तविक रूप से टाइमआउट वाले क्लाइंट का उपयोग करें