Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Should WebException.Response.GetResponseStream() be close / disposed?

When I catch a .NET WebException, should I close / dispose the Response.GetResponseStream()?

The MSDN example does not close or dispose anything in the exception.

Many SO answers recommend disposing the response and / or the stream.

I disposed the stream and this caused big problems. Because GetResponseStream() (always? / sometimes?) returns the same instance. So when I get the response stream and then dispose it, then maybe rethrow the exception to another layer that also gets the response stream it will be already disposed and unreadable and throw more exceptions because of that.

like image 598
Peter Avatar asked Oct 01 '15 15:10

Peter


2 Answers

A short answer is that you don't have to dispose it although it is a good exercise to dispose any IDisposable objects that you own.

In fact, trying to dispose WebException.Response or the stream returned from it would cause problems you mentioned since you may encounter code attempting to read its properties in upper call chain's exception handler.

The reason why it is safe not to dispose it is because HttpWebRequest internally makes a memory stream from the network stream before it throws WebException, and the underlying network stream has already been closed/disposed. So it doesn't really have any unmanaged resource associated at that point. This I assume was a decision to make it easier to handle the exception.

Unfortunately MSDN documentation doesn't have any explanation about this behavior. Technically the implementation can change in future causing problem to your code not disposing the HttpWebResponse and/or associated stream you get from WebException, but it is highly unlikely that this behavior would change the implementation given many applications depend on current behavior.

I have to add though that it is a good practice that you should dispose IDisposable objects you own. If possible, use HttpClient class instead so that you don't have to deal with this situation at all. If you can't, consider handling the WebException yourself and throw new type of exception that does not expose WebException to the caller of your code so that you don't run into a situation where a caller is trying to access WebException.Response after you dispose it.

Disclaimer: I work for Microsoft, but this does not represent my employer or .NET Framework team's view. No warranty implied.

like image 102
Sunghwa Jin Avatar answered Sep 20 '22 15:09

Sunghwa Jin


You should dispose of that stream because it might hold resources. But only dispose of it when you are done with it. Simply stop disposing it before you no longer need the stream. Make the last user of the stream dispose of it.

Probably, you should call GetResponseStream() only once and pass the stream around explicitly so that it is clear that it's the same stream.

like image 30
usr Avatar answered Sep 21 '22 15:09

usr