Rust'ta reqwest ile proxy kullanmak, bir ClientBuilder üzerinde proxy ayarlarını yapılandırmak anlamına gelir; daha alt seviye bir HTTP kütüphanesi olan hyper ise bağlantının proxy sunucusu üzerinden elle kurulmasını gerektirir.
Proxy sunucuları ağ istekleri için aracı görevi görür ve anonimlik, coğrafi kısıtlı içeriğe erişim, yük dengeleme ve trafik filtreleme gibi avantajlar sunar. Rust'ın asenkron HTTP istemcileri reqwest ve hyper, proxy işlevselliğini entegre etmek için farklı yaklaşımlar sunar. reqwest üst seviye, yerleşik destek verirken hyper bağlantı süreci üzerinde daha ayrıntılı kontrol ister.
reqwest ile proxy kullanımı
reqwest, hyper üzerine kurulu, popüler ve kullanımı kolay bir Rust HTTP istemcisidir. Proxy yapılandırması dahil yaygın HTTP işlerini basitleştirir. reqwest'in ClientBuilder yapısı çeşitli proxy türlerini kurmak için metotlar sağlar.
Proxy yapılandırması
reqwest ile proxy kullanmak için reqwest::ClientBuilder ve onun proxy() metodunu kullanarak bir reqwest::Client örneği oluşturun. proxy() metodu, farklı proxy şemaları için oluşturulabilen bir reqwest::Proxy nesnesi alır:
- HTTP proxy: düz HTTP istekleri için
Proxy::http(url)ile yapılandırılır. - HTTPS proxy (CONNECT yöntemi): HTTPS istekleri için
Proxy::https(url)ile yapılandırılır.reqwest, TLS bağlantısını proxy üzerinden tünellemek içinCONNECTyöntemini kullanır. - SOCKS5 proxy: SOCKS5 proxy sunucuları için
Proxy::socks5(url)ile yapılandırılır. - Birleşik proxy:
Proxy::all(url), hem HTTP hem HTTPS istekleri için tek bir proxy tanımlar.
Proxy kimlik doğrulaması
Birçok proxy sunucusu kimlik doğrulama ister. reqwest::Proxy, basic_auth() metoduyla basic authentication'ı destekler.
Ortam değişkeni desteği
Varsayılan olarak reqwest'in ClientBuilder yapısı HTTP_PROXY, HTTPS_PROXY ve NO_PROXY ortam değişkenlerini otomatik olarak kontrol eder. Bunlar tanımlıysa, ClientBuilder::no_proxy() ile veya belirli bir proxy yapılandırılarak açıkça geçersiz kılınmadıkça reqwest bunları kullanır.
Örnek: reqwest ile proxy kullanımı
Bu örnek, basic authentication dahil olmak üzere reqwest'in HTTP, HTTPS ve SOCKS5 proxy'leri kullanacak şekilde yapılandırılmasını gösterir.
use reqwest::{Client, Error, Proxy};
use std::time::Duration;
#[tokio::main]
async fn main() -> Result<(), Error> {
// 1. HTTP proxy
let http_proxy_url = "http://user:[email protected]:8080";
let http_client = Client::builder()
.proxy(Proxy::http(http_proxy_url)?)
.timeout(Duration::from_secs(10))
.build()?;
println!("HTTP Proxy request...");
let http_res = http_client.get("http://httpbin.org/ip").send().await?;
println!("HTTP Proxy Response: {:?}", http_res.text().await?);
// 2. HTTPS proxy (CONNECT yöntemi)
// Not: HTTPS için proxy URL'inin kendisi HTTP olabilir, ancak HTTPS trafiğini tünelleyerek taşır.
let https_proxy_url = "http://user:[email protected]:8080";
let https_client = Client::builder()
.proxy(Proxy::https(https_proxy_url)?)
.timeout(Duration::from_secs(10))
.build()?;
println!("\nHTTPS Proxy request...");
let https_res = https_client.get("https://httpbin.org/ip").send().await?;
println!("HTTPS Proxy Response: {:?}", https_res.text().await?);
// 3. SOCKS5 proxy
let socks5_proxy_url = "socks5://user:[email protected]:1080";
let socks5_client = Client::builder()
.proxy(Proxy::socks5(socks5_proxy_url)?)
.timeout(Duration::from_secs(10))
.build()?;
println!("\nSOCKS5 Proxy request...");
let socks5_res = socks5_client.get("http://httpbin.org/ip").send().await?;
println!("SOCKS5 Proxy Response: {:?}", socks5_res.text().await?);
// 4. Birleşik proxy (hem HTTP hem HTTPS istekleri için geçerli)
let all_proxy_url = "http://user:[email protected]:8080";
let all_client = Client::builder()
.proxy(Proxy::all(all_proxy_url)?)
.timeout(Duration::from_secs(10))
.build()?;
println!("\nUnified Proxy (HTTP) request...");
let all_http_res = all_client.get("http://httpbin.org/ip").send().await?;
println!("Unified Proxy (HTTP) Response: {:?}", all_http_res.text().await?);
println!("\nUnified Proxy (HTTPS) request...");
let all_https_res = all_client.get("https://httpbin.org/ip").send().await?;
println!("Unified Proxy (HTTPS) Response: {:?}", all_https_res.text().await?);
Ok(())
}
Not: your-http-proxy.com:8080, your-https-proxy.com:8080 ve your-socks5-proxy.com:1080 değerlerini gerçek proxy sunucu adresleri ve portlarıyla, kimlik doğrulamalı proxy'ler için user:password bilgisiyle birlikte değiştirin.
hyper ile proxy kullanımı
hyper, reqwest dahil birçok Rust HTTP crate'inin temelini oluşturan, alt seviye ve yüksek performanslı bir HTTP kütüphanesidir. reqwest'ten farklı olarak hyper, istemcisi için yerleşik ve doğrudan proxy yapılandırma metotları sunmaz. Bunun yerine hyper ile proxy kullanımı, alttaki TCP bağlantısının elle yönetilmesini veya proxy'ye özel harici crate'lerle entegrasyonu gerektirir.
Bağlantının elle yönetimi
hyper ile proxy kullanmak için önce proxy sunucusuna bağlantıyı kurmanız, ardından hyper'a bu hazır bağlantıyı ya da proxy mantığını yöneten özel bir connector'ı kullanmasını söylemeniz gerekir.
HTTP istekleri için HTTP proxy
Bir HTTP proxy üzerinden düz metin HTTP istekleri için istemci, proxy sunucusuyla bir TCP bağlantısı kurar. Ardından HTTP isteğini doğrudan proxy'ye gönderir ve istek satırında hedefin tam URL'ini belirtir (örneğin GET http://target.com/path HTTP/1.1). Host başlığı yine hedef sunucuyu göstermelidir.
HTTPS istekleri için HTTP proxy (CONNECT yöntemi)
HTTPS istekleri için istemci önce proxy'ye bir HTTP CONNECT isteği göndererek hedef host ve porta bir TCP tüneli açmasını ister. Proxy 200 OK yanıtını verdikten sonra istemci, kurulan tünel üzerinden doğrudan hedef sunucuyla TLS el sıkışmasını gerçekleştirir.
SOCKS5 proxy
SOCKS5 proxy'ler HTTP proxy'lerden daha alt seviyede çalışır ve TCP ile UDP dahil çeşitli protokolleri destekler. SOCKS5'i hyper ile entegre etmek genellikle proxy'li bağlantıyı kurmak için özel bir SOCKS5 istemci kütüphanesi (örneğin tokio-socks) kullanmayı ve bu bağlantıyı hyper'ın connection builder'ına aktarmayı gerektirir.
Örnek: hyper ile proxy kullanımı (HTTP için HTTP proxy)
Bu örnek, isteği elle oluşturup TCP akışını yöneterek hyper ile bir HTTP proxy üzerinden temel bir HTTP isteğinin nasıl yapılacağını gösterir. Altta yatan mekanizmayı açıklar; sağlam çözümler için bu mantığı sarmalamayı ya da özel bir connector kullanmayı düşünün.
use hyper::{Body, Client, Request, Uri};
use hyper::client::conn::Builder;
use tokio::net::TcpStream;
use std::str::FromStr;
#[tokio::main]
async fn main() -> Result<(), Box<dyn std::error::Error + Send + Sync>> {
let proxy_addr = "127.0.0.1:8080"; // Kendi HTTP proxy adresinizle değiştirin
let target_url = "http://httpbin.org/ip";
println!("Connecting to proxy: {}", proxy_addr);
let stream = TcpStream::connect(proxy_addr).await?;
// HTTP proxy için proxy'ye bağlanıp istekte tam URI'yi göndeririz.
// Düz HTTP hedefleri için CONNECT yöntemi gerekmez.
let (mut sender, conn) = Builder::new()
.http1_only(true) // HTTP proxy uyumluluğu için HTTP/1.1 kullanılmasını sağlar
.handshake(stream)
.await?;
tokio::spawn(async move {
if let Err(e) = conn.await {
eprintln!("Connection error: {:?}", e);
}
});
let req = Request::builder()
.uri(Uri::from_str(target_url)?) // HTTP proxy yönlendirmesi için mutlak URI
.header("Host", "httpbin.org") // Hedef sunucu için Host başlığı
.body(Body::empty())?;
println!("Sending request through proxy to: {}", target_url);
let res = sender.send(req).await?;
println!("Response Status: {}", res.status());
let body_bytes = hyper::body::to_bytes(res.into_body()).await?;
println!("Response Body: {}", String::from_utf8_lossy(&body_bytes));
Ok(())
}
Not: Bu örnek, kimlik doğrulama istemeyen ve HTTP isteklerini doğrudan ileten temel bir HTTP proxy varsayar. HTTPS veya kimlik doğrulamalı proxy'lerde mantık, CONNECT istekleri ya da özel proxy anlaşma kütüphaneleri nedeniyle belirgin şekilde karmaşıklaşır.
hyper için harici connector kullanımı
hyper ile daha karmaşık proxy senaryolarında, özellikle SOCKS5 veya kimlik doğrulamalı HTTP/HTTPS proxy'lerinde, özel bir hyper::client::connect::Connection uygulamak ya da böyle bir uygulama sunan bir crate kullanmak yaygındır. Örneğin SOCKS5 için genellikle tokio-socks gibi bir crate ile SOCKS5 üzerinden proxy'lenmiş bir TcpStream kurar, ardından bu akışla hyper::client::conn::Builder::handshake çağrısını yaparsınız.
Proxy kullanımında reqwest ile hyper karşılaştırması
| Özellik | reqwest |
hyper |
|---|---|---|
| Proxy yapılandırması | Yerleşik, üst seviye metotlar (ClientBuilder::proxy()) |
hyper::client::connect::Connection'ın elle uygulanması veya harici kütüphanelerle entegrasyon |
| Kullanım kolaylığı | Üst seviye, yaygın proxy türleri için basit | Alt seviye, proxy'ler için karmaşık, daha fazla tekrar eden kod ister |
| Desteklenen proxy türleri | HTTP, HTTPS (CONNECT), SOCKS5 | Her tür için elle işlem gerekir; SOCKS5 veya karmaşık kimlik doğrulama için genellikle harici crate'ler kullanılır |
| Kimlik doğrulama | Yerleşik (Proxy::basic_auth()) |
Elle başlık ekleme (Proxy-Authorization) veya özel proxy kütüphanesi özellikleri |
| Kontrol düzeyi | Orta, bağlantı ayrıntılarını soyutlar | Yüksek, bağlantılar ve HTTP protokol ayrıntıları üzerinde ayrıntılı kontrol |
| Bağımlılıklar | Proxy için daha basit, reqwest alttaki karmaşıklığı üstlenir |
Sağlam proxy mantığı için ek crate'ler gerekebilir (tokio-socks, özel connector'lar) |
| Tipik kullanım senaryosu | Geliştirme hızını ve sadeliği önceleyen, proxy destekli HTTP isteklerine ihtiyaç duyan çoğu uygulama | Ağ bağlantıları üzerinde ince ayar kontrolünün kritik olduğu özel HTTP istemcileri, sunucular veya yüksek optimizasyonlu ağ bileşenleri geliştirmek |
En iyi uygulamalar ve dikkat edilecekler
Hata yönetimi
Proxy bağlantıları çeşitli nedenlerle başarısız olabilir (ağ sorunları, proxy'nin devre dışı olması, kimlik doğrulama hatası). Özellikle hyper ile bağlantıları elle yönetirken, proxy ile ilgili işlemler için sağlam bir hata yönetimi uygulayın. reqwest, proxy'ye özgü sorunlar açısından incelenebilen reqwest::Error döndürür.
Proxy türleri ve protokol uyumluluğu
- HTTP proxy'ler: temel olarak HTTP trafiği içindir.
CONNECTyöntemiyle HTTPS trafiğini tünelleyebilir. - SOCKS5 proxy'ler: protokolden bağımsızdır, TCP ve UDP'yi destekler. HTTP dışı trafik için veya daha yüksek anonimlik istendiğinde sıklıkla tercih edilir.
- Yapılandırdığınız proxy türünün, proxy sunucusunun yeteneklerine ve göndermeyi planladığınız trafik türüne uygun olduğundan emin olun.
Kimlik doğrulama
Kimlik doğrulamalı proxy'ler için her zaman doğru kimlik bilgilerini verin. Yanlış yapılandırılmış kimlik doğrulama, proxy bağlantı hatalarının yaygın bir kaynağıdır. reqwest için Proxy::basic_auth() kullanın. hyper veya özel connector'lar için Proxy-Authorization başlığını uygun kimlik bilgileriyle (örneğin Base64 kodlanmış username:password) gönderin.
Performansa etkisi
Proxy kullanmak ağ yoluna ek bir sıçrama ekler ve bu gecikmeyi artırabilir. Performans yükü; proxy sunucusunun konumuna, yüküne ve istemciniz, proxy ile hedef sunucu arasındaki ağ koşullarına bağlıdır.
Güvenlik değerlendirmeleri
- Güven: yalnızca güvendiğiniz proxy sunucularını kullanın. Kötü niyetli proxy'ler trafiğinizi inceleyebilir, değiştirebilir veya kaydedebilir.
- HTTPS proxy'leme:
CONNECTyöntemiyle bir HTTPS proxy kullandığınızda proxy bir tünel kurar ve istemciniz TLS el sıkışmasını doğrudan hedef sunucuyla yapar. Yani proxy, HTTPS trafiğinizin içeriğini çözemez (istemcinizde kendi kök sertifikası kurulu bir "man-in-the-middle" proxy olmadığı sürece).reqwestbunu varsayılan olarak güvenli biçimde yönetir. - Proxy başlıkları: proxy'ler sıklıkla
X-Forwarded-Forgibi başlıklar ekler. Anonimlik öncelikliyse buna dikkat edin.
Ortam değişkenleriyle etkileşim
reqwest, HTTP_PROXY, HTTPS_PROXY ve NO_PROXY ortam değişkenlerine otomatik olarak uyar. Bu davranışı geçersiz kılmanız gerekirse ClientBuilder::no_proxy() kullanın veya proxy'leri açıkça yapılandırın. hyper'ı doğrudan kullanırken, istiyorsanız bu ortam değişkenlerini kendiniz ayrıştırıp uygulamanız gerekir.
