Redis 6.0 訪問控制列表ACL說明


背景

      在Redis6.0之前的版本中,登陸Redis Server只需要輸入密碼(前提配置了密碼 requirepass )即可,不需要輸入用戶名,而且密碼也是明文配置到配置文件中,安全性不高。並且應用連接也使用該密碼,導致應用有所有權限處理數據,風險也極高。在Redis6.0有了ACL之后,終於解決了這些不安全的因素,可以按照不同的需求設置相關的用戶和權限。本文來介紹下Redis 6.0 ACL相關的配置和使用。具體的說明可以查看官方文檔:ACL 

說明

       Redis ACL 是向后兼容的,即默認情況下用戶為default,使用的是requirepass配置的密碼。要是不使用ACL功能,對舊版客戶端來說完全一樣。Redis Auth可以有2種方式進行工作:

1:舊版本的使用方式,默認用戶。兼容舊版本Redis的支持
AUTH <password>
2:新方式,還需要驗證用戶名
AUTH <username> <password>

因為需要驗證用戶名了,所以客戶端的認證方式也多了參數:

  --user <username>  驗證用戶名
  --pass <password>  驗證密碼,是參數-a的別名;配合--user使用
  --askpass          強制用戶輸入帶有STDIN掩碼的密碼

現在開始來說明如何在Redis中根據ACL來定制需要的用戶權限。首先看ACL的help,了解大致的使用方法:ACL help

> ACL help 1) ACL <subcommand> arg arg ... arg. Subcommands are:
 2) LOAD                             -- 從ACL文件中重新載入用戶信息.
 3) SAVE                             -- 保存當前的用戶配置信息到ACL文件.
 4) LIST                             -- 以配置文件格式顯示用戶詳細信息.
 5) USERS                            -- 列出所有注冊的用戶名.
 6) SETUSER <username> [attribs ...] -- 創建或則修改一個用戶.
 7) GETUSER <username>               -- 得到一個用戶的詳細信息.
 8) DELUSER <username> [...]         -- 刪除列表中的用戶.
 9) CAT                              -- 列出可用的類別.
10) CAT <category>                   -- 列出指定類別中的命令.
11) GENPASS [<bits>]                 -- 生成一個安全的用戶密碼.
12) WHOAMI                           -- 返回當前的連接用戶.
13) LOG [<count> | RESET]            -- 顯示ACL日志條目.

使用方法:

在創建用戶之前,先說明下ACL的規則,首先看下一個完整的用戶權限的格式:

> ACL LIST --顯示用戶信息 1) "user default on #ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad ~* +@all"

格式說明

