I'm looking at the scala-arm library, prompted by this answer, and it looks great for managing resources in most contexts.
There's one context, though, that it doesn't, on first glance, appear to handle: that of "handing off" a resource to another resource. This comes up frequently when working with I/O:
for (fin <- managed(new FileInputStream(file));
// almost what we want, except see below
gzip <- managed(new GZIPInputStream(fin));
src <- managed(Source.fromInputStream(gzip))) {
/* some fancy code */
}
Now, the problem is this: If gzip
is successfully created, then it is responsible for closing fin, and fin should not be closed (update: this isn't quite right - double-close is fine; see accepted answer). The alternative, though:
for (src <- managed(Source.fromInputStream(
new GZIPInputStream(new FileInputStream(file))))) {
/* some fancy code */
}
is not quite correct - if there is an (admittedly unlikely) error in the GZIPInputStream
constructor, the FileInputStream
is not closed. Ditto for fromInputStream
.
Does scala-arm (or some other package) provide a facility for handling this cleanup safely that I haven't found yet?