Catch SQLExceptoin then use SQLException.getSQLState() and compare it to see if it's what you want.
catch (SQLException ex) {
final String ss = ex.getSQLState();
//... blah blah ...
}
See PostgreSQL error codes for SQLState details. (While most of the state categories and codes are standard across DBs not all DBs implement them the same way and throw them at the same times, and most DBs have extras that are DB specific).
There is no way to catch an exception based on the SQLState. You must, unfortunately, catch it, and if it's not what you want wrap and re-throw it. (Don't just rethrow without wrapping, you lose the original stack).
In JDBC 4 there are subclasses of SQLException like SQLNonTransientException that you can catch, but only if the JDBC driver throws those subclasses. At time of writing PgJDBC does not support those, and always simply throws SQLException, so if you try to catch them you'll never catch anything. (Patches are welcome!).
In the real world you're usually interested in a number of different error conditions and want to do different things based on them.
Something vaguely like the untested, written-in-the-window:
} catch (SQLException ex) {
final String ss = ex.getSQLState();
if (ss.equals("40001") || ss.equals("40P01")) {
/* It is a serialization failure or a deadlock abort. Retry the tx. */
retry_transaction = true;
} else if (ss.startsWith("08") || ss.startsWith("53")) {
/* It is a connection error or resource limit. Reconnect and retry. */
try {
conn.close();
} catch (SQLException ex) {
logger.log("Error closing suspected bad connection after SQLState " + ss, ex);
}
conn = null; /* App knows to reconnect if it sees a null connection */
retry_transaction = true;
} else {
throw new MyAppException(ex);
}
}
... where your app knows to reconnect if it sees a null connection, and keeps a record of the transaction it just attempted so it can retry it in a loop until it succeeds if it hits a deadlock or serialization failure.
In reality you'd be smarter than this, adding rate-limiting of retries, etc. This is just a simplistic example.
For more details, cast the exception to PSQLException after testing for castability, or catch it as a PSQLException in the first place. Then get details with:
ex.getServerErrorMessage()
which gives you a ServerErrorMessage with detailed fields.