Move LockManager API back to using int timeouts, since that's the way they're

handled elsewhere (FetchConfiguration, Broker, etc). Only use the lock timeout
on a forUpdate query if it is greater than the configured query timeout. 
Selects that are made *only* to lock a row (rather than to query data, with 
locking as a side effect) still use the lock timeout exclusively, ignoring the 
query timeout.



git-svn-id: https://svn.apache.org/repos/asf/incubator/openjpa/trunk@526192 13f79535-47bb-0310-9956-ffa450edef68
This commit is contained in:
A. Abram White 2007-04-06 15:08:39 +00:00
parent 1773160684
commit 1c8f82b810
5 changed files with 25 additions and 24 deletions

View File

@ -86,7 +86,7 @@ public class PessimisticLockManager
setLockLevel(sm, LOCK_DATASTORE_ONLY); setLockLevel(sm, LOCK_DATASTORE_ONLY);
} }
protected void lockInternal(OpenJPAStateManager sm, int level, long timeout, protected void lockInternal(OpenJPAStateManager sm, int level, int timeout,
Object sdata) { Object sdata) {
// we can skip any already-locked instance regardless of level because // we can skip any already-locked instance regardless of level because
// we treat all locks the same (though super doesn't) // we treat all locks the same (though super doesn't)
@ -103,7 +103,7 @@ public class PessimisticLockManager
* Lock the specified instance row by issuing a "SELECT ... FOR UPDATE" * Lock the specified instance row by issuing a "SELECT ... FOR UPDATE"
* statement. * statement.
*/ */
private void lockRow(OpenJPAStateManager sm, long timeout) { private void lockRow(OpenJPAStateManager sm, int timeout) {
// assert that the dictionary supports the "SELECT ... FOR UPDATE" // assert that the dictionary supports the "SELECT ... FOR UPDATE"
// construct; if not, and we the assertion does not throw an // construct; if not, and we the assertion does not throw an
// exception, then just return without locking // exception, then just return without locking
@ -136,7 +136,7 @@ public class PessimisticLockManager
if (log.isWarnEnabled()) if (log.isWarnEnabled())
log.warn(_loc.get("millis-query-timeout")); log.warn(_loc.get("millis-query-timeout"));
} }
stmnt.setQueryTimeout((int) (timeout / 1000)); stmnt.setQueryTimeout(timeout / 1000);
} }
rs = stmnt.executeQuery(); rs = stmnt.executeQuery();
if (!rs.next()) if (!rs.next())
@ -145,19 +145,10 @@ public class PessimisticLockManager
throw SQLExceptions.getStore(se, dict); throw SQLExceptions.getStore(se, dict);
} finally { } finally {
if (stmnt != null) if (stmnt != null)
try { try { stmnt.close(); } catch (SQLException se) {}
stmnt.close();
} catch (SQLException se) {
}
if (rs != null) if (rs != null)
try { try { rs.close(); } catch (SQLException se) {}
rs.close(); try { conn.close(); } catch (SQLException se) {}
} catch (SQLException se) {
}
try {
conn.close();
} catch (SQLException se) {
}
} }
} }

View File

@ -340,8 +340,19 @@ public class SelectImpl
else else
stmnt = sql.prepareStatement(conn, rsType, -1); stmnt = sql.prepareStatement(conn, rsType, -1);
if (forUpdate) // if this is a locking select and the lock timeout is greater than
// the configured query timeout, use the lock timeout
if (forUpdate && _dict.supportsQueryTimeout && fetch != null
&& fetch.getLockTimeout() > stmnt.getQueryTimeout() * 1000) {
int timeout = fetch.getLockTimeout();
if (timeout < 1000) {
timeout = 1000;
Log log = _conf.getLog(JDBCConfiguration.LOG_JDBC);
if (log.isWarnEnabled())
log.warn(_loc.get("millis-query-timeout"));
}
stmnt.setQueryTimeout(fetch.getLockTimeout() / 1000); stmnt.setQueryTimeout(fetch.getLockTimeout() / 1000);
}
rs = stmnt.executeQuery(); rs = stmnt.executeQuery();
} catch (SQLException se) { } catch (SQLException se) {
// clean up statement // clean up statement

View File

@ -48,11 +48,8 @@ cant-lock-on-load: The database is unable to lock this query. Each object \
start-trans-for-lock: Though you are using optimistic transactions, OpenJPA is \ start-trans-for-lock: Though you are using optimistic transactions, OpenJPA is \
now beginning a datastore transaction because you have requested a lock \ now beginning a datastore transaction because you have requested a lock \
on some data. on some data.
millis-timeout: JDBC lock manager does not support millisecond-granularity \ millis-query-timeout: JDBC locking does not support millisecond-granularity \
timeouts. Use timeouts that are multiples of 1000 for even second values. timeouts. Use timeouts that are multiples of 1000 for even second values.
millis-query-timeout: JDBC lock manager does not support \
millisecond-granularity timeouts. Use timeouts that are multiples \
of 1000 for even second values.
batch-not-supported: The update count for the statement was an invalid \ batch-not-supported: The update count for the statement was an invalid \
value ({0}). This indicates that your database or JDBC driver does not \ value ({0}). This indicates that your database or JDBC driver does not \
have complete support for executing batch statements. Batch \ have complete support for executing batch statements. Batch \

View File

@ -162,3 +162,5 @@ oracle-timestamp-bug: An ArrayIndexOutOfBoundsException has occured when \
property to "true". property to "true".
isolation-level-config-not-supported: This DBDictionary does not support \ isolation-level-config-not-supported: This DBDictionary does not support \
customization of isolation levels on a per-query basis. DBDictionary: {0}. customization of isolation levels on a per-query basis. DBDictionary: {0}.
millis-query-timeout: JDBC locking does not support millisecond-granularity \
timeouts. Use timeouts that are multiples of 1000 for even second values.

View File

@ -90,7 +90,7 @@ public class VersionLockManager
* *
* @see StoreContext#transactional * @see StoreContext#transactional
*/ */
protected void lockInternal(OpenJPAStateManager sm, int level, long timeout, protected void lockInternal(OpenJPAStateManager sm, int level, int timeout,
Object sdata) { Object sdata) {
// Set lock level first to prevent infinite recursion with // Set lock level first to prevent infinite recursion with
// transactional(..) call // transactional(..) call