SoFunction
Updated on 2025-05-04

Detailed explanation of the principle and basic usage of using lua scripts in redis

Using Lua scripts in Redis can achieve atomic operations, reduce network overhead, and improve execution efficiency.

Redis's principle of executing Lua scripts

Redis has a built-in Lua interpreter that can execute Lua scripts directly on the server side. When executing Lua scripts, Redis will execute the script as a whole to ensure that the script will not be inserted by other commands during execution, thereby achieving atomic operations.

Basic usage method

Execute Lua scripts using the EVAL command

The EVAL command is used to execute Lua scripts in Redis, and its basic syntax is as follows:

EVAL script numkeys key [key ...] arg [arg ...]

script: The Lua script to be executed.

numkeys: The number of keyname parameters used in the script.

key [key ...]: key name parameter list.

arg [arg ...]: List of other parameters.

redis-cli EVAL "return ('SET', KEYS[1], ARGV[1])" 1 mykey myvalue

The function of the script return ('SET', KEYS[1], ARGV[1]) is to call the SET command of Redis and set the value of ARGV[1] to the corresponding key of KEYS[1].

1 means that the number of key name parameters used in the script is 1.

mykey is the key name parameter.

myvalue is another parameter.

Execute preloaded scripts using the EVALSHA command

To avoid transmitting the entire script content every time the script is executed, you can use the SCRIPT LOAD command to load the script into Redis, get a SHA1 hash value, and then use the EVALSHA command to execute the script through the hash value.

# Load the script and get the SHA1 hash valueredis-cli SCRIPT LOAD "return ('SET', KEYS[1], ARGV[1])"
# Output example: "a1b2c3d4e5f6..." 
# Use the EVALSHA command to execute scriptsredis-cli EVALSHA "a1b2c3d4e5f6..." 1 mykey myvalue

Using Lua scripting in Go Redis

Here is an example of executing Lua scripts using the Go language and the go-redis library

package main
 
import (
    "context"
    "fmt"
    "/go-redis/redis/v8"
)
 
func main() {
    rdb := (&{
        Addr:     "localhost:6379",
        Password: "",
        DB:       0,
    })
 
    ctx := ()
 
    // Define Lua scripts    script := `
    local key = KEYS[1]
    local value = ARGV[1]
    return ('SET', key, value)
    `
 
    // Execute Lua scripts    result, err := (ctx, script, []string{"mykey"}, "myvalue").Result()
    if err != nil {
        ("Failed to execute Lua script:", err)
        return
    }
    ("Script execution result:", result)
}    

Redis API in Lua scripts

In Lua scripts, you can use and functions to call the Redis command:

: Call the Redis command. If the command execution error occurs, the script will terminate and return an error message.

: Call the Redis command. If the command execution error occurs, the script will not terminate, but will return a Lua table containing the error message.

Call example:

package main
 
import (
    "context"
    "fmt"
    "/go-redis/redis/v8"
)
 
func main() {
    rdb := (&{
        Addr:     "localhost:6379",
        Password: "",
        DB:       0,
    })
 
    ctx := ()
 
    // Define Lua scripts    script := `
    ('SET', KEYS[1], ARGV[1])
    local value = ('GET', KEYS[1])
    return value
    `
 
    // Execute Lua scripts    result, err := (ctx, script, []string{"mykey"}, "myvalue").Result()
    if err != nil {
        ("Failed to execute Lua script:", err)
        return
    }
    ("Script execution result:", result)
}    

pcall example:

package main
 
import (
    "context"
    "fmt"
    "/go-redis/redis/v8"
)
 
func main() {
    rdb := (&{
        Addr:     "localhost:6379",
        Password: "",
        DB:       0,
    })
 
    ctx := ()
 
    // Define the Lua script that contains    script := `
    local result = ('GET', 'nonexistent_key')
    if type(result) == 'table' and  then
        return 'Error: ' .. 
    else
        return result
    end
    `
 
    // Execute Lua scripts    result, err := (ctx, script, []string{}).Result()
    if err != nil {
        ("Failed to execute Lua script:", err)
        return
    }
    ("Script execution result:", result)
}    

Things to note

Atomicity: Lua scripts are executed atomically in Redis, but be careful that the execution time of the script should not be too long, otherwise it will block requests from other clients.

Performance: Using Lua scripts rationally can reduce network overhead and improve execution efficiency, but if the scripts are too complex, it may affect performance.

Data type: The data type in the Lua script and the data type of Redis need to be converted appropriately.

Lua Comments

Single line comments

In Lua, use two hyphens -- to enable single-line comments. After -- the content until the end of the line will be considered a comment and will not be executed by the Lua interpreter.

-- This is a single line comment
local num = 10 -- Define a variable num and assign a value of 10

Multi-line comments

Multi-line comments start with --[[ and end with ]]. Everything between these two tags belongs to comments, no matter how many lines it spans.

--[[
This is a multi-line comment
Can contain many lines of content
Used to provide detailed description of code blocks
]]
local str = "Hello, World!"

Lua Basic Syntax

variable

Lua is a dynamically typed language, and variables do not need to be declared in advance. Common variable types are nil, boolean, number, string, table, function, thread, and userdata.

Global variables: By default, variables are global variables. The value of the unassigned global variable is nil.

-- Define a global variable
message = "Hello, Lua!"
print(message)

Local variables: Declare local variables using the local keyword, and their scope is limited to the code blocks that declare it.

do
    local num = 20
print(num) -- Can be accessed within the code block
end
-- print(num) -- An error occurs here because num is a local variable, out of scope

Data Type

1. Boolean type

There are only two values: true and false. In conditional judgment, except for false and nil, all other values ​​are considered true.

local isEnabled = true
if isEnabled then
    print("Enabled")
end

2. Number type (number)

The number type in Lua is a double-precision floating point number by default.

local num1 = 10
local num2 = 3.14
print(num1 + num2)

3. String type (string)

Single or double quotes can be used to represent strings.

local str1 = 'Hello'
local str2 = "World"
print(str1 .. " " .. str2) -- use .. Do string stitching

4. Table type (table)

The most powerful data type in Lua can be used as arrays, dictionaries, etc. The table is created using curly braces {}.

-- Used as an array
local fruits = {"apple", "banana", "cherry"}
print(fruits[1]) -- Index from 1 start
 
-- Used as a dictionary
local person = {name = "John", age = 30}
print()

Control structure

1. if-else statement

local score = 80
if score >= 90 then
    print("A")
elseif score >= 80 then
    print("B")
else
    print("C")
end

2. for loop

Numerical for loop: used to traverse a numerical range.

for i = 1, 5 do
    print(i)
end

Generic for loop: used to traverse iterators, such as arrays or tables.

local fruits = {"apple", "banana", "cherry"}
for index, value in ipairs(fruits) do
    print(index, value)
end

3. while loop

local count = 0
while count < 3 do
    print(count)
    count = count + 1
end

function

Functions are defined using the function keyword, and can have parameters and return values.

function add(a, b)
    return a + b
end
 
local result = add(3, 5)
print(result)

This is the article about the principles and basic usage of lua scripts in redis. For more related contents of using lua scripts, please search for my previous articles or continue browsing the related articles below. I hope everyone will support me in the future!