-
Notifications
You must be signed in to change notification settings - Fork 87
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
withShouldSkipBlockingWait will always fail to acquire lock if already exists and expired #93
Comments
I am facing the same issue, any solution to this please? A lock is stale in my DDB and no other instance is able to acquire the lock indefinitely. Is there a way to save the lastUpdatedTime to DDB, so that the isExpired() method of LockItem works well. |
Facing the same issue. Can be easily reproduced val lockClient = AmazonDynamoDBLockClient(
AmazonDynamoDBLockClientOptions.builder(ddb, "test_lock")
.withTimeUnit(TimeUnit.SECONDS)
.withLeaseDuration(5L)
.withCreateHeartbeatBackgroundThread(false)
.build())
val lock1 = lockClient.acquireLock(
AcquireLockOptions
.builder("myTest")
.withAdditionalTimeToWaitForLock(0)
.withTimeUnit(TimeUnit.SECONDS)
.build()
)
log.info { "First lock $lock1" }
Thread.sleep(10000)
log.info { "Slept a 10 sec. Lease time is 5 sec. Attempting to acquire lock again" }
val lock2 = lockClient.acquireLock(
AcquireLockOptions
.builder("myTest")
.withShouldSkipBlockingWait(true)
.withAdditionalTimeToWaitForLock(1)
.withTimeUnit(TimeUnit.SECONDS)
.build()
)
log.info { "Lock $lock2" } Fails in attempt to acquire the lock2
|
README says this should work in a different way
Issue is happening because the return LockClientUtils.INSTANCE.millisecondTime() - this.lookupTime.get() > this.leaseDuration.get(); The https://github.com/awslabs/amazon-dynamodb-lock-client/blame/master/src/main/java/com/amazonaws/services/dynamodbv2/AmazonDynamoDBLockClient.java#L987 By reading the documentation I was interpreting "stale" and "lease time" meaning: if an item is added at X time and the lease time is L, at time Y where Y>X+L the lock would be stale (or expired). The implementation does not translate to that exactly. When using Can be easily reproduced by changing the lock2 in the example above to use
(it took 5 seconds to acquire the lock after the 10 second sleep. The lease time of this lock was 5 seconds. The attempt to get the second lock should have immediately acquired the lock if the definition of stale was the one I added here) |
+1 @a-lcardos I had If my understanding is correct, it looks like the only way for a lock to "expire" (without calling release) is to call acquireLock() and let it block for the entire lease duration (?) It seems like there's no way you can use this to have a non-blocking lock acquire w/ lease expiration. Maybe you could work around it by setting a ttl on you table items, but that's just super not ideal. |
This was fixed in the internally-maintained version of this package. Would be good to have the fix shipped to the public version as well. |
@cristianocca It looks like you're right! I guess this was resolved on branch v1.3.x 👀. |
@cristianocca It looks like you're also right about that version not being shipped to the public 🥲. |
We have merged the latest commit from @moshegood and this change has been release in version 1.3. |
Acquiring a lock with
withShouldSkipBlockingWait(true)
(so we don't block waiting) does not attempt to retrieve a lock that is expired (e.g., owner died / past lease time) as opposed to not using this option. Basically, if a lock is stale in DDB, usingwithShouldSkipBlockingWait
will never be able to pick up the lock and it will consider it as already taken.The text was updated successfully, but these errors were encountered: