指令碼

Redis 2.6 及更高版本透過 evalevalsha 命令支援執行 Lua 指令碼。Spring Data Redis 提供了一種高階抽象來執行指令碼,它處理序列化並自動使用 Redis 指令碼快取。

指令碼可以透過呼叫 RedisTemplateReactiveRedisTemplateexecute 方法來執行。兩者都使用可配置的 ScriptExecutor(或 ReactiveScriptExecutor)來執行提供的指令碼。預設情況下,ScriptExecutor(或 ReactiveScriptExecutor)負責序列化提供的鍵和引數,並反序列化指令碼結果。這是透過模板的鍵和值序列化器完成的。還有一個額外的過載,允許您為指令碼引數和結果傳遞自定義序列化器。

預設的 ScriptExecutor 透過檢索指令碼的 SHA1 並首先嚐試執行 evalsha 來最佳化效能,如果指令碼尚未存在於 Redis 指令碼快取中,則回退到 eval

以下示例透過使用 Lua 指令碼執行一個常見的“檢查並設定”場景。這是 Redis 指令碼的理想用例,因為它要求原子地執行一組命令,並且一個命令的行為受另一個命令結果的影響。

@Bean
public RedisScript<Boolean> script() {

  ScriptSource scriptSource = new ResourceScriptSource(new ClassPathResource("META-INF/scripts/checkandset.lua"));
  return RedisScript.of(scriptSource, Boolean.class);
}
  • 命令式

  • Reactive

public class Example {

  @Autowired
  RedisOperations<String, String> redisOperations;

  @Autowired
  RedisScript<Boolean> script;

  public boolean checkAndSet(String expectedValue, String newValue) {
    return redisOperations.execute(script, List.of("key"), expectedValue, newValue);
  }
}
public class Example {

  @Autowired
  ReactiveRedisOperations<String, String> redisOperations;

  @Autowired
  RedisScript<Boolean> script;

  public Flux<Boolean> checkAndSet(String expectedValue, String newValue) {
    return redisOperations.execute(script, List.of("key"), expectedValue, newValue);
  }
}
-- checkandset.lua
local current = redis.call('GET', KEYS[1])
if current == ARGV[1]
  then redis.call('SET', KEYS[1], ARGV[2])
  return true
end
return false

上述程式碼配置了一個 RedisScript,指向名為 checkandset.lua 的檔案,該檔案預期返回一個布林值。指令碼的 resultType 應該是 LongBooleanList 之一,或一個反序列化的值型別。如果指令碼返回一個一次性狀態(具體來說是 OK),它也可以是 null

理想情況下,在應用程式上下文中配置一個 DefaultRedisScript 例項,以避免在每次指令碼執行時重新計算指令碼的 SHA1。

上述 checkAndSet 方法隨後執行指令碼。指令碼可以在 SessionCallback 中作為事務或管道的一部分執行。有關更多資訊,請參閱“Redis 事務”和“管道”。

Spring Data Redis 提供的指令碼支援還允許您使用 Spring Task 和 Scheduler 抽象來排程 Redis 指令碼以進行定期執行。有關更多詳細資訊,請參閱 Spring Framework 文件。

© . This site is unofficial and not affiliated with VMware.