用户权限管理

管理员,用户和组

管理员可以创建其他管理员、用户和组。非管理员的用户不能创建其他用户或组。

当DolphinDB集群第一次启动时,会自动创建一个管理员,用户ID为"admin",密码为"123456"。"admin"管理员具有所有的权限,并且不能被删除。其他管理员在刚创建时,是没有任何权限的,需要手动赋予他权限。

管理员可以赋予或禁止其他管理员,用户和组的权限,亦可撤销权限设置。

用户可以属于0,1或多个组。把用户添加到组或把用户从组中移除会影响用户的访问权限。

访问权限

DolphinDB支持以下9种类型的权限:

1. TABLE_READ:读取指定数据表

2. TABLE_WRITE:写入指定数据表

3. DBOBJ_CREATE:在某个数据库中创建数据表

4. DBOBJ_DELETE:删除某个数据库中的数据表

5. VIEW_EXEC:执行某个视图

6. DB_MANAGE:创建以及删除数据库。可删除任何人所建数据库,包括具有DB_OWNER权限之用户所建数据库。

7. DB_OWNER:创建数据库并管理其创建的数据库,包括删除数据库、创建或删除数据表、增加或删除分区、可赋予、禁止或取消其他用户对自己创建的数据库的以下权限:TABLE_READ, TABLE_WRITE, DBOBJ_CREATE, DBOBJ_DELETE。

8. SCRIPT_EXEC:执行脚本

9. TEST_EXEC:执行测试脚本

可以使用 grantdenyrevoke 命令来赋予权限、禁止权限,以及撤销权限设置。以上的9种权限类型作为这三个命令中的accessType参数。在设置访问权限1-5时,还需要指定权限应用的具体对象。

用户的权限是由其本身的权限以及所属组的权限共同决定的:

  • 如果用户在组中被授予一种权限,并且该用户所在的其他组没有禁止这个权限,那么该用户拥有这个权限。

  • 若某用户被赋予了某权限,但在这之后,其所属的某个组被禁止了此权限,那么该用户不具备此权限。若使该用户重新具备此权限,管理员可以使用grant命令重新赋予该权限,或者使用revoke命令撤销之前的禁止权限,并且赋予该用户或该用户所属的组此权限。

当用户安排计划作业时,他不需要具备与对象相关的权限。但是,执行计划作业时,用户需要具备与对象相关的权限。

流数据表相关权限管理:

1. 可以对流数据表的READ权限进行赋予权限、禁止权限,以及撤销权限的设置。赋予READ权限后,可以对流表进行读取、写入和删除的权限。

2.当用户使用 subscribeTable 函数订阅流数据表之前,应当确认其是否具有流表的访问管理权限。 没有 READ 权限的用户不能订阅或者发布该流表。同时,如果订阅时需要将实时数据存入数据表,需要确保用户具有向保存流数据的表写入数据的权限。

3. 集群上对流数据表进行权限管理,权限对象必须为"nodeAlias:tableName",比如:deny(`amy,TABLE_READ,"DFS_NODE1:st"), DFS_NODE1为流数据表所在节点Alias,st为流数据表名。

4. 使用grant赋予流数据表权限后,建议使用revoke进行撤销。

例子

1. 以管理员身份登录系统,并创建数据库 dfs://db1 以及其内的数据表 pt1。

$ login(`admin, `123456);

$ n=1000000
$ ID=rand(10, n)
$ x=rand(100, n)
$ t1=table(ID, x)

$ db=database("dfs://db1", HASH,  [INT, 2]);
$ pt1 = db.createPartitionedTable(t1, `pt1, `ID)
$ pt1.append!(t1)

2. 创建名为"football"的组,该组包含3个成员,分别是EliManning、JoeFlacco和DeionSanders。该组的所有成员都可以读取 dfs://db1/pt1 表中的数据。用户DeionSanders可以创建或删除数据库。

$ createUser(`EliManning, "AB123!@")
$ createUser(`JoeFlacco, "CD234@#")
$ createUser(`DeionSanders, "EF345#$")
$ createGroup(`football, `EliManning`JoeFlacco`DeionSanders)
$ grant(`football, TABLE_READ, "dfs://db1/pt1")
$ grant("DeionSanders", DB_MANAGE);

用户EliManning不可创建数据库:

$ login(`EliManning, "AB123!@");
$ db=database("dfs://db2", HASH,  [INT, 2]);

$ db = database("dfs://db2", HASH, [4,2]) => Not granted to create or delete databases.

3. 增加两个成员到"football"组中,并且把JoeFlacco从组中移除。使用 getUsersByGroupId 函数可以获取"football"组中的用户。

$ login(`admin, `123456);

$ createUser(`AlexSmith, "GH456$%")
$ createUser(`NickFoles, "IJ567%^")
$ addGroupMember(`AlexSmith`NickFoles, `football)
$ deleteGroupMember(`JoeFlacco, `football)
$ getUsersByGroupId(`football);

["AlexSmith","DeionSanders","EliManning","NickFoles"]

4. 创建名为"baseball"的组,该组包含3个成员,分别是CliffLee、ShoheiOhtani和DeionSanders。

$ createUser(`CliffLee, "GH456$%")
$ createUser(`ShoheiOhtani, "IJ567%^")
$ createGroup(`baseball, `CliffLee`ShoheiOhtani`DeionSanders)

DeionSanders属于两个组。使用 getGroupsByUserId 函数可以获取DeionSanders所在的组。

$ getGroupsByUserId(`DeionSanders);

["football","baseball"]

进行以下权限设置:

$ grant(`baseball, DBOBJ_CREATE, "dfs://db2")
$ deny(`baseball, TABLE_READ, "dfs://db1/pt1")
$ deny(`baseball, DB_MANAGE);

"football"组可以读取dfs://db1/pt1表,而"baseball"组被禁止了该权限。因此,DeionSanders不具有该权限。

$ login(`DeionSanders, "EF345#$");
$ t = loadTable("dfs://db1","pt1");

$ t = loadTable("dfs://db1", "pt1") => Not granted to read table dfs://db1/pt1

尽管DeionSanders之前已经被赋予了创建和删除数据库的权限,但是步骤4中的“baseball”组被禁止了该权限。DeionSanders作为"baseball"组的一个成员,也被禁止了该权限。当DeionSanders不属于"baseball"组,或撤销禁止"baseball"组创建和删除数据库的权限,或授予"baseball"组该权限时,用户DeionSanders才具有创建和删除数据库的权限。

5. 定义一个计算表 dfs://db1/pt1 行数的函数,将它定义为视图,并赋予"baseball"组执行该视图的权限。

$ login(`admin, `123456);

$ def countPt1(){
$     return exec count(*) from loadTable("dfs://db1","pt1")
$ }

$ addFunctionView(countPt1)
$ grant("baseball", VIEW_EXEC, "countPt1");

尽管"baseball"组没有读取表 dfs://db1/pt1 的权限,但是该组成员可以通过视图countPt1来获取表中的记录条数。以ShoheiOhtani身份登录,执行以下脚本:

$ login(`ShoheiOhtani, "IJ567%^");
$ countPt1();

1000000

6. 定义一个函数,以计算表 dfs://db1/pt1 中ID为指定值的某列的最大值,将其定义为视图,并赋予"baseball"组执行该视图的权限。

$ login(`admin, `123456);

$ def getMax(column, idValue){
$ return exec max(column) from loadTable("dfs://db1","pt1") where id=idValue
$ }

$ addFunctionView(getMax)
$ grant("baseball", VIEW_EXEC, "getMax");

用户CliffLee可以登录并执行视图getMax。

$ login(`CliffLee, "GH456$%")
$ getMax(x, 6);

99

7. 管理员赋予用户 MitchTrubisky DB_OWNER的权限:

$ login(`admin, `123456);
$ createUser(`MitchTrubisky, "JI3564^")
$ grant(`MitchTrubisky,DB_OWNER);

MitchTrubisky创建数据表 dfs://dbMT/dt,并赋予用户 NickFoles读取该数据表的权限:

$ login(`MitchTrubisky, "JI3564^");
$ db = database("dfs://dbMT", VALUE, 1..10)
$ t=table(1..1000 as id, rand(100, 1000) as x)
$ dt = db.createTable(t, "dt").append!(t)
$ grant(`NickFoles, TABLE_READ, "dfs://dbMT/dt");

用户 NickFoles 登录并读取 dfs://dbMT/dt 数据进行计算:

$ login(`NickFoles, "IJ567%^")
$ select max(x)-min(x) from loadTable("dfs://dbMT", "dt");

99