Currently, there are two ways exceptions are handled in web2py:
If the controller/view does *NOT* use try: except:, and an exception is
raised, then it is very helpfully logged in the ticket system, and a
somewhat-useful message (that can be customized a little, see e.g.
<http://www.web2py.com/book/default/chapter/04#Routes-on-Error>), is given
as a reply. The link in this message is, in general, useful to the
developer, but not to the end user of the app (who will usually be unable
to follow the ticket link). It is very likely to break the user's flow of
work, as this message is not actually an app view/controller.
If the controller/view *DOES* use try: except: to catch errors, then any
reply could be given to the user, but everything needs to be implemented in
the app, including db rollback, logging of problems, etc.
It would be great if there was a *middle ground* in between them, where a
ticket could be generated for the developer, logging everything that can be
useful to diagnose the problem, but to let processing continue. For
example, I would like to be able to do something like this:
try:
# verify that the next insert will succeed
table.insert(**record)
except integrity_error, e:
# db.rollback() can be called here if needed.
ticket_id = gluon.user_ticket(e)
return dict(flash_message = "Unfortunately, we were unable to complete
the request even though we should have. Our developer has been notified.
You may use incident code %s to inquire about this" %
make_a_user_facing_code(ticket_id))
return dict(flash_message="Completed successfully")
That is, logically there's a bug here, and I would love to have the ticket
to diagnose the problem, so I'm tempted to not handle the exception at all.
However, I do want to detect the problem and keep the user within the
app-flow.
This situation appears quite often If you have a database model whose
consistency cannot be encoded into SQL constraints that are automatically
enforced - and it is thus possible that a bug in one place (creating an
inconsistent database) manifests in another place. While developing,
web2py's default tickets are great. But on deployment, I'd rather have
friendlier logic-error handling, without giving up the snapshot/ticketing
system that web2py provides.
Looks like it's quite easy to do already - something like:
def user_ticket(e):
from restricted import RestrictedError
ticket = None
try: raise RestrictedError('user-ticket')
except RestrictedError, e: ticket = e.log(request)
return ticket
would probably work, except that it uses web2py internals that are likely
to change. Is there an official way to get this kind of functionality? If
not, do other people think this would be a useful addition?