Class RedisLockService
-
- All Implemented Interfaces:
public class RedisLockServiceA reentrant, Redis based lock service
The Redis clock is used as a time source such that all JVMs use the same source.
-
-
Nested Class Summary
Nested Classes Modifier and Type Class Description public final classRedisLockService.LockInfopublic final classRedisLockService.ThreadIdpublic final classRedisLockService.ThreadWaitingInfopublic final classRedisLockService.RedisLockServiceDeadlockExceptionpublic interfaceRedisLockService.LockServiceJsonHandler
-
Constructor Summary
Constructors Constructor Description RedisLockService(RedisConnectionPool connectionPool, RedisPubSubService redisPubSubService, Boolean deadlockDetection, Integer expireLocksWhichShallNotBeKeptSeconds, Long pollDelayWhenWaitingForLockMs, String lockKeyPrefix, Long lockLeaseTimeSeconds, Long lockLeaseRenewalTimeSeconds, RedisLockService.LockServiceJsonHandler lockServiceJsonHandler, Function1<Runnable, Runnable> onNewThreadHandler)
-
Method Summary
Modifier and Type Method Description final Unitstart()Starts the service. final Unitstop()Stops the service, for example when the JVM is shutting down. final List<RedisLockService.LockInfo>getLockInfo(Collection<String> lockNames)Fetches the LockInfos for given lockNames, if still available in Redis final <T extends Any> Pair<Boolean, T>tryLock(Collection<String> locks, Long timeoutMs, Boolean keepLockDataAfterUse, Function1<Function0<Boolean>, T> protectedCode)Tries to acquire all locks atomically and runs the protected code. -
-
Constructor Detail
-
RedisLockService
RedisLockService(RedisConnectionPool connectionPool, RedisPubSubService redisPubSubService, Boolean deadlockDetection, Integer expireLocksWhichShallNotBeKeptSeconds, Long pollDelayWhenWaitingForLockMs, String lockKeyPrefix, Long lockLeaseTimeSeconds, Long lockLeaseRenewalTimeSeconds, RedisLockService.LockServiceJsonHandler lockServiceJsonHandler, Function1<Runnable, Runnable> onNewThreadHandler)
- Parameters:
connectionPool- the pool to be used for communicating with RedisredisPubSubService- optional RedisPubSubService to detect faster when other threads release a lock.deadlockDetection- if true, throws a RedisLockServiceDeadlockException if it detects that two or more threads wait to acquire locks that the other threads already ownexpireLocksWhichShallNotBeKeptSeconds- expire time in seconds for locks, for which keepLockDataAfterUse (see tryLock) was set to false.pollDelayWhenWaitingForLockMs- time to wait between attempts to acquire the locks.lockKeyPrefix- prefix that shall be used for all keys in Redis (namespacing)lockLeaseTimeSeconds- duration in seconds, for how long a lock should be marked as taken in Redis (lease time)lockLeaseRenewalTimeSeconds- duration in seconds, for how often the lease time should automatically be extended while the locks are being held.onNewThreadHandler- each time a new virtual thread is started for renewing the leases of an acquisition, this handler is used to wrap the Runnable.
-
-
Method Detail
-
stop
final Unit stop()
Stops the service, for example when the JVM is shutting down.
hasLockreturns false from now on, and waiting tryLock calls give up. The lock records are not released here, but when the protected code returns.
-
getLockInfo
final List<RedisLockService.LockInfo> getLockInfo(Collection<String> lockNames)
Fetches the LockInfos for given lockNames, if still available in Redis
-
tryLock
final <T extends Any> Pair<Boolean, T> tryLock(Collection<String> locks, Long timeoutMs, Boolean keepLockDataAfterUse, Function1<Function0<Boolean>, T> protectedCode)
Tries to acquire all locks atomically and runs the protected code.
While the lock is being held and the protected code is being executed, the lease is automatically renewed to ensure that the lock does not expire. The protected code can use the provided
hasLocklambda to check if the lock is still being held. It should abort if this lambda returns false.The calling thread should preferably be a VirtualThread, because Thread.sleep() is used.
- Parameters:
locks- that must all be acquired before running the protected codetimeoutMs- max time to wait in case one or more of the requested locks are currently taken/unavailablekeepLockDataAfterUse- if true, the lock data, stored in Redis, is kept after use.protectedCode- the code to be executed once all locks are acquired- Returns:
If the locks were acquired and the protected code was executed, then true+result is returned. If the locks could not be acquired within the timeout, then false+null is returned. That is also the case for a nested call, if one of the locks the current thread already holds was lost meanwhile (see
hasLock) - it is not acquired again
-
-
-
-