Come risolvere i problemi con i cookies tramite proxy
I cookies sono una delle fonti più comuni di errori quando si lavora con i proxy. Le sessioni si interrompono, l'autorizzazione si blocca, i dati vanno persi. In questo articolo scopriremo perché accade e come configurare correttamente la gestione dei cookies per un funzionamento stabile.
Perché i cookies vanno persi quando si utilizza un proxy
Quando invii una richiesta tramite un proxy, tra il tuo client e il server di destinazione si interpone un nodo intermedio. Questo crea diversi problemi:
- Indirizzi IP diversi per una stessa sessione. Il server potrebbe notare che le richieste provengono da indirizzi diversi e rifiutare i cookies come sospetti.
- Perdita di intestazioni Set-Cookie. Una configurazione non corretta del proxy potrebbe non trasmettere le intestazioni Set-Cookie al client.
- Mancata corrispondenza del dominio e del percorso. Se il proxy riscrive l'intestazione Host, i cookies potrebbero non salvarsi a causa della mancata corrispondenza del dominio.
- Assenza di mantenimento dello stato. Se invii ogni richiesta separatamente senza salvare i cookies, la sessione andrà persa.
Che cos'è un cookie jar e come utilizzarlo
Un cookie jar è un archivio di cookies che gestisce automaticamente il loro invio e la loro ricezione. Invece di aggiungere manualmente le intestazioni Cookie in ogni richiesta, consenti alla libreria di farlo automaticamente.
La maggior parte dei client HTTP ha il supporto integrato per cookie jar:
import requests
from requests.cookies import RequestsCookieJar
# Creiamo un jar per archiviare i cookies
jar = RequestsCookieJar()
# Prima richiesta — il server invierà Set-Cookie
response1 = requests.get(
'https://example.com/login',
cookies=jar,
proxies={'https': 'http://proxy.example.com:8080'}
)
# I cookies vengono automaticamente salvati nel jar
print(jar)
# Seconda richiesta — i cookies verranno inviati automaticamente
response2 = requests.get(
'https://example.com/dashboard',
cookies=jar,
proxies={'https': 'http://proxy.example.com:8080'}
)
Senza jar, avresti dovuto analizzare manualmente Set-Cookie e aggiungerli alla richiesta successiva — questo è inaffidabile e ingombrante.
Salvataggio dei cookies tra le richieste
Se il tuo script funziona a lungo o hai bisogno di ripristinare la sessione dopo un riavvio, salva i cookies in un file:
import requests
from http.cookiejar import LWPCookieJar
# Creiamo un jar con salvataggio in file
jar = LWPCookieJar('cookies.txt')
# Carichiamo i vecchi cookies se esistono
try:
jar.load(ignore_discard=True, ignore_expires=True)
except FileNotFoundError:
pass
# Utilizziamo il jar nelle richieste
response = requests.get(
'https://example.com/login',
cookies=jar,
proxies={'https': 'http://proxy.example.com:8080'}
)
# Salviamo i cookies aggiornati
jar.save(ignore_discard=True, ignore_expires=True)
I flag ignore_discard=True e ignore_expires=True consentono di salvare anche i cookies temporanei.
Problemi con l'associazione al dominio dei cookies
I cookies hanno un attributo Domain che determina per quali domini verranno inviati. I problemi sorgono se:
- Il proxy riscrive l'Host. Se il proxy modifica l'intestazione Host, il cookie jar potrebbe rifiutare il cookie come appartenente a un altro dominio.
- I sottodomini non corrispondono. Un cookie per
example.compotrebbe non essere inviato aapi.example.com. - Il percorso non corrisponde. Un cookie per
/apinon sarà inviato a/admin.
Controlla gli attributi del cookie in questo modo:
import requests
response = requests.get(
'https://example.com',
proxies={'https': 'http://proxy.example.com:8080'}
)
# Stampiamo tutti i cookies
for cookie in response.cookies:
print(f"Name: {cookie.name}")
print(f"Value: {cookie.value}")
print(f"Domain: {cookie.domain}")
print(f"Path: {cookie.path}")
print(f"Secure: {cookie.secure}")
print(f"HttpOnly: {cookie.has_nonstandard_attr('HttpOnly')}")
print("---")
Se il Domain è troppo ristretto, prova a trasmettere esplicitamente i cookies invece di affidarti alla gestione automatica:
headers = {
'Cookie': 'session_id=abc123; user_token=xyz789'
}
response = requests.get(
'https://example.com/api',
headers=headers,
proxies={'https': 'http://proxy.example.com:8080'}
)
Flag Secure e HttpOnly
Il flag Secure significa che il cookie viene inviato solo su HTTPS. Se utilizzi un proxy HTTP per accedere a una risorsa HTTPS, assicurati che la connessione al proxy sia protetta o che il proxy inoltri correttamente HTTPS.
Il flag HttpOnly impedisce l'accesso al cookie da JavaScript. Questo non influisce sull'invio del cookie nelle richieste, ma è importante ricordare che non potrai leggere tali cookies dal browser.
Quando lavori con proxy residenziali, assicurati che:
- Il proxy supporti HTTPS (metodo CONNECT)
- I certificati siano validi (non utilizzare
verify=Falsein produzione) - Le intestazioni non vengano riscritte dal proxy
Esempi pratici con codice
Esempio 1: Login con salvataggio della sessione
import requests
from requests.cookies import RequestsCookieJar
jar = RequestsCookieJar()
proxy = 'http://proxy.example.com:8080'
# Login
login_response = requests.post(
'https://example.com/login',
data={'username': 'user', 'password': 'pass'},
cookies=jar,
proxies={'https': proxy}
)
if login_response.status_code == 200:
print("Login riuscito")
# Utilizziamo la sessione salvata
dashboard = requests.get(
'https://example.com/dashboard',
cookies=jar,
proxies={'https': proxy}
)
print(dashboard.text)
Esempio 2: Elaborazione di più richieste
import requests
from http.cookiejar import LWPCookieJar
import time
jar = LWPCookieJar('session.txt')
try:
jar.load(ignore_discard=True)
except:
pass
proxy = 'http://proxy.example.com:8080'
urls = [
'https://example.com/page1',
'https://example.com/page2',
'https://example.com/page3'
]
for url in urls:
response = requests.get(
url,
cookies=jar,
proxies={'https': proxy},
timeout=10
)
print(f"{url}: {response.status_code}")
jar.save(ignore_discard=True)
time.sleep(1) # Non sovraccaricare il server
Esempio 3: Trasmissione esplicita dei cookies in caso di problemi
import requests
proxy = 'http://proxy.example.com:8080'
# Se la gestione automatica non funziona
cookies_dict = {
'session_id': 'abc123def456',
'user_pref': 'dark_mode'
}
headers = {
'User-Agent': 'Mozilla/5.0...',
'Cookie': '; '.join([f"{k}={v}" for k, v in cookies_dict.items()])
}
response = requests.get(
'https://example.com/api/data',
headers=headers,
proxies={'https': proxy}
)
print(response.json())
Debug dei problemi con i cookies
Se i cookies non funzionano, utilizza questi strumenti:
| Strumento | Scopo |
|---|---|
requests.Session |
Gestisce automaticamente i cookies per tutte le richieste nella sessione |
logging |
Abilita DEBUG per requests per visualizzare tutte le intestazioni |
Fiddler / Charles |
Intercetta il traffico e visualizza le intestazioni Set-Cookie e Cookie |
curl -v |
Testa lo stesso tramite proxy dalla riga di comando |
Abilita la registrazione per il debug:
import logging
import requests
logging.basicConfig(level=logging.DEBUG)
# Ora tutte le richieste stamperanno intestazioni e cookies
response = requests.get(
'https://example.com',
proxies={'https': 'http://proxy.example.com:8080'}
)
Verifica che il proxy non blocchi i cookies:
curl -v -x http://proxy.example.com:8080 https://example.com
# Guarda le intestazioni:
# Set-Cookie: ... (dovrebbero essere presenti)
# Cookie: ... (dovrebbero essere inviati nella richiesta successiva)
Consiglio: Se utilizzi proxy residenziali, ricorda che possono ruotare l'IP tra le richieste. Assicurati che la tua logica di gestione dei cookies tenga conto di questo — alcuni server rifiutano le richieste da IP diversi nella stessa sessione.
Conclusioni
I problemi con i cookies quando si lavora tramite proxy si risolvono con una configurazione corretta:
- Utilizza un cookie jar per la gestione automatica dei cookies
- Salva i cookies tra le richieste in un file
- Controlla l'associazione al dominio e gli attributi Path
- Assicurati del supporto HTTPS del proxy
- Utilizza il debug per identificare i problemi
Per attività di automazione e scraping dove è necessario un funzionamento affidabile delle sessioni tramite proxy, i proxy residenziali con supporto HTTPS e gestione dei cookies sono appropriati. Inizia con un semplice cookie jar e passa a schemi più complessi solo se necessario.