參 數
說明
user 用戶
default   表示默認用戶名,或則自己定義的用戶名
on 表示是否啟用該用戶,默認為off(禁用)
#... 表示用戶密碼,nopass表示不需要密碼
~* 表示可以訪問的Key(正則匹配)
+@ 表示用戶的權限,+/-表示授權還是銷權; @為權限類。+@all 表示所有權限













  • 密碼相關
    ① 配置密碼:一個用戶可以設置不同的密碼,即一個用戶可以有多個密碼。
    -- 添加密碼 
    ## >開頭: >password,明文密碼;
    > ACL SETUSER zhoujy on >abc
    OK
    
    # 獲取哈希值密碼 echo -n "cba" | shasum -a 256
    6d970874d0db767a7058798973f22cf6589601edab57996312f2ef7b56e5584d
    
    ## #開頭: #hash,SHA-256哈希值
    > ACL SETUSER zhoujy on #6d970874d0db767a7058798973f22cf6589601edab57996312f2ef7b56e5584d
    OK
    
    ## 查看
    > ACL GETUSER zhoujy
    1) "flags"
    2) 1) "on"
    3) "passwords"
    4) 1) "ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad"
       2) "6d970874d0db767a7058798973f22cf6589601edab57996312f2ef7b56e5584d"
    5) "commands"
    6) "-@all"
    7) "keys"
    8) (empty array)
    
    ## 認證密碼
    > AUTH zhoujy abc
    OK
    > AUTH zhoujy cba
    OK
    
    
    -- 移除密碼
    ## <開頭: <password ,明文密碼
    > ACL SETUSER zhoujy <abc
    OK
    
    ## 用!開頭: !hash,SHA-256哈希值
    > ACL SETUSER zhoujy on !6d970874d0db767a7058798973f22cf6589601edab57996312f2ef7b56e5584d
    OK
    
    ## 查看
    > ACL GETUSER zhoujy
    1) "flags"
    2) 1) "on"
    3) "passwords"
    4) (empty array)
    5) "commands"
    6) "-@all"
    7) "keys"
    8) (empty array)
    
    ## 認證密碼
    > AUTH zhoujy abc
    (error) WRONGPASS invalid username-password pair

    ② 清理/刪除密碼:通過nopass清理用戶的密碼,但是該用戶連接還是需要AUTH,只是密碼可以是任意值

    -- 清理/刪除密碼,可以用任意密碼登陸
    ## 查看
    > ACL GETUSER zhoujy
    1) "flags"
    2) 1) "on"
       2) "allkeys"
       3) "allcommands"
    3) "passwords"
    4) 1) "ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad"
       2) "6d970874d0db767a7058798973f22cf6589601edab57996312f2ef7b56e5584d"
    5) "commands"
    6) "+@all"
    7) "keys"
    8) 1) "*"
    
    ## 刪除、清理用戶密碼
    > ACL SETUSER zhoujy nopass
    OK
    
    ## 查看
    > ACL GETUSER zhoujy
    1) "flags"
    2) 1) "on"
       2) "allkeys"
       3) "allcommands"
       4) "nopass"
    3) "passwords"
    4) (empty array)
    5) "commands"
    6) "+@all"
    7) "keys"
    8) 1) "*"
    
    ## 驗證
    > AUTH zhoujy  --需要AUTH
    (error) WRONGPASS invalid username-password pair
    
    > AUTH zhoujy ''  --可以輸入任何密碼
    OK
    
    
    -- 清理/刪除密碼,不能登陸,需要設置密碼后才能登陸
    ## 查看
    > ACL GETUSER zhoujy
    1) "flags"
    2) 1) "on"
       2) "allkeys"
       3) "allcommands"
    3) "passwords"
    4) 1) "ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad"
       2) "6d970874d0db767a7058798973f22cf6589601edab57996312f2ef7b56e5584d"
    5) "commands"
    6) "+@all"
    7) "keys"
    8) 1) "*"
    
    ## 刪除、清理用戶密碼
    > ACL SETUSER zhoujy resetpass
    OK
    > ACL GETUSER zhoujy
    1) "flags"
    2) 1) "on"
       2) "allkeys"
       3) "allcommands"
    3) "passwords"
    4) (empty array)
    5) "commands"
    6) "+@all"
    7) "keys"
    8) 1) "*"
    
    ## 驗證,被resetpass重置密碼之后,不能登陸,只能設置密碼或則設置nopass才能登陸
    > AUTH zhoujy
    (error) WRONGPASS invalid username-password pair
    
    > AUTH zhoujy ''
    (error) WRONGPASS invalid username-password pair

    ③ 重置用戶和密碼:實際上是執行 resetpass,resetkeys,off,-@all

    ## 查看
    > ACL LIST
    1) "user default on #ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad ~* +@all"
    2) "user zhoujy on #ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad ~* +@all"
    
    ## 重置用戶
    > ACL SETUSER zhoujy reset
    OK
    
    ## 查看
    > ACL LIST
    1) "user default on #ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad ~* +@all"
    2) "user zhoujy off -@all"

    ④ 獲取隨機密碼:

    -- 生成隨機密碼
    > ACL GENPASS
    "7a3288b05577cb6fea9b1a9a8bcfe10d9589e64be74e8a0e16c131ba896c7bde"
  • 鍵模式:~<pattern>,通配符模式。比如: ~*表示允許訪問所有key,也可以用 allkeys來表示~*resetkeys 表示清空它之前所有的鍵模式,之后的鍵模式不影響。
    -- 可以操作foo開頭和bar:開頭的所有key
    > ACL SETUSER zhoujy on >abc ~foo* ~bar:*+@all
    OK
    
    ## 查看
    > ACL LIST
    1) "user default on #ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad ~* +@all"
    2) "user zhoujy on #ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad ~foo* ~bar:*+@all"
    
    --  只能操作ob:開頭的key,前面的key模式被resetkeys清空了
    > ACL SETUSER zhoujy on >abc ~foo* ~bar:* resetkeys ~ob:*+@all
    OK
    
    ## 查看
    > ACL LIST
    1) "user default on #ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad ~* +@all"
    2) "user zhoujy on #ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad ~ob:*+@all"
    
    -- 操作所有key,allkeys 和 ~* 一樣
    > ACL SETUSER zhoujy allkeys +@all
    OK
    > ACL LIST
    1) "user default on #ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad ~* +@all"
    
    ## 查看
    2) "user zhoujy on #ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad ~*+@all"
  • 權限相關:權限這塊涉及到的比較多:權限的類別、類別里包含的命令,以及子權限。
    注意:-@all表示沒有任何權限;+@all表示有所有權限;
    -- 返回權限的類別
    > ACL CAT
     1) "keyspace"
     2) "read"
     3) "write"
     4) "set"
     5) "sortedset"
     6) "list"
     7) "hash"
     8) "string"
     9) "bitmap"
    10) "hyperloglog"
    11) "geo"
    12) "stream"
    13) "pubsub"
    14) "admin"
    15) "fast"
    16) "slow"
    17) "blocking"
    18) "dangerous"
    19) "connection"
    20) "transaction"
    21) "scripting"
    
    -- 返回指定類別中的命令,下面hash是上面返回的一個結果
    > ACL CAT hash 1) "hsetnx"
     2) "hset"
     3) "hlen"
     4) "hmget"
     5) "hincrbyfloat"
     6) "hgetall"
     7) "hvals"
     8) "hscan"
     9) "hkeys"
    10) "hstrlen"
    11) "hget"
    12) "hdel"
    13) "hexists"
    14) "hincrby"
    15) "hmset" 

    從上面的權限列表里看到:權限對key的類型和命令的類型進行了分類,如有對類型進行分類:string、hash、list、set、sortedset,和對命令類型進行分類:connection、admin、dangerous。 以及對每個分類的方法進行說明,如上面查看hash類型key的一些方法。
    授權方法

    +<command>:將命令添加到用戶可以調用的命令列表中,如+@hash
    -<command>: 將命令從用戶可以調用的命令列表中移除
    +@<category>: 添加一類命令,如:@admin, @set, @hash ... 可以ACL CAT 查看具體的操作指令。特殊類別@all表示所有命令,包括當前在服務器中存在的命令,以及將來將通過模塊加載的命令
    -@<category>: 類似+@<category>,從客戶端可以調用的命令列表中刪除命令
    +<command>|subcommand: 允許否則禁用特定子命令。注意,這種形式不允許像-DEBUG | SEGFAULT那樣,而只能以“ +”開頭
    allcommands:+@all的別名,允許所有命令操作執行。注意,這意味着可以執行將來通過模塊系統加載的所有命令。
    nocommands:-@all的別名,不允許所有命令操作執行。

    ① 添加指定類型的權限:+@hash

    -- 添加hash類型key的所有權限
    > ACL SETUSER zhoujy +@hash
    OK
    
    ## 查看
    > ACL LIST
    1) "user default on #ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad ~* +@all"
    2) "user zhoujy on #ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad ~* -@all +@hash" 

    說明:用戶zhoujy只有對hash類型的key有權限。

    ② 刪除指定類型的權限:-@hash
    -- 刪除hash類型key的所有權限
    > ACL SETUSER zhoujy -@hash +@string
    OK
    
    ## 查看
    > ACL LIST
    1) "user default on #ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad ~* +@all"
    2) "user zhoujy on #ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad -@all +@string"

    說明:用戶zhoujy移除對hash類型的key有權限。
    ③ 指定特定key的權限:如sortedset:~z*,z開頭的key

    -- 訪問指定key的正則
    > ACL SETUSER zhoujy ~z* +@sortedset -@string
    OK
    
    ## 查看
    > ACL LIST
    1) "user default on #ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad ~* +@all"
    2) "user zhoujy on #ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad ~z* -@all +@sortedset"

    說明:用戶zhoujy只有對z開頭的key有權限。

    ④ 授權只讀/只寫的權限:+@read、+@write
    -- 授權所有key的只讀權限
    > ACL SETUSER zhoujy ~* +@read
    OK
    
    ##查看
    > ACL LIST
    1) "user default on #ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad ~* +@all"
    2) "user zhoujy on #ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad ~* -@all +@read +@hash +@bitmap +@geo -georadiusbymember -hsetnx -setbit -hset -geoadd -bitop -hincrbyfloat -hdel -bitfield -hincrby -hmset -georadius"
    
    -- 授權所有key的只寫權限
    > ACL SETUSER zhoujy +@write
    OK
    
    ##查看
    192.168.163.134:8379> ACL LIST
    1) "user default on #ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad ~* +@all"
    2) "user zhoujy on #ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad ~* -@all +@write +@list +@string +@stream +@fast +@blocking -dbsize -getrange -scard -xrevrange -zrank -llen -xread -ttl -get -ping -watch -publish -hlen -xrange -stralgo -zcount -getbit -lastsave -readonly -hmget -hello -zcard -discard -hstrlen -xinfo -hget -exists -bitfield_ro -select -role -zlexcount -zrevrank -lolwut -hexists -touch -lindex -unwatch -sismember -strlen -xlen -asking -type -mget -time -xpending -echo -multi -auth -readwrite -lrange -pttl -zscore -substr"

    說明:用戶zhoujy對所有key有只讀或則只寫的權限,如果下個這對指定key,則替換 ~* 即可。
    ⑤ 授權管理權限:@admin

    -- 授權管理權限
    > ACL SETUSER zhoujy on >abc ~* +@admin
    OK
    
    ## 查看
    > ACL LIST
    1) "user default on #ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad ~* +@all"
    2) "user zhoujy on #ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad ~* -@all +@admin +@dangerous -flushall -flushdb -swapdb -keys -role -sort -migrate -restore-asking -restore -info"

    說明:用戶zhoujy有管理權限,包含了危險操作的類型,但排除了-開頭命令的權限。

    ⑥ 允許特定類型key的子命令權限:
    -- 設置子命令。
    > ACL SETUSER zhoujy on >abc ~* -client +client|getname +client|setname
    OK
    
    ##查看
    > ACL LIST
    1) "user default on #ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad ~* +@all"
    2) "user zhoujy on #ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad ~* -@all +client|getname +client|setname"

    說明:開始刪除CLIENT命令,然后添加了兩個允許的子命令。請注意,不能相反,即不能+在前面,只能添加而不是排除子命令,因為將來可能會添加新的子命令。注意子命令匹配可能會增加一些性能損失。
    ⑦:特定用途的賬號權限:Sentinel 和 Replicas

    -- Sentinel:允許用戶在主和副本實例中都有以下命令權限
    > ACL SETUSER sentinel-user >somepassword +client +subscribe +publish +ping +info +multi +slaveof +config +client +exec on
    OK
    
    -- Replicas:副本需要在主實例上有以下命令權限
    > ACL SETUSER replica-user >somepassword +psync +replconf +ping on
    OK
  • 保存、加載相關:save、load
    通過ACL創建的用戶是保存在內存里的,如果Redis Server重啟則ACL創建的用戶會丟失,所以在創建完用戶后需要用save保存,在重啟之后需要用load加載。有兩種方式進行保存和加載:
    1,使用ACL命令:ACL SAVE、ACL LOAD
    2,使用Redis配置,用戶被定義,然后重啟服務器並生效。 或者使用外部ACL文件,使用ACL LOAD 來導入ACL信息

    注意:ACL的配合文件需要事先手動touch,否則實例啟動會失敗。在redis.conf里配置和acl文件里配置的方法互不兼容,Redis會要求使用其中一種。 否則實例啟動報錯:

    -- 報錯信息
    #Configuring Redis with users defined in redis.conf and at the same setting an ACL file path is invalid. This setup is very likely to lead to configuration errors and security holes, please define either an ACL file or declare users directly in your redis.conf, but not both.

    在redis.conf中指定用戶是一種非常簡單的方法,適用於簡單的用例。 當有多個用戶要定義時,在復雜的環境中,強烈建議使用ACL文件。該2個文件里的配置內容是一致的,可以相互進行配置,如格式如下:在redis.conf和users.acl里的格式

    -- 配置文件
    user default on #ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad ~* +@all
    user zhoujy on #ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad ~* +@all

    ① 保存ACL規則

    -- 保存ACL規則
    > ACL SAVE
    OK

    ② 加載ACL規則

    -- 加載ACL規則
    > ACL LOAD
    OK

    說明:在使用ACL配置文件之后,如果設置了默認用戶(default)規則的話,需要看配置文件中aclfile和requirepass參數的先后順序,密碼以最后出現的為准。

  • 日志相關:顯示最近的ACL安全事件列表
    通過ACL LOG  [<count> | RESET]  返回ACL的日志信息,可以指定條目顯示,也可以進行重置:
    -- 顯示日志信息
    > ACL LOG 1
    1)  1) "count"
        2) (integer) 1
        3) "reason"
        4) "auth"
        5) "context"
        6) "toplevel"
        7) "object"
        8) "AUTH"
        9) "username"
       10) "zhoujy"
       11) "age-seconds"
       12) "282.90499999999997"
       13) "client-info"
       14) "id=5 addr=192.168.163.134:35246 fd=7 name= age=403 idle=0 flags=N db=0 sub=0 psub=0 multi=-1 qbuf=36 qbuf-free=32732 obl=0 oll=0 omem=0 events=r cmd=auth user=zhoujy"
    
    -- 重置日志,類似slow
    > acl log reset
    OK

