Domanda

I'm inserting the lines of a file into a database using plain JDBC. For that, I'm using Guava's LineProcessor, along with Closer. However that interface can only throw an IOException with its method processLine(String).

This doesn't feel right when an SQLException is thrown. So far I wrap the SQLException in an unchecked exception, but I'm wondering if I should not wrap it in an IOException as the interface doesn't mention anything about another exception. Simply return false? This seems more wrong than anything.

Technically, I think it was an oversight from Guava's team not to explicitly mention what behavior is expected when a checked exception occurs whether in the wiki or the Javadoc.

So how should I actually use LineProcessor when I'm encountering checked exceptions?

È stato utile?

Soluzione

Wrapping the SQLException into an IOException is a valid solution, because you are reading from a file (input) and writing to a database (output). The root cause of the IOException would be the SQLException.

You are correct though on the documentation, since it only mentions that the LineProcessor is meant to be used with the readLines methods. It doesn't explicitly say what behaviour is expected when an exception occurs. The documentation of readLines, however, mentions that an IOException should be thrown when an I/O error occurs.

Note that the LineProcessor is also designed to be able to collect a result and return it using the LineProcessor#getResult method, so you can always fully read the file first and return a result (if your files aren't too big). This will allow you to split the responsibilities of reading/processing the lines and the insertion of the data in your database.

Altri suggerimenti

This is an issue that all callback-based APIs have with checked exceptions. You can make the callback able to throw any type of Exception, but then the methods that use the callback also have to throw Exception, which is a pain to users (especially if the actual callback doesn't throw any exception at all!). You can also parameterize the callback with a type of checked exception (e.g. LineProcessor<T, X extends Throwable>) and make the method on it able to throw an X, but what if there are two or three types of checked exceptions it could throw? It's just a mess.

In this case, IOException is allowed because A) it's the most likely type of exception most callbacks would have a need to throw, and B) (more importantly) the methods that use LineProcessor (e.g. CharStreams.readLines(Readable, LineProcessor<T>) already necessarily have to be able to throw IOException since they do I/O, so it's no extra burden on the user if the LineProcessor can also throw IOException.

The easiest way to handle this might simply be to create an UncheckedSQLException class whose cause must be a SQLException, and then throw that from your LineProcessor and catch it and unwrap it wherever you use that LineProcessor.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top