Illia Khokholkov created JCR-3977:
-------------------------------------
Summary: New cluster node resets timeout of the open-scoped lock
Key: JCR-3977
URL: https://issues.apache.org/jira/browse/JCR-3977
Project: Jackrabbit Content Repository
Issue Type: Bug
Components: JCR 2.0
Affects Versions: 2.11.3
Reporter: Illia Khokholkov
*Problem*
Suppose we have an active open-scoped lock with a timeout set to 5 minutes (the
time to wait before the lock gets automatically released). Such a lock would be
present in the data store, e.g. Oracle DBMS, in the following format (for
instance, judging from the content of the persisted BLOB):
{noformat}
0899d423-c9e4-4d9b-a46e-a5055df8a23c-2,300
{noformat}
Consider that before the lock is unlocked, a new
{{org.apache.jackrabbit.core.cluster.ClusterNode}} joins the cluster. When
synchronization takes places for the new member of the cluster, the timeout of
the existing lock gets updated to the {{Long.MAX_VALUE}}, ignoring the
previously existing value (the absence of the {{,N}} indicates, essentially, no
expiry):
{noformat}
0899d423-c9e4-4d9b-a46e-a5055df8a23c-2
{noformat}
On the client side, if the branch of code that handles unlocking is never
reached, e.g. due to JVM failure, the originally locked node now becomes
permanently locked. I am aware of the [background
thread|https://github.com/apache/jackrabbit/blob/2.11.3/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/LockManagerImpl.java#L154]
that every so often
[looks|https://github.com/apache/jackrabbit/blob/2.11.3/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/LockManagerImpl.java#L177]
for the expired open-scoped locks and attempts to get rid of them. However, to
such a handler, the lock would still appear as active and not expired.
*Possible Reason*
When a cluster node
[processes|https://github.com/apache/jackrabbit/blob/2.11.3/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/cluster/ClusterNode.java#L960]
the lock record, for a lock operation it talks to the lock event listener:
{code}
if (record.isLock()) {
listener.externalLock(record.getNodeId(), record.isDeep(),
record.getOwner());
}
{code}
That operation, in turn,
[defines|https://github.com/apache/jackrabbit/blob/2.11.3/jackrabbit-core/src/main/java/org/apache/jackrabbit/core/lock/LockManagerImpl.java#L1354]
a new timeout value for the lock, ignoring the previously set one (the one
that was obtained from the persistent storage):
{code}
// create lock token
InternalLockInfo info = new InternalLockInfo(
nodeId, false, isDeep, lockOwner, Long.MAX_VALUE);
{code}
*Questions*
# Am I overlooking something evident here that would tell me that the observed
behavior is the one I should expect? Thanks!
--
This message was sent by Atlassian JIRA
(v6.3.4#6332)