到此,大致的權限介紹已經結束,后續會不定時更新相關內容。

場景說明

  1. 創建DBA管理賬號
    > ACL SETUSER dba on #6d0ac515af9df81653ed0aa3ffa692663c3f556079791e2f00a4578990da66f3 allkeys +@all
    OK
  2. 創建讀寫賬號
    > ACL SETUSER readwrite on >abc allkeys -@all +@read +@write
    OK
  3. 創建只讀賬號
    > ACL SETUSER readonly on >abc allkeys -@all +@read
    OK
  4. 創建只寫賬號
    > ACL SETUSER write_user on >abc allkeys -@all +@write
    OK
  5. 創建復制賬號
    > ACL SETUSER replica-user >abc -@all +psync +replconf +ping on
    OK
  6. 創建哨兵賬號
    > ACL SETUSER sentinel-user >abc -@all +client +subscribe +publish +ping +info +multi +slaveof +config +client +exec on
    OK
  7. 創建監控賬號
    > ACL SETUSER monitor on >abc +monitor
    OK
  8. 創建指定key、有指定類型權限的賬號
    -- 指定對h開頭的hash類型的key有權限
    > ACL SETUSER ops_user on >abc ~h* +@hash
    OK

    其中key的模式是正則匹配,需要~開頭,針對權限則是hash的類,其權限可以通過ACL CAT hash查看。

注意:以上操作完只有需要執行ACL SAVE。不然重置之后用戶信息全部都清空了。

總結

      在默認配置中,Redis 6(第一個具有ACL的版本)的工作方式與Redis的舊版本完全相同,即每個新連接都能夠調用每個可能的命令並訪問每個鍵,因此ACL功能與舊版本向后兼容。同樣使用requirepass配置指令配置密碼的舊方法仍然可以按預期工作(只是為默認用戶設置密碼)。關於ACL更多的操作指南可以看官方文檔PS:如果后續有補充會繼續更新到文章中。

參考文檔:

https://redis.io/topics/acl

https://redis.io/commands/acl-setuser

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM