.NET Core 實現 Redis 批量查詢指定格式的Key

來源:互聯網
上載者:User
一. 問題情境

Redis 作為當前最流行的記憶體型 NoSQL 資料庫,被許多公司所使用,作為分布式緩衝。我們在實際使用中一般都會為 key 帶上指定的首碼或者其他定義的格式。當由於我們程式出現bug,造成 redis 裡面的儲存的值,與我們預期的不一致時,我們可以通過查詢指定格式的 key,來定位到我們具體的出現問題的key,從而方便我們解決問題。

二. 解決辦法1.Keys 命令

Keys 命令用於尋找所有符合給定模式 pattern 的 key 。要求 Redis 版本大於 1.0.0。keys在查詢大數量key時,會長時間阻塞Redis,由於Redis是單線程的,這就是一個突出的問題,需要注意。

2.Scan 命令

Scan 命令相對於 Keys 命令來說,優點就是不會阻塞伺服器。要求 Redis 版本大於 2.8。

三. 代碼實現

這裡採用的Redis驅動是 StackExchange.Redis。

在 StackExchange.Redis 裡封裝 Redis 命令時分為了兩種,一種是針對於叢集的命令,一種是針對於單個Redis伺服器的命令,Keys 和 Scan 命令便是後者,我們在使用的時候必須在單獨的伺服器上執行。

Keys 和 Scan 命令都支援模糊查詢,這裡介紹三種匹配符:

  1. * 表示可以匹配多個任一字元
  2. ? 表示可以匹配單個任一字元
  3. [] 表示可以匹配指定範圍內的字元

因為我們的key可能分布在叢集內多個Redis伺服器上,所以我們需要在每台伺服器上都執行命令。我們可以通過 ConnectionMultiplexer.GetEndPoints() 方法來擷取所有的終結點資訊。

在 StackExchange.Redis 對於 keys 和 scan 命令統一封裝為了 IServer.Keys()方法,它會自動根據Redis伺服器版本來決定使用keys命令還是scan命令。

為了方便測試,我在 Redis 裡面準備了四個以 test 為首碼的key,放在序號為1的db裡面:

1.遍曆所有首碼為 test 的key 代碼如下:

static async Task Main(string[] args){    //建立串連    var conn = await ConnectionMultiplexer.ConnectAsync("192.168.10.110");    //擷取db    var db = conn.GetDatabase(1);    //遍曆叢集內伺服器    foreach (var endPoint in conn.GetEndPoints())    {        //擷取指定伺服器        var server = conn.GetServer(endPoint);        //在指定伺服器上使用 keys 或者 scan 命令來遍曆key        foreach (var key in server.Keys(1,"test.*"))        {            //擷取key對於的值            var val = db.StringGet(key);            Console.WriteLine($"key: {key}, value: {val}");        }    }}

執行結果:

2.[]的用法

假設我要遍曆 key為 test.1-test.3 的資料,可以這樣寫:

static async Task Main(string[] args){    //建立串連    var conn = await ConnectionMultiplexer.ConnectAsync("192.168.10.110");    //擷取db    var db = conn.GetDatabase(1);    //遍曆叢集內伺服器    foreach (var endPoint in conn.GetEndPoints())    {        //擷取指定伺服器        var server = conn.GetServer(endPoint);        //在指定伺服器上使用 keys 或者 scan 命令來遍曆key        foreach (var key in server.Keys(1,"test.[1-3]"))        {            //擷取key對於的值            var val = db.StringGet(key);            Console.WriteLine($"key: {key}, value: {val}");        }    }}

執行結果:

假設我要遍曆 key為 test.1和test.4 的資料,可以這樣寫:

static async Task Main(string[] args){    //建立串連    var conn = await ConnectionMultiplexer.ConnectAsync("192.168.10.110");    //擷取db    var db = conn.GetDatabase(1);    //遍曆叢集內伺服器    foreach (var endPoint in conn.GetEndPoints())    {        //擷取指定伺服器        var server = conn.GetServer(endPoint);        //在指定伺服器上使用 keys 或者 scan 命令來遍曆key        foreach (var key in server.Keys(1,"test.[1,4]"))        {            //擷取key對於的值            var val = db.StringGet(key);            Console.WriteLine($"key: {key}, value: {val}");        }    }}

執行結果:

好了,關於 Redis 查詢指定格式的 key 的方法就介紹到這裡了。

四. 參考資料

Where are KEYS, SCAN, FLUSHDB etc? by StackExchange.Redis

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.