Q: Exception design questions

Myron Alexander someone at somewhere.com
Sat Jun 16 05:29:15 PDT 2007


eao197 wrote:
> IMHO, the following variant is more preferable for me, because I can 
> easily find all places where an exception is thrown simply by `grep 
> throw` (and `throw` keywords is highlighted in editors):
> 
> throw ((new SqlProgrammingException (
>     "Invalid bind type. Mixing single and multiple value rows. "
>     "The first argument type is other than Box[], thus it is "
>     "assumed that the rest of the arguments are single value "
>     "rows."))
>     .setSql (operation)
>     .setProperty ("ValueRow", i)
>     .setProperty ("ValueType", t));
> 

When I first came across that style, there was a reason for a .raise 
method. I cannot recall the reason, just that it was used. I do prefer 
using throw so I have decided to drop raise.

I forgot to show an example of why I chose a property bag mechanism. 
Here is an example:

>    try {
>       try {
>          // Within position bind method. The name of the bind parameter is not
>          // known, only the position.
>          throw (new SqlProgrammingException ("Unable to bind parameter value."))
>             .setVendorMsg ("Data type mismatch")
>             .setVendorCode (20)
>             .setSqlState ("2200G")
>             .setSql ("SELECT * FROM TABLE WHERE A = :somevalue")
>             .setProperty ("BindPosition", 1)
>             ;
> 
>       } catch (SqlException e) {
>          // Within name lookup method. The name lookup method finds the position
>          // of a parameter based on the name. It then calls the position
>          // bind method.
>          e.setProperty ("BindName", "somevalue");
>          throw e;
>       }
> 
>    } catch (SqlProgrammingException e) {
>       writefln ("%s: \n---\n%s\n----", typeid(typeof(e)), e);
> 
>    } catch (SqlDatabaseException e) {
>       writefln ("%s: \n---\n%s\n----", typeid(typeof(e)), e);
> 
>    } catch (Exception e) {
>       writefln ("%s: \n---\n%s\n----", typeid(typeof(e)), e);
>    }

In this example, when the exception is raised, I do not know the name of 
the parameter, just it's position. The name is known higher up the call 
hierarchy. With the property mechanism, I can then add the name and 
rethrow. Without the property mechanism, I would either have to create a 
new exception class, or recreate the exception with the information 
appended to the message string.

Another way to do the above would be to have the type mismatch error in 
a SqlDataException, wrapped in a SqlBindException, which is a 
SqlProgrammingException. The data exception would contain specific 
information about the type expected and the type received, the sql state 
and vendor code/message, and the sql statement. The bind exception would 
have the position and name. So the print out would be like:

> Error: Unable to bind parameter value
> 
> BindName: somevalue
> BindPosition: 1
> 
> caused by: Data type mismatch
> 
> DataTypeExpected: numeric
> DataTypeReceived: string
> Sql: SELECT * FROM TABLE WHERE A = :somevalue
> SqlState: 2200G
> VendorCode: 20
> VendorMsg: Data type mismatch

Can anyone point me to Walter's design explanation for how Error and 
Exception are supposed to be structured. I'm guessing that Walter 
intends Errors to be more generic (problem domain rather than individual 
problem) and that Exception to be very specific to the exact problem.

I'm also considering moving away from the PEP249 exception hierarchy and 
going towards the JDBC 4 design based on sql states.

I'm experimenting here, I honestly have no clue what I am doing. Like a 
rat in a maze, I can smell the cheese but can't see it.

Any help and thoughts would help alot.

Thanks ahead,

Myron.
dprogramming...myron...alexander...com
replace the first ... with @, remove the second, and replace the third 
with ".".



More information about the Digitalmars-d mailing list