Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Redis load Lua script and cache it from file (instead of SCRIPT LOAD)

Tags:

caching

redis

lua

I understand that the common way of running Lua scripts with EVALSHA is to is to load the script first by passing it with SCRIPT LOAD. However, from my understanding, if the Redis server unexpectedly reboots, for example, the cached script will no longer exist and will have to be reloaded with SCRIPT LOAD.

Is there some way to set the Redis server to automatically load some specified Lua scripts from a file into its cache upon startup so they can be reliably executed with EVALSHA without worrying about the script possibly being unloaded?

like image 313
abagshaw Avatar asked Jul 30 '17 23:07

abagshaw


2 Answers

Thank you for the comment done by Curtis Yallop I can finally load myscript.lua file using this command. In my case,

$(cat myscript.lua)

was causing an error. Saying that "$" is an unknown character.

redis-cli -x script load < myscript.lua

worked for me :)

like image 80
Raihanul Alam Hridoy Avatar answered Sep 16 '22 11:09

Raihanul Alam Hridoy


This is not the same as stored procedures in RDBMS. These loaded scripts are not stored by redis server, they are just cached. so once server restarted, loaded scripts will be gone.

2 possible ways:

You provide the full text of the script for the first execution of the script (i.e. EVAL for the first execution) then you can use EVALSHA for all subsequent calls.

EVALSHA returns special error NOSCRIPT: No Matching script, Please Use [EVAL] in case this SHA digest is invalid so the client can always optimistically send EVALSHA under the hood even when the client actually send EVAL. if NOSCRIPT returned, EVAL will be used instead.

You can use SCRIPT EXISTS and load the script using SCRIPT LOAD in case it doesn't exist.

Check whether script exists:

SCRIPT EXISTS sha1 sha2 ... shaN

Load script:

SCRIPT LOAD script

Or code of the application (including Lua scripts) is managed on application side and you send script everytime you need to execute it if it is small text, in this case you do not need to configure or do anything in Redis side. This is very useful in the context of a distributed environment and with Redis cluster.

A third approach where you may want to change the behavior by adding custom startup scripts in linux where you start redis server and then load all of your scripts there however your app code still won't know anything about these SHA hashes but I don't like this approach with also difficulties in distributed environments.

More Info:

  • https://redis.io/commands/eval

  • https://grokbase.com/t/gg/redis-db/12ce84e9b3/lua-script-at-startup

like image 26
Muhammad Soliman Avatar answered Sep 20 '22 11:09

Muhammad Soliman