try-with-resources & AutoCloseable
try-with-resources & AutoCloseable
Every time your code opens a file, a network connection, a database connection, or any other external resource, that resource must be closed when you are done with it. Forgetting to close resources is one of the most common bugs in Java: it causes memory leaks, file-handle exhaustion, and locked files that nothing else can open.
Java 7 introduced the try-with-resources statement to solve this problem automatically. Instead of writing close logic yourself, you declare the resource inside the try parentheses and Java guarantees it will be closed — even if an exception is thrown.
The Problem: Manual Resource Cleanup Is Error-Prone
Before try-with-resources, you had to close resources in a finally block. Even careful code had subtle bugs:
This is ten lines of boilerplate just to close one resource safely. If close() also throws, the original exception is swallowed — a very hard bug to track down.
The Solution: try-with-resources
Declare the resource in parentheses after try. Java automatically calls close() at the end of the block, whether the block exits normally or via an exception:
The compiler rewrites this into a version that correctly handles every edge case, including suppressed exceptions.
close() is always called — even when an exception is thrown inside the try block, and even when there is no catch clause at all.
Multiple Resources in One Statement
You can declare multiple resources separated by semicolons. They are closed in reverse order of declaration — the last one opened is the first one closed:
The AutoCloseable Interface
Try-with-resources works with any class that implements AutoCloseable (or its subinterface Closeable). The interface has exactly one method:
All standard Java I/O classes (InputStream, OutputStream, Reader, Writer, Scanner, Connection, PreparedStatement, etc.) already implement this interface. That is why they all work in try-with-resources out of the box.
Writing Your Own AutoCloseable Class
You can make any class work with try-with-resources by implementing AutoCloseable. A common example is a class that wraps a network connection or a temporary file:
Now you can use it exactly like any built-in resource:
close() to be called more than once without throwing an error. Use a boolean flag (like open above) to guard against double-close.
Suppressed Exceptions
What happens when the try body throws an exception and close() also throws? In old finally-block code, the second exception would hide the first. Try-with-resources handles this correctly: the exception from the try body is the primary exception, and the one from close() is attached to it as a suppressed exception.
You can retrieve suppressed exceptions with getSuppressed(), which returns a Throwable[]. No information is lost.
Reading a File Line by Line — A Realistic Example
In practice, the most common use of try-with-resources is reading text files with BufferedReader:
BufferedReader automatically closes the wrapped FileReader too, because the close call propagates through the chain. Declaring both separately could actually close the inner reader twice.
Summary
Try-with-resources is the modern, correct way to manage any resource that must be closed. Declare resources in the try() parentheses, implement AutoCloseable for your own classes, and let the JVM handle cleanup. You get shorter code, fewer bugs, and correct suppressed-exception handling — all for free.