Redis 7 及更高版本的腳本化方案

一、背景與動機

傳統的 Redis 腳本機制依賴于客戶端加載 EVAL 腳本,存在以下局限:

  1. 網絡與編譯開銷
    每次調用都要傳輸腳本源碼或重新加載 SHA1。
  2. 緩存失效風險
    重啟、主從切換、SCRIPT FLUSH 后腳本緩存丟失,事務易失敗。
  3. 調試與運維困難
    SHA1 不可讀、難以在 MONITOR 或日志中追蹤。
  4. 代碼復用受限
    腳本之間無法互相調用,只能由客戶端拼接多份代碼。

Redis Functions 應運而生,將腳本納入 Redis 數據模型,以「聲明—持久化—調用」的方式,提供了更高效、更可靠、更易運維的服務器端腳本化能力。

二、Redis Functions 概覽

  • 第一類工件
    函數(Function)屬于數據庫自身的組成部分,隨數據持久化(AOF/RDB)與復制而同步。

  • 庫(Library)管理
    多個函數組織在同一庫中,整體加載或替換,不支持單個函數增量更新。

  • Shebang 元數據
    通過 #!<engine> name=<library> 指定執行引擎與庫名稱。

  • 調用接口

    • FUNCTION LOADFUNCTION DELETEFUNCTION LIST 管理庫
    • FCALL(可寫)或 FCALL_RO(只讀)執行函數

三、加載與注冊函數庫

  1. 編寫庫源碼
    以 Lua 為例,庫文件開頭必須包含 Shebang 行:

    #!lua name=mylib
    
  2. 注冊函數
    通過 redis.register_function(name, callback, [flags]) 將每個函數注冊到庫中:

    redis.register_function('knockknock',function() return "Who's there?" end
    )
    
  3. 加載到 Redis

    cat mylib.lua | redis-cli -x FUNCTION LOAD REPLACE
    

    返回值為庫名(如 mylib),表示加載成功。

四、調用函數:FCALL 與 FCALL_RO

  • FCALL [keys…] [args…]
    在任何節點執行(可寫)。
  • FCALL_RO [keys…] [args…]
    只讀副本上執行,只允許標記為 no-writes 的函數。

示例調用:

redis> FCALL knockknock 0
"Who's there?"

五、鍵名與參數

  • KEYS:指定所有將要訪問的 Redis 鍵名,必須在調用時列出,保證集群模式下數據訪問的正確路由。
  • ARGV:所有非鍵名輸入,供函數內部業務邏輯使用。

在函數回調中,Lua 參數形式為:

function(keys, args)-- keys 是一個 Lua 數組,包含前 numkeys 個參數-- args 是包含后續所有普通輸入的數組
end

六、示例:可復用的 Hash 操作庫

下面以一個「自動記錄最后修改時間」的 Hash 操作庫為例,演示如何在同一庫中組織多個函數并實現代碼復用。

#!lua name=mylib-- 輔助:校驗 keys 數量
local function check_keys(keys)if #keys ~= 1 thenreturn redis.error_reply("只允許傳入一個鍵名")endreturn nil
end-- my_hset:設置字段并記錄時間戳
local function my_hset(keys, args)local err = check_keys(keys)if err then return err endlocal hash = keys[1]local ts = redis.call("TIME")[1]return redis.call("HSET", hash, "_last_modified_", ts, unpack(args))
end-- my_hgetall:讀取所有字段(排除 _last_modified_)
local function my_hgetall(keys, args)local err = check_keys(keys)if err then return err endredis.setresp(3)  -- 切換到 RESP3,返回字典格式local hash = keys[1]local res = redis.call("HGETALL", hash)res.map["_last_modified_"] = nilreturn res
end-- my_hlastmodified:讀取修改時間戳
local function my_hlastmodified(keys, args)local err = check_keys(keys)if err then return err endreturn redis.call("HGET", keys[1], "_last_modified_")
end-- 注冊函數,并為只讀函數添加 no-writes 標志
redis.register_function("my_hset",    my_hset)
redis.register_function{function_name = "my_hgetall",callback      = my_hgetall,flags         = {"no-writes"}
}
redis.register_function{function_name = "my_hlastmodified",callback      = my_hlastmodified,flags         = {"no-writes"}
}

