Ever wondered if there was a way to stop Zope from barfing error messages all over your screen when one of your scripts crashes and burns? Well, guess what - there is! Meet the and tags, which can be used to trap and resolve errors in script execution.
You can also write specific exception handlers for different types of exceptions, by noting the exception type within the tag. Consider the following handler, which only handles KeyError exceptions:
Of course, this handler will now only restrict its activities to KeyError exceptions. All other errors will be routed via the default Zope error handler.
You can trap more than one exception, and handle each one in a different way, by using multiple <dtml-except> statements within a single <dtml-try> block.
<dtml-try>
execute this block<dtml-except err1>execute this block if exception "err1" is raised<dtml-except err2>execute this block if exception "err2" is raised... and so on ...<dtml-else>execute this block if no exceptions are raised</dtml-try>
If an exception is encountered while running the code within the <dtml-try> block, Zope stops execution of the <dtml-try> block at that point and begins checking each <dtml-except> block to see if there is a handler for the exception. If a handler is found, the code within the appropriate <dtml-except> block is executed; if not, control either moves to the parent <dtml-try> block, if one exists, or to the default handler.
Once the <dtml-try> block has been executed and assuming that the program has not been terminated, the lines following the <dtml-try> block are executed.
In case you're wondering, the <dtml-else> branch in the block above is executed only if no exceptions are raised. It's optional, though, so only include it if you need to.
Take a look at the next example, which demonstrates how this works:
<dtml-try>
<dtml-var alpha> divided by <dtml-var beta> is <dtml-varexpr="_.int(alpha)/_.int(beta)" >.<br><dtml-except KeyError><b>No value assigned to the variable: <dtml-var error_value></b><dtml-except ZeroDivisionError><b>Division by zero</b><dtml-except ValueError><b>Illegal value: <dtml-var error_value></b><dtml-else><i>No errors encountered.</i></dtml-try>
Save this code in a DTML Document named "ExceptionallyYours", and test it by passing it values for the variables "alpha" and "beta" on the URL string, via the GET method (you can also use a form and submit values for these variables via POST). For example, if you access the URL
Since no values have been passed for the variables, Zope barfs with a KeyError, which is caught by the exception handler, and the following message is displayed:
No value assigned to the variable: alpha
What about if you pass an illegal value, like a very large integer? Try the following URL,
and watch as Zope generates a ZeroDivisionError, and an appropriate message.
Division by zero
If you'd like to save yourself some keystrokes, you also have the option of handling multiple exceptions within a single <dtml-except> block, by specifying a list of exception types separated by spaces. Consider the following rewrite of the previous example, which uses the same exception handler for both ZeroDivisionError and ValueError exceptions:
<dtml-try>
<dtml-var alpha> divided by <dtml-var beta> is <dtml-varexpr="_.int(alpha)/_.int(beta)" >.<br><dtml-except KeyError><b>No value assigned to the variable: <dtml-var error_value></b><dtml-except ValueError ZeroDivisionError><b>Illegal value: <dtml-var error_value></b><dtml-else><i>No errors encountered.</i></dtml-try>