2010-07-12 13 views
29

Sto scrivendo un client REST per Elgg utilizzando python, e anche quando la richiesta ha esito positivo, ho ottenere questo in risposta:Python httplib ResponseNotReady

Traceback (most recent call last): 
    File "testclient.py", line 94, in <module> 
    result = sendMessage(token, h1) 
    File "testclient.py", line 46, in sendMessage 
    res = h1.getresponse().read() 
    File "C:\Python25\lib\httplib.py", line 918, in getresponse 
    raise ResponseNotReady() 
httplib.ResponseNotReady 

Guardando l'intestazione, vedo ('content-length ',' 5749 '), quindi so che c'è una pagina lì, ma non riesco a usare .read() per vederlo perché si presenta l'eccezione. Cosa significa ResponseNotReady e perché non riesco a vedere il contenuto che è stato restituito?

+0

Stai riutilizzando la connessione? – ChristopheD

+0

Infatti. Stranamente, a volte funziona e altre volte no. Non riesco a determinare quale comportamento lo determini. – directedition

risposta

35

Assicurarsi di non riutilizzare lo stesso oggetto da una connessione precedente. Si verrà colpiti quando il server keep-alive termina e il socket si chiude.

+1

Generalmente, di regola, non mi preoccupo di provare a riutilizzare gli oggetti HttpRequest a meno che non avessi bisogno di prestazioni specifiche. Solo single-shot 'em – rossipedia

+0

Nel mio caso, l'aggiunta di 'preload_content = False' ha risolto il problema. Ecco lo snippet: 'http = urllib3.PoolManager (threadsNo, maxsize = threadsNo, block = True); request = http.request ('GET', queryUrl, preload_content = False) 'Sembra che' request.release_conn() 'non rilasci realmente l'oggetto di connessione precedente a meno che il parametro precedente non venga passato a http.request. Maggiori dettagli qui: https://urllib3.readthedocs.org/en/latest/pools.html – dex

2

stavo correndo in questa stessa eccezione oggi, utilizzando questo codice:

conn = httplib.HTTPConnection(self._host, self._port) 
    conn.putrequest('GET', 
     '/retrieve?id={0}'.format(parsed_store_response['id'])) 
    retr_response = conn.getresponse() 

non ho notato che stavo usando putrequest piuttosto che request; Stavo mescolando le mie interfacce. ResponseNotReady viene generato perché non ho ancora inviato la richiesta.

49

Le risposte precedenti sono corrette, ma c'è un altro caso in cui è possibile ottenere tale eccezione: è se si eseguono più richieste senza leggere completamente la risposta intermedia.

Per esempio:

conn.request('PUT',...) 
conn.request('GET',...) 
# will not work: raises ResponseNotReady 

conn.request('PUT,...) 
r = conn.getresponse() 
r.read() # <-- that's the important call! 
conn.request('GET',...) 
r = conn.getresponse() 
r.read() # <-- same thing 

e così via.

+0

Questo è quello che cercavo .read() così posso riutilizzare la mia connessione. – schwiz

+0

è .read() costoso. Cosa succede se non mi interessa la risposta? Posso farlo funzionare più velocemente?> – SoulMan

+2

@ronnefeldt, i documenti Python su https://docs.python.org/3/library/http.client.html hanno la seguente nota: "Notare che è necessario aver letto l'intera risposta prima puoi inviare una nuova richiesta al server. ". – mvsagar

0

Inoltre, errori di questo tipo possono verificarsi quando il server invia una risposta senza un'intestazione Content-Length, che bloccherà lo stato del client HTTP se Keep-Alive viene utilizzato e un'altra richiesta viene inviata sullo stesso socket.

0

Ciò può verificarsi anche se un firewall blocca la connessione.

Problemi correlati