加載并調用:

cat mylib.lua | redis-cli -x FUNCTION LOAD REPLACE
redis> FCALL my_hset 1 myhash field1 "value1"
(integer) 2redis> FCALL_RO my_hgetall 1 myhash
1) "field1"
2) "value1"redis> FCALL_RO my_hlastmodified 1 myhash
"1640772721"

七、集群與持久化

  • 復制與持久化
    函數與數據一同寫入 AOF/RDB,并復制到從節點,保證函數持久可用。
  • 集群加載
    需要在所有主節點執行 FUNCTION LOAD,可借助 redis-cli --cluster-only-masters 批量操作。
  • RDB 鉤子
    使用 redis-cli --functions-rdb 可導出函數的 RDB 文件,在啟動時預加載到新的實例。

八、函數標志與權限控制

  • 默認行為
    Redis 假定所有函數可能讀寫數據,故禁止在只讀場景(FCALL_RO 或只讀副本)下執行。
  • no-writes 標志
    redis.register_function 時添加 flags={'no-writes'},表明函數僅執行讀操作,允許在只讀場景下調用。
  • 更多 Flags
    請參見官方文檔 Script flags,設置合適權限確保安全與隔離。

九、最佳實踐與注意事項

  1. 避免長時間阻塞
    函數執行時會阻塞主線程,應保持邏輯簡短,避免慢查詢或大批量數據掃描。
  2. 鍵名列舉全
    集群模式下訪問所有鍵必須列出于 numkeys 參數,防止跨槽錯誤。
  3. 整體替換
    函數庫更新時會替換全量代碼,確保所有函數均在同一版本下協同工作。
  4. 日志與監控
    可在函數內部調用 redis.log() 輸出警告或錯誤,便于生產環境診斷。
  5. 版本管理
    建議將函數庫源碼納入版本控制,與應用一并發布,保持部署可追溯。

十、總結

Redis Functions 通過將服務器端腳本化提升為第一類工件,徹底解決了 EVAL 腳本在分發、緩存、調試和復用上的痛點。它不僅讓腳本管理更可靠,也讓 Redis 能像模塊一樣對外提供統一 API,助力構建更復雜、更高效的業務邏輯。結合本文示例和最佳實踐,相信你能快速上手 Redis 7+ 的函數特性,并在生產環境中獲得顯著的運維與性能收益。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/912997.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/912997.shtml
英文地址,請注明出處:http://en.pswp.cn/news/912997.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

Java項目:基于SSM框架實現的云端學習管理系統【ssm+B/S架構+源碼+數據庫+畢業論文】

摘 要 互聯網發展至今&#xff0c;無論是其理論還是技術都已經成熟&#xff0c;而且它廣泛參與在社會中的方方面面。它讓信息都可以通過網絡傳播&#xff0c;搭配信息管理工具可以很好地為人們提供服務。針對課程學習信息管理混亂&#xff0c;出錯率高&#xff0c;信息安全性差…

【壓力測試之_Jmeter鏈接Oracle數據庫鏈接】

Oracle數據庫鏈接 歡迎來到挖坑避坑課堂鏈接數據庫 歡迎來到挖坑避坑課堂 之前性能測試都是業務之類的&#xff0c;數據庫壓測很少涉及&#xff0c;就會出現很多各式各樣的問題&#xff0c;首要問題就是Jmeter鏈接數據庫的問題&#xff0c;本篇主要講解Jmeter鏈接Oracle數據庫…

Appium與Appium Inspector配置教程

