Change withTransactionModeRetry to allow the user to determine when to retry

withTransactionModeRetry previously would retry if a not_serializable exception
was thrown, but this can be a little too fine grained. There are cases when a
transaction should be retried when a unique_violation occurs (e.g., a race
condition occurs). This allows users to tune the retrying semantics to the
needs of their application.

-----

My specific motivation here can be seen at http://dba.stackexchange.com/questions/26905/how-do-i-implement-insert-if-not-found-for-transactions-at-serializable-isolatio. Basically, I use the serializable isolation level, and do handle the unique condition, but the race condition means that the whole transaction must be retried. Instead of copying and pasting your logic, I've made it a little more general. Would love feedback on whether this makes sense, whether we should break the API or enhance it with a new method, and if my coding style is OK :)