From 703f6f57bf8f27adf800f8e576bf1ec3fbeaa013 Mon Sep 17 00:00:00 2001 From: Nikita Koksharov Date: Fri, 17 May 2024 19:52:44 +0300 Subject: [PATCH] Fixed - FairLock methods throw 'attempt to compare nil with number' error #4153 --- .../java/org/redisson/RedissonFairLock.java | 16 +++++++------- .../redisson/command/CommandAsyncService.java | 21 +++++++++++++------ 2 files changed, 23 insertions(+), 14 deletions(-) diff --git a/redisson/src/main/java/org/redisson/RedissonFairLock.java b/redisson/src/main/java/org/redisson/RedissonFairLock.java index 51dddae25..3cb2beab5 100644 --- a/redisson/src/main/java/org/redisson/RedissonFairLock.java +++ b/redisson/src/main/java/org/redisson/RedissonFairLock.java @@ -116,8 +116,8 @@ public class RedissonFairLock extends RedissonLock implements RLock { "if firstThreadId2 == false then " + "break;" + "end;" + - "local timeout = tonumber(redis.call('zscore', KEYS[3], firstThreadId2));" + - "if timeout <= tonumber(ARGV[3]) then " + + "local timeout = redis.call('zscore', KEYS[3], firstThreadId2);" + + "if timeout ~= false and tonumber(timeout) <= tonumber(ARGV[3]) then " + // remove the item from the queue and timeout set // NOTE we do not alter any other timeout "redis.call('zrem', KEYS[3], firstThreadId2);" + @@ -162,8 +162,8 @@ public class RedissonFairLock extends RedissonLock implements RLock { "break;" + "end;" + - "local timeout = tonumber(redis.call('zscore', KEYS[3], firstThreadId2));" + - "if timeout <= tonumber(ARGV[4]) then " + + "local timeout = redis.call('zscore', KEYS[3], firstThreadId2);" + + "if timeout ~= false and tonumber(timeout) <= tonumber(ARGV[4]) then " + // remove the item from the queue and timeout set // NOTE we do not alter any other timeout "redis.call('zrem', KEYS[3], firstThreadId2);" + @@ -247,8 +247,8 @@ public class RedissonFairLock extends RedissonLock implements RLock { + "if firstThreadId2 == false then " + "break;" + "end; " - + "local timeout = tonumber(redis.call('zscore', KEYS[3], firstThreadId2));" - + "if timeout <= tonumber(ARGV[4]) then " + + "local timeout = redis.call('zscore', KEYS[3], firstThreadId2);" + + "if timeout ~= false and tonumber(timeout) <= tonumber(ARGV[4]) then " + "redis.call('zrem', KEYS[3], firstThreadId2); " + "redis.call('lpop', KEYS[2]); " + "else " @@ -328,8 +328,8 @@ public class RedissonFairLock extends RedissonLock implements RLock { + "if firstThreadId2 == false then " + "break;" + "end; " - + "local timeout = tonumber(redis.call('zscore', KEYS[3], firstThreadId2));" - + "if timeout <= tonumber(ARGV[2]) then " + + "local timeout = redis.call('zscore', KEYS[3], firstThreadId2);" + + "if timeout ~= false and tonumber(timeout) <= tonumber(ARGV[2]) then " + "redis.call('zrem', KEYS[3], firstThreadId2); " + "redis.call('lpop', KEYS[2]); " + "else " diff --git a/redisson/src/main/java/org/redisson/command/CommandAsyncService.java b/redisson/src/main/java/org/redisson/command/CommandAsyncService.java index bf5bbfc3a..7470e30ac 100644 --- a/redisson/src/main/java/org/redisson/command/CommandAsyncService.java +++ b/redisson/src/main/java/org/redisson/command/CommandAsyncService.java @@ -924,20 +924,29 @@ public class CommandAsyncService implements CommandAsyncExecutor { public CompletionStage handleNoSync(CompletionStage stage, Supplier> supplier) { CompletionStage s = stage.handle((r, ex) -> { if (ex != null) { - if (ex.getCause().getMessage() != null - && ex.getCause().getMessage().equals("None of slaves were synced")) { + if (ex.getCause() != null + && ex.getCause().getMessage() != null + && ex.getCause().getMessage().equals("None of slaves were synced")) { return supplier.get().handle((r1, e) -> { if (e != null) { - if (ex.getCause().getMessage() != null - && e.getCause().getMessage().equals("None of slaves were synced")) { + if (e.getCause() != null + && e.getCause().getMessage() != null + && e.getCause().getMessage().equals("None of slaves were synced")) { throw new CompletionException(ex.getCause()); } - e.getCause().addSuppressed(ex.getCause()); + if (e.getCause() != null) { + e.getCause().addSuppressed(ex.getCause()); + } else { + e.addSuppressed(ex.getCause()); + } } throw new CompletionException(ex.getCause()); }); } else { - throw new CompletionException(ex.getCause()); + if (ex.getCause() != null) { + throw new CompletionException(ex.getCause()); + } + throw new CompletionException(ex); } } return CompletableFuture.completedFuture(r);