一、連接設備 首先將手機的開發者模式打開&#xff0c;不同手機的開啟方法不同&#xff0c;這里演示的測試機為vivoS1&#xff0c;其他機型的開啟方法大家可以自行AI搜索。 1.手機授權 &#xff08;1&#xff09;點擊手機的【設置】選項 &#xff08;2&#xff09;打開手機…

【web出海】深度拆解 FLUX.1 kontext:這不僅是AI繪畫的革命,更是 MicroSaaS 創業者的黃金機遇

前言 近日&#xff0c;Black Forest Labs 發布的 FLUX.1 Kontext 模型在AI圈掀起了波瀾。它不僅僅是又一個文生圖工具&#xff0c;其獨特的“在情境中&#xff08;in-context&#xff09;”編輯、驚人的角色一致性、精準的局部修改和強大的文字渲染能力&#xff0c;標志著一個技…

Git 安裝閉坑指南(僅 Windows 環境)

&#x1f4bb; Git 安裝閉坑指南&#xff08;僅 Windows 環境&#xff09; 適用人群&#xff1a;剛開始用 Git 的 Windows 用戶&#xff1b;重新配置開發環境的程序員&#xff1b;不想踩坑的團隊小伙伴 目標&#xff1a;快速、穩定地安裝 Git&#xff0c;在各種常見場景下避免“…

2025年4月SCI-呂佩爾狐優化算法Rüppell’s fox optimizer-附Matlab免費代碼

引言 本期介紹一種新的元啟發式算法——呂佩爾狐優化算法Rppell’s fox optimizer&#xff0c;RFO。RFO的靈感來自于呂佩爾狐貍在白天和晚上自然而聰明的集體覓食行為。優化器利用呂佩爾狐敏銳的視覺、聽覺和嗅覺對其各種主要覓食活動進行數學模擬&#xff0c;在優化過程中兼顧…

SwiftUI 中的模糊效果詳解:.blur、.material、UIVisualEffectView

模糊效果&#xff08;Blur Effect&#xff09;是 iOS 用戶界面設計的重要組成部分&#xff0c;它被廣泛應用于系統控制中心、通知背景、彈窗蒙版等場景&#xff0c;營造出“毛玻璃”的視覺層次感。 本文將深入解析 SwiftUI 中實現模糊效果的三種主流方式&#xff1a;.blur(radi…

Euler2203安裝.NetCore6.0環境操作步驟

# 1. 下載.NET二進制包 wget https://download.visualstudio.microsoft.com/download/pr/xxxx/dotnet-sdk-6.0.xxx-linux-x64.tar.gz把dotnet-sdk-6.0.428-linux-x64.tar.gz放到一個目錄里面# 2. 創建安裝目錄sudo mkdir -p /usr/share/dotnetsudo tar -zxf dotnet-sdk-6.0.428…

解決安裝SunloginClient問題記錄(Ubuntu 24.04.2)

成功安裝流程&#xff08;Ubuntu 24.04.2&#xff09; 1. 首次嘗試安裝&#xff08;失敗&#xff0c;缺少依賴&#xff09; sudo dpkg -i ./SunloginClient_15.2.0.63064_amd64.deb sudo apt-get install -f # 修復依賴&#xff08;此時提示缺少 libgconf-2-4&#xff09; …

wordpress安裝教程

一、安裝軟件 1、apache sudo apt install apache2 -y 2、mysql sudo apt install mysql-server -y 3、PHP及其擴展 sudo apt install php libapache2-mod-php php-mysql php-curl php-gd php-mbstring php-xml php-xmlrpc php-soap php-intl php-zip php-fpm -y 重啟ap…

C#,VB.NET從JSON數據里提取數組中的對象節點值

在VB.NET中&#xff0c;若要從 JSON 數據里提取Data.DataList數組中的CategoryId&#xff0c;并將其轉換為VB.NET數組&#xff0c;可借助Json.NET&#xff08;Newtonsoft.Json&#xff09;庫來實現。下面為你詳細介紹具體的實現步驟和代碼示例&#xff1a; 一、實現 JSON 到數…

Flutter 進階:實現帶圓角的 CircularProgressIndicator

在 Flutter 中&#xff0c;我們經常使用 CircularProgressIndicator 來展示加載進度。但是你是否注意到&#xff1a;它的進度端始終是“平頭”的&#xff08;直角&#xff09;&#xff1f; 這在一些 UI 設計中并不美觀&#xff0c;特別是想實現類似 Apple 健身環那樣“前端圓清…

解決CentOS7下載docker-compose出現沒有可用軟件包問題

1 問題描述 今天在使用虛擬機CentOS 7系統安裝docker-compose時&#xff0c;用的是aliyun鏡像&#xff0c;出現沒有可用軟件包的問題&#xff0c;這就說明不是因為網絡&#xff0c;而是因為aliyun鏡像沒有該軟件包。 2 解決辦法 這里推薦最穩定的解決辦法&#xff0c;去docker-…

基于SpringBoot+Vue的酒類倉儲管理系統

文檔包含用例圖、系統架構圖、系統功能結構圖、實體屬性圖、總體e-r圖。一.系統開發工具與環境搭建1.系統設計開發工具后端使用Java編程語言的Spring boot框架項目架構&#xff1a;B/S架構運行環境&#xff1a;win10/win11、jdk17前端&#xff1a;技術&#xff1a;框架Vue.js&a…

月付物理服務器租用平臺-青蛙云

青蛙云物理服務器租用服務概述 青蛙云是一家提供物理服務器租用服務的平臺&#xff0c;支持月付、年付等靈活付費方式&#xff0c;物理服務器適合企業或個人用戶的高性能計算需求。其服務覆蓋多地區機房&#xff0c;提供多種配置選項&#xff0c;支持定制化需求。 核心優勢 …

基于二分類方法和安全系數方法使用comsol with matlab蒙特卡洛模擬實現邊坡失效概率計算——隨機變量模型

基于二分類方法和安全系數方法使用comsol with matlab蒙特卡洛模擬實現邊坡失效概率計算——隨機變量模型 模型和全部代碼下載隨機變量模擬加載comsol模型蒙特卡洛模擬(分類模型)蒙特卡洛模擬(安全系數模型)內聚力和內摩擦角隨機變量分布二分類穩定性1000次運行結果失效概率…

機器學習-02(深度學習的基本概念)

機器學習的步驟 1.定義帶有未知參數的函數 線性模型&#xff08;linear models&#xff09;具有較大的限制&#xff08;Model Bias&#xff09; y b wx 無論如何更改b或者w&#xff0c;其只會呈現出一條直線&#xff0c;不能滿足更加復雜的現實情況。 我們可以將復雜的函…

InspireFace C++ 架構分析

InspireFace C 架構分析 https://github.com/deepinsight/insightface/tree/master/cpp-package/inspireface 1. 項目概述 InspireFace 是一個高性能的人臉識別和分析 SDK&#xff0c;采用 C 開發&#xff0c;提供了完整的人臉檢測、跟蹤、特征提取、活體檢測、屬性分析等功…

【網絡安全】Webshell命令執行失敗解決思路

前言費盡心思上傳了webshell&#xff0c;上傳下載都沒問題&#xff0c;卻發現命令執行總是失敗&#xff1f;最近也打點也遇到了這些問題&#xff0c;網上有部分文章&#xff0c;但都是零碎知識點并且實戰不一定能用&#xff0c;今天就結合我個人經驗剖析webshell上線后cmd命令執…

【機器人】復現 HOV-SG 機器人導航 | 分層 開放詞匯 | 3D 場景圖

HOV-SG 是通過語言指令實現機器人導航的&#xff0c;核心特點是分層結構、開放詞匯、3D場景圖。 來自RSS 2024&#xff0c;大規模、多層次的環境構建精確的、開放詞匯的3 場景圖&#xff0c;并使機器人能夠通過語言指令在其中有效地導航。 論文地址&#xff1a;Hierarchical …