55

My code is:

InputStream confFile=classLoader.getResourceAsStream("myconffile.properties");

In docs:

The close method of InputStream does nothing.

Does it mean that I don't need close InputStream?

JasonMArcher
  • 14,195
  • 22
  • 56
  • 52
user710818
  • 23,228
  • 58
  • 149
  • 207

2 Answers2

42

You do need to close the input Stream, because the stream returned by the method you mention is actually FileInputStream or some other subclass of InputStream that holds a handle for a file. If you do not close this stream you have resource leakage.

Boris Strandjev
  • 46,145
  • 15
  • 108
  • 135
  • 1
    I don't think it will be a FileInputStream in most cases. – Michael Borgwardt Mar 03 '12 at 16:53
  • I should investigate in that, regretfully I do not have any java instance at hand at the moment. However, I agree with you that it is holding a file handle. – Boris Strandjev Mar 03 '12 at 17:00
  • Won't the finalize() method close the resource stream for you? – Ryan Amos Mar 03 '12 at 17:07
  • 1
    @Ryan Amos: yes - when and if it runs. Which can be an arbitrarily long time later, time enough for you to run out of file handles. Or for a delete or rename operation to fail. Something that actually happened to me (not with a resource stream): I wanted to modify the EXIF metadata of image files. That involves creating a copy of the file with the update meatada, then deleting the original file and renaming the copy to the original file's name. Unfortunately, the EXIF manipulation library did not close the input stream on the original file, which caused the delete to fail (most of the time). – Michael Borgwardt Mar 03 '12 at 17:41
  • @MichaelBorgwardt you are correct it seems to be `ByteArrayInputStream` in my experiment. – Boris Strandjev Mar 03 '12 at 18:21
  • @MichaelBorgwardt While I agree that you need to call close(), I think your example is a little extreme. Using an external library is definitely a situation in which you need to call close, but as long as you're using up plenty of memory and not a lot of file handles, the internal libraries should take care of you. Now, it is definitely bad practice NOT to call close, and it can be disastrous if you're making tons of file connections, but I think that finalize() will fix it for just 1 or 2 file streams. However, boris says we're talking about byte arrays streams now :P – Ryan Amos Mar 03 '12 at 20:36
  • @Ryan Amos: I'm not sure you got the point of my example: the external library was the one failing to call close(), and it caused my program to fail because a single stream still open prevented a file from being deleted. Having the stream closed by finalize() is what made this error possible in the first place because it hides it sometimes. finalize() is a design error that should never have existed. – Michael Borgwardt Mar 03 '12 at 20:44
  • I happen to be staring right now at a list of 1093 open file descriptors as a result of not calling close when using getResourceAsStream(). Relying on finalize() is not advisable. – brandon Apr 17 '14 at 05:42
24

No, it does not mean that - because InputStream is an abstract class, and getResourceAsStream() returns a concrete subclass whose close() method does something - most importantly free a file handle.

Michael Borgwardt
  • 342,105
  • 78
  • 482
  • 720