数据分支权限模型¶
每条 DATA BRANCH 命令现在要求对源对象和目标对象持有特定于操作类型的作用域权限。本文档说明每条分支操作的权限要求、用户可能遇到的错误消息以及受保护数据库机制。
说明¶
MatrixOne 对所有 DATA BRANCH SQL 命令强制执行细粒度的权限检查。每种操作类型需要对源和目标表或数据库持有特定级别的对象权限。权限模型还包括跨账号克隆限制、系统数据库保护以及防止意外删除的受保护数据库机制。
语法¶
权限模型通过标准的 SQL GRANT 和 REVOKE 语句强制执行。以下是每条 DATA BRANCH 操作所需的权限模式。
DATA BRANCH CREATE TABLE¶
GRANT SELECT ON TABLE <source_db>.<source_table> TO <role>;
GRANT CREATE TABLE ON DATABASE <target_db> TO <role>;
DATA BRANCH CREATE DATABASE¶
GRANT SELECT ON TABLE <source_db>.<source_table> TO <role>;
GRANT CREATE DATABASE ON ACCOUNT * TO <role>;
DATA BRANCH DIFF¶
GRANT SELECT ON TABLE <db>.<target_table> TO <role>;
GRANT SELECT ON TABLE <db>.<base_table> TO <role>;
# 使用 OUTPUT AS <target_db>.<table> 时还需要:
GRANT CREATE TABLE ON DATABASE <target_db> TO <role>;
DATA BRANCH MERGE¶
GRANT SELECT ON TABLE <db>.<source_table> TO <role>;
GRANT SELECT, INSERT, UPDATE, DELETE ON TABLE <db>.<destination_table> TO <role>;
DATA BRANCH PICK¶
GRANT SELECT ON TABLE <db>.<source_table> TO <role>;
GRANT SELECT, INSERT, UPDATE, DELETE ON TABLE <db>.<destination_table> TO <role>;
GRANT SELECT ON TABLE <db>.<keys_table> TO <role>;
DATA BRANCH DELETE TABLE¶
GRANT DROP TABLE ON DATABASE <db> TO <role>;
DATA BRANCH DELETE DATABASE¶
GRANT DROP DATABASE ON ACCOUNT * TO <role>;
参数说明¶
权限 |
作用域 |
说明 |
|---|---|---|
|
表级 |
允许从指定表读取行。源表的所有分支读取操作及 DIFF、MERGE、PICK 的双方均需要此权限。 |
|
数据库级 |
允许在指定数据库中创建新表。 |
|
账号级 |
允许在账号中创建新数据库。 |
|
表级 |
允许向指定表插入新行。 |
|
表级 |
允许修改指定表中的现有行。 |
|
表级 |
允许从指定表删除行。 |
|
数据库级 |
允许在指定数据库中删除表。 |
|
数据库级 |
允许在指定数据库中删除对象。可满足 |
|
账号级 |
允许在账号中删除数据库。 |
|
数据库级 |
授予数据库级的所有权限。可满足作用于数据库的 |
|
数据库级 |
授予数据库的所有权级权限。可满足作用于数据库的 |
|
账号级 |
授予账号级的所有权限。可满足 |
各操作的权限要求¶
DATA BRANCH CREATE TABLE¶
从源表创建分支表。
对象 |
所需权限 |
|---|---|
源表 |
|
目标数据库 |
以下之一: |
跨账号克隆需要快照。仅 sys 账号可以将表克隆到其他账号。
DATA BRANCH CREATE DATABASE¶
从源数据库创建分支数据库。
对象 |
所需权限 |
|---|---|
每个源表 |
|
目标 |
|
DATA BRANCH DELETE TABLE¶
删除分支表。目标必须是活跃的分支表(由先前的 DATA BRANCH CREATE TABLE 创建)。
对象 |
所需权限 |
|---|---|
目标数据库 |
以下之一: |
对于非系统数据库,表所有权也满足要求。
DATA BRANCH DELETE DATABASE¶
删除分支数据库。目标数据库中的所有表必须是活跃的分支表。
对象 |
所需权限 |
|---|---|
账号 |
以下之一: |
对于非系统数据库,数据库所有权也满足要求。
DATA BRANCH DIFF¶
比较两个表并输出差异。
对象 |
所需权限 |
|---|---|
目标表 |
|
基准表 |
|
|
|
DATA BRANCH MERGE¶
将源表的变更合并到目标表中。
对象 |
所需权限 |
|---|---|
源表 |
|
目标表 |
|
DATA BRANCH PICK¶
按主键将源表中选定的行拷贝到目标表中。
对象 |
所需权限 |
|---|---|
源表 |
|
目标表 |
|
KEYS 子查询表 |
|
跨账号克隆限制¶
从一个账号克隆表或数据库到另一个账号需要快照(
{snapshot = '<name>'}或{timestamp = <expr>})。仅
sys账号用户可以将表克隆到其他账号。COPY GRANTS不能与TO ACCOUNT一起使用。
系统数据库保护¶
非 sys 账号不能从系统数据库(mo_catalog、system、information_schema)克隆数据。任何账号都不能将数据克隆到系统数据库中。
受保护数据库¶
MatrixOne 支持 protected_databases 系统变量,可将指定数据库标记为受保护,防止意外删除。
SET GLOBAL protected_databases = 'db1,db2';
当数据库在 protected_databases 中列出时:
对受保护数据库执行
DROP DATABASE会被拒绝,即使用户拥有DatabaseAll和DatabaseOwnership权限。对受保护数据库的其他操作(SELECT、INSERT、UPDATE、DELETE、CREATE TABLE、ALTER TABLE、CREATE VIEW)仍然可用,但仍受各自限制;其中,对 data-branch lineage 表执行
ALTER TABLE时不能处于显式事务中。只有能够设置全局变量的用户才能修改
protected_databases。
REPLACE INTO 的 DELETE 权限¶
当 REPLACE INTO 遇到唯一键冲突时,会在内部执行对冲突行的 DELETE。用户必须同时持有 DELETE 权限以及 SELECT 和 INSERT 权限,REPLACE INTO 才能在冲突路径上成功执行。纯插入路径(无冲突,如 NULL 唯一值)无需 DELETE 权限即可成功。
示例¶
以下脚本把管理员准备步骤与 u_branch 用户实际执行的语句分开。mo-tester 会识别 -- @session 指令;手工验证时,应为指令包围的语句另开一个 u_branch 连接。
DROP DATABASE IF EXISTS dbbranchpriv;
CREATE DATABASE dbbranchpriv;
USE dbbranchpriv;
-- 创建分支操作的源表和数据
CREATE TABLE src_t(a INT PRIMARY KEY, b VARCHAR(20));
INSERT INTO src_t VALUES (1, 'one'), (2, 'two');
-- 创建 DIFF 操作的目标表
CREATE TABLE target_t(a INT PRIMARY KEY, b VARCHAR(20));
INSERT INTO target_t VALUES (1, 'ten'), (3, 'thirty');
-- 创建表级分支操作的快照
CREATE SNAPSHOT sp_t FOR TABLE dbbranchpriv src_t;
-- 创建对源表拥有 SELECT 权限、对数据库拥有 CREATE TABLE 权限的角色
CREATE ROLE r_branch;
GRANT SELECT ON TABLE dbbranchpriv.src_t TO r_branch;
GRANT SELECT ON TABLE dbbranchpriv.target_t TO r_branch;
GRANT CREATE TABLE ON DATABASE dbbranchpriv TO r_branch;
CREATE USER u_branch IDENTIFIED BY '111' DEFAULT ROLE r_branch;
-- 通过真实的 u_branch 连接执行以下语句
-- @session:id=1&user=sys:u_branch&password=111
-- DATA BRANCH CREATE TABLE:从源快照创建分支表
DATA BRANCH CREATE TABLE dbbranchpriv.branch_t FROM dbbranchpriv.src_t{snapshot="sp_t"};
-- 验证分支表包含源数据
SELECT COUNT(*) FROM dbbranchpriv.branch_t;
-- DATA BRANCH DIFF:比较两个表并输出差异
DATA BRANCH DIFF dbbranchpriv.target_t AGAINST dbbranchpriv.src_t OUTPUT COUNT;
-- 清理前返回管理员会话
-- @session
-- 错误示例:DATA BRANCH DELETE TABLE 在目标不是分支创建的表时失败
-- Expected-Success: false
DATA BRANCH DELETE TABLE dbbranchpriv.target_t;
-- 清理
DROP SNAPSHOT sp_t;
DROP USER u_branch;
DROP ROLE r_branch;
DROP DATABASE IF EXISTS dbbranchpriv;
错误消息¶
错误 |
原因 |
|---|---|
|
尝试的分支操作缺少所需权限 |
|
非 sys 账号尝试从 |
|
尝试克隆到系统数据库 |
|
DELETE 目标不是分支创建的表 |
|
DELETE 目标数据库没有活跃的分支表 |
|
将 COPY GRANTS 与跨账号克隆组合使用 |
|
跨账号克隆未提供快照 |
使用说明¶
内部系统用户和启用
SkipCheckPrivilege时会跳过权限检查。DATA BRANCH CREATE DATABASE在权限检查期间解析源表,以确保授权和执行使用相同的对象集。对于
DATA BRANCH DELETE TABLE和DELETE DATABASE,系统会验证目标对象是否为活跃的分支对象(记录在mo_catalog.mo_branch_metadata中)。需要多个权限的分支操作会独立检查每个权限;缺少任一权限都会导致整个语句失败。