quote:Original post by Mayrel
But the caller of the caller might .void doFooWithDB (Database db){ while (true) { try { Database db = new Database; FooConsumer fc = new FooConsumer(new FooProvider()); fc.consume(); break; } catch (DBConnectionDropped e) { db.reconnect(); } }}
We cannot check that the DBConnectionDropped exception is being handled.
Using a FooProvidingException as defined in my previous post, the catch block would become :
catch(FooProvidingException fpe){ //if we can't make assumption on FooProvider implementation //we handle only the fact we can't get a Foo, not the reason //for example : fpe.printStackTrace(); System.exit(-1); //else we know what implementation is used (here FooProviderDB) //we get the encapsulated exception and handle it properly Exception e = fpe.getException(); if(e instanceof DBConnectionDropped) { ... }}
quote:Original post by Mayrelquote:
The caller should react to the fact that he can't get its Foo object and not care about possible resource leak (for example).
You have to be joking? I should write a program that doesn't care about resource leaks?
No, I wasn't clear enough. Potential resource leaks should be handled by the FooProvider implementation, since it knows how stuff is made and how it should be cleaned.
A generic method doFoo(FooProvider fp) is not equipped to deal with a SQLException, a FileNotFoundException or a premature EOF.
However it knows that without Foo it can't work properly. So doFoo should contain the logic to handle the fact it can't get its Foo object, while resource leaks should be handled directly by the FooProvider impl.
With that in mind, I would modify the code from your FooProvider as follow :
public Foo get() throws FooProviderException{ Foo f; try { Foo f = new Foo(rs.getField("Name"), rs.getField("Height")); rs.moveNext(); } catch(DBException e) { //clean resources and state ... throw new FooProviderException(msg,e); } return f;};
[edited by - overnhet on February 29, 2004 3:37:23 PM]