BeginRead flusso di annullamento .NET
Domanda
Non sono stato in grado di trovare un modo per annullare / terminare l'operazione di lettura asincrona dopo l'esito positivo di HttpWebRequest. Non è possibile impostare il timeout, ThreadPool.RegisterWaitForSingleObject non funziona anche. E chiudere il socket sottostante non è un'opzione, perché né HttpWebRequest / Reponse forniscono l'accesso ad esso.
Modifica:
Purtroppo questo approccio suggerito da Sunny funziona solo per HttpWebRequest.BeginGetResponse. Per lo stream che si ottiene dopo GetResponseStream () per qualche motivo RegisterWaitForSingleObject non funziona: il callback non viene mai chiamato.
La situazione è la seguente: Ho ottenuto un'applicazione che utilizza HttpGetRequest. Viene creato utilizzando l'esempio MSDN predefinito per httpwebrequest asincrono. Ottenere una risposta funziona come un incantesimo. Ma in rare occasioni il server a cui la mia httpwebrequest si sta connettendo si dimentica di chiudere il socket. Quindi sono appeso a una lettura infinita di BeginRead.
In alcune rare occasioni, l'altro server dimentica
Soluzione
Perché non RegisterWaitForSingleObject? Puoi usarlo per il timeout e nel gestore puoi chiamare request.Abort ().
Ecco un esempio . A proposito, ho usato un approccio simile prima di trovare questo articolo in passato e ha funzionato come un fascino.
NOTA: la vera fine dell'operazione avverrà sul successivo Stream.Read (solo la richiesta / risposta era asincrona) o Stream.EndRead (se anche la lettura è asincrona). È ancora necessario acquisire l'eccezione generata nel gestore EndXXXX.
EDIT: se RegisterWaitForSingleObject non viene mai chiamato, allora hai un altro problema, che è molto probabilmente un ThreadPool che non ha abbastanza thread gratuiti. Il callback per l'oggetto RegisterWaitForSingle viene chiamato su un thread ThreadPool e se non esiste un thread libero nel pool, non verrà mai chiamato. Hai alcune soluzioni:
- Rendi le tue pagine asincrone. Perché ? How .
- Modifica le max thread nel pool .
In ogni caso, aumentare le dimensioni del pool non ti aiuterà molto. Devi ispezionare il tuo codice per individuare eventuali perdite di risorse (stream) e assicurarti di non solo chiamare request.Abort (), ma anche chiudere la risposta. Assicurati che nei tuoi callback usi il metodo EndXXX corretto, ecc.
I nazdrave :)