首批通过分布式安全可靠测评,为关键业务系统打造
物化视图日志
更新时间:2026-07-16 20:01:47
物化视图日志(Materialized View Log,mlog)用于记录基表的增量更新数据,以支持物化视图的快速刷新功能。mlog 是一个记录表,追踪基表的变化,并将这些变化应用于相应的物化视图,实现快速刷新。
OceanBase 数据库支持手动管理物化视图日志和自动管理物化视图日志。
使用限制
- 只能在普通表和物化视图上创建物化视图日志。
- 一张基表只与一个物化视图日志做绑定。
- 在创建物化视图日志时,如果基表正在运行事务,则创建操作将被阻塞,直到该事务结束。
- 物化视图日志支持 LOB 类型的列,但是仅支持 LOB 数据内联存储。有关 LOB 类型的介绍信息,参见 LOB 类型。
- 物化视图日志暂不支持以下四种类型的数据:JSON、XML、空间数据和 UDT。
- 物化视图日志暂不支持生成列(包括虚拟列和非虚拟列)。
- 物化视图日志暂不支持指定分区,其分区和基表的分区是绑定关系。
- 物化视图日志的名称长度上限与普通表相同,不能超过 64 个字符。由于物化视图日志的名称会加上
mlog$_前缀,因此创建物化视图日志的基表名称不能超过 58 个字符。 - 物化视图日志不支持表级恢复。
- 物化视图日志在单独删除时不会进入回收站。
- 物化视图日志在创建后不支持
ALTER操作。 - 物化视图日志上不支持建立索引。
- 物化视图日志不支持进行 DML 操作,会报错。
物化视图日志 Schema 定义
一个表只能有一个物化视图日志,其 Schema 名称为 mlog$_table,其中 table 为基表的名称。
物化视图日志的 Schema 定义如下:
| 列名 | 类型 | 说明 |
|---|---|---|
| sequence$$ | in64_t | 自增列,为物化视图日志(mlog)的主键列。
说明mlog 的主键由基表的主键、所有分区键(如果存在)以及自增列 |
| primary key | 跟随基表 | 基表是有主键表时,mlog 中会记录基表的主键列(如果是复合主键,则会包含多列)。 |
| dmltype$$ | char(1) | 记录 DML 类型。有三种取值,I、D 和 U,分别表示 INSERT、DELETE 和 UPDATE。 |
| old_new$$ | char(1) | 用于 UPDATE 语句中标记旧值和新值,UPDATE 一行会往物化视图日志中写入两行数据,一行是 UPDATE 前的旧值,另一行是 UPDATE 后的新值,分别用 O 和 N 进行标记。 |
| column 1 | 跟随基表 | 基表普通列 1。 |
| ... | N/A | N/A |
| column N | 跟随基表 | 基表普通列 N。 |
| ora_rowscn | N/A | 伪列,记录在存储层的一个隐藏列中,可以读取。 |
| m_row$$ | uint64_t | 基表是无主键表时,mlog 中才会记录该值。mlog 中必须包含基表的主键列。如果基表是无主键表,那么基表隐藏主键的名称在 mlog 中的名称为 M_ROW$$。 |
操作已有的物化视图日志
- 您可以直接查询物化视图日志所在的 Schema 的结构和其中的数据。
- 您可以通过 DBMS_MVIEW.PURGE_LOG(table_name) 来对某个基表的物化视图日志执行
PURGE操作。 - 如果物化视图日志的大小增长到超过可用的磁盘容量,将会报错。此时,您必须先删除该物化视图日志并重新创建,才能继续使用它。
基表操作对物化视图日志的影响
基表 DML 操作
物化视图日志表的定义就是负责记录对基表 DML 操作,因此对基表进行 INSERT、DELETE 和 UPDATE 操作最终都会记录到物化视图日志中,具体如下:
- 对基表进行
INSERT操作,则插入的每行数据也会生成一条记录插入在物化视图日志中;该记录的dmltype$$列值为I,old_new$$列值为N。 - 对基表进行
DELETE操作,则删除的每行数据也会生成一条记录插入在物化视图日志中;该记录的dmltype$$列值为D,old_new$$列值为O。 - 对基表进行
UPDATE操作,则修改的每行数据也会生成两条记录插入在物化视图日志中;第一行记录的是被UPDATE行的旧值,dmltype$$列值为U,old_new$$列值为O;第二行记录的是UPDATE后的新值,dmltype$$列值为U,old_new$$列值为N。
基表 DDL 操作
- V4.4.2 BP2 之前版本,在删除基表之前,需要先删除相应的物化视图日志,否则会报错。因为物化视图日志与基表有一一绑定关系,所以不支持直接删除基表只保留物化视图日志。
- 对于 V4.4.2 版本,从 V4.4.2 BP2 版本开始,可以直接删除基表,无需先删除相应的物化视图日志再删除基表。
更多有关基表支持的 DDL 操作信息,请参见 Online DDL 和 Offline DDL 操作。
自动管理物化视图日志
OceanBase 数据库支持物化视图日志(Materialized View Log,mlog)自动管理功能,该功能包含以下方面:
- 在创建物化视图时,分析物化视图对于基表的依赖,自动创建所需要的 mlog。
- V4.4.2 BP2 之前版本在后台定期裁剪 mlog,删除不被依赖的 mlog,以及精简 mlog 中的列集合,从而降低 mlog 的维护代价。
- 对于 V4.4.2 版本,从 V4.4.2 BP2 版本开始删除物化视图(MV)时,MV 依赖的 mlog 如果不被其他 MV 依赖,则 mlog 会被删除。
OceanBase 数据库默认开启物化视图日志自动管理功能,在创建增量刷新物化视图或实时物化视图时,OceanBase 数据库会自动创建 mlog 或自动更新 mlog 定义。
使用限制
创建物化视图时,只有显式声明为增量刷新物化视图(即指定 REFRESH FAST)或实时物化视图(即指定 ENABLE ON QUERY COMPUTATION),才会自动创建 mlog 或自动更新 mlog 定义。
注意事项
V4.4.2 BP2 之前版本在更新 mlog 定义时,OceanBase 数据库实际会创建一个新的 mlog 表并替换原 mlog,在替换过程中,需要对相关联的增量刷新物化视图做一次增量刷新,将原 mlog 中的增量数据刷入物化视图中,这样才能安全替换 mlog。因此,当一个基表关联的物化视图个数、增量数据量较多时,更新 mlog 定义可能会是一个很耗时的操作,需要提前有所感知。
说明
对于 V4.4.2 版本,从 V4.4.2 BP2 版本起,如果物化视图有新增依赖列,系统将采用 Online 在尾部加列,不再是通过创建新的 mlog 表并替换原有 mlog 表的方式进行操作。
V4.4.2 BP2 之前版本建议
mlog_trim_interval的时间间隔不要设置的太小,否则可能导致 mlog 被误裁剪,创建物化视图时又需要重新创建或更新 mlog。
相关配置
OceanBase 数据库提供了两个配置项以控制 mlog 自动化的行为:
enable_mlog_auto_maintenance:用于控制是否启用物化视图日志自动管理功能。
mlog_trim_interval:用于控制 mlog 后台自动裁剪任务的调度周期。
说明
对于 V4.4.2 版本,
mlog_trim_interval从 V4.4.2 BP2 版本开始不再生效。
示例
启用 mlog 自动化管理功能。
说明
在 OceanBase 数据库 V4.4.2 版本中:
- 对于新创建的租户,其配置项
enable_mlog_auto_maintenance的默认值为True,即默认启用 mlog 自动管理功能。 - 对于由 OceanBase 数据库低版本(即 V4.4.2 之前的版本)升级而来的租户,其配置项
enable_mlog_auto_maintenance的默认值为False,即默认关闭 mlog 自动管理功能。
obclient> ALTER SYSTEM SET enable_mlog_auto_maintenance = True;
示例一:自动创建 mlog
创建表
test_tbl1。obclient> CREATE TABLE test_tbl1(col1 INT, col2 INT, col3 INT);直接在表
test_tbl1上创建增量刷新物化视图mv_test_tbl1。OceanBase 数据库会自动为test_tbl1表在所需的col2列上创建 mlog。obclient> CREATE MATERIALIZED VIEW mv_test_tbl1 REFRESH FAST AS SELECT col2, count(*) cnt FROM test_tbl1 GROUP BY col2;查看表
test_tbl1上物化视图日志的信息。obclient> DESC mlog$_test_tbl1;返回结果如下:
+------------+---------------------+------+------+---------+-------+ | Field | Type | Null | Key | Default | Extra | +------------+---------------------+------+------+---------+-------+ | col2 | int(11) | YES | | NULL | | | SEQUENCE$$ | bigint(20) | NO | PRI | NULL | | | DMLTYPE$$ | varchar(1) | NO | | NULL | | | OLD_NEW$$ | varchar(1) | NO | | NULL | | | M_ROW$$ | bigint(20) unsigned | NO | PRI | NULL | | +------------+---------------------+------+------+---------+-------+ 5 rows in set
示例二:自动更新 mlog 定义
创建表
test_tbl2。obclient> CREATE TABLE test_tbl2(col1 INT, col2 INT, col3 INT);直接在表
test_tbl2上创建增量刷新物化视图mv1_test_tbl2。OceanBase 数据库会自动为test_tbl2表在所需的col2列上创建 mlog。obclient> CREATE MATERIALIZED VIEW mv1_test_tbl2 REFRESH FAST AS SELECT col2, count(*) cnt FROM test_tbl2 GROUP BY col2;查看表
test_tbl2上物化视图日志的信息。obclient> DESC mlog$_test_tbl2;返回结果如下:
+------------+---------------------+------+------+---------+-------+ | Field | Type | Null | Key | Default | Extra | +------------+---------------------+------+------+---------+-------+ | col2 | int(11) | YES | | NULL | | | SEQUENCE$$ | bigint(20) | NO | PRI | NULL | | | DMLTYPE$$ | varchar(1) | NO | | NULL | | | OLD_NEW$$ | varchar(1) | NO | | NULL | | | M_ROW$$ | bigint(20) unsigned | NO | PRI | NULL | | +------------+---------------------+------+------+---------+-------+ 5 rows in set直接在表
test_tbl2上创建增量刷新物化视图mv2_test_tbl2。OceanBase 数据库检测到当前 mlog 表中只包含了col2列,因此会修改现有 mlog 定义,在 mlog 表中增加col3列。obclient> CREATE MATERIALIZED VIEW mv2_test_tbl2 REFRESH FAST AS SELECT col3, count(*) cnt FROM test_tbl2 GROUP BY col3;再次查看表
test_tbl2上物化视图日志的信息,可以观察到表test_tbl2的 mlog 表定义中包含了col2列和col3列。obclient> DESC mlog$_test_tbl2;返回结果如下:
+------------+---------------------+------+------+---------+-------+ | Field | Type | Null | Key | Default | Extra | +------------+---------------------+------+------+---------+-------+ | col2 | int(11) | YES | | NULL | | | SEQUENCE$$ | bigint(20) | NO | PRI | NULL | | | DMLTYPE$$ | varchar(1) | NO | | NULL | | | OLD_NEW$$ | varchar(1) | NO | | NULL | | | M_ROW$$ | bigint(20) unsigned | NO | PRI | NULL | | | col3 | int(11) | YES | | NULL | | +------------+---------------------+------+------+---------+-------+ 6 rows in set删除物化视图
mv1_test_tbl2。obclient> DROP MATERIALIZED VIEW mv1_test_tbl2;查看表
test_tbl2上物化视图日志的信息。obclient> DESC mlog$_test_tbl2;返回结果如下:
+------------+---------------------+------+------+---------+-------+ | Field | Type | Null | Key | Default | Extra | +------------+---------------------+------+------+---------+-------+ | col2 | int(11) | YES | | NULL | | | SEQUENCE$$ | bigint(20) | NO | PRI | NULL | | | DMLTYPE$$ | varchar(1) | NO | | NULL | | | OLD_NEW$$ | varchar(1) | NO | | NULL | | | M_ROW$$ | bigint(20) unsigned | NO | PRI | NULL | | | col3 | int(11) | YES | | NULL | | +------------+---------------------+------+------+---------+-------+ 6 rows in set删除物化视图
mv2_test_tbl2。obclient> DROP MATERIALIZED VIEW mv2_test_tbl2;查看表
test_tbl3上物化视图日志的信息,可以观察到表test_tbl2的 mlog 表已经不存在了。obclient> DESC mlog$_test_tbl2;返回结果如下:
ERROR 1146 (42S02): Table 'test_db.mlog$_test_tbl2' doesn't exist
手动管理物化视图日志
使用权限
- 创建物化视图日志需要对基表的
SELECT权限和CREATE TABLE的权限。 - 修改物化视图日志需要对基表的
ALTER权限。 - 删除物化视图日志需要
DROP TABLE的权限。 - 物化视图日志只能赋予
SELECT权限,不支持其他的 DML 操作。
创建物化视图日志
说明
OceanBase 数据库 mlog 暂时不支持指定分区(Partition),mlog 的 Partition 和基表的 Partition 是绑定关系。
权限要求
创建物化视图日志需要有 CREATE TABLE 和基表的 SELECT 权限。更多有关 OceanBase 数据库权限的详细介绍,请参见 MySQL 模式下的权限分类。
语法
创建物化视图日志的 SQL 语句格式如下:
CREATE MATERIALIZED VIEW LOG ON [database.] table_name
[parallel_clause]
[with_clause]
[mv_log_purge_clause];
参数说明:
table_name:指定物化视图日志对应的基表名称。parallel_clause:可选项,用于指定物化视图日志清理的并行度。with_clause:可选项,指定物化视图日志中包含的辅助列。mv_log_purge_clause:可选项,指定物化视图日志中数据的清除时间。
有关创建物化视图日志语法的详细参数说明信息,请参见 CREATE MATERIALIZED VIEW LOG。
示例如下:
创建表
tbl1。CREATE TABLE tbl1 (col1 INT, col2 VARCHAR(20), col3 INT, PRIMARY KEY(col1, col3)) PARTITION BY HASH(col3) PARTITIONS 10;在
tbl1表上创建物化视图日志。指定并行处理物化视图日志的并行度为5和物化视图日志记录col2列的变更信息,并且会记录变更前后的新值;配置物化视图日志从当前日期开始,每隔1天清理一次过期的物化视图日志记录。CREATE MATERIALIZED VIEW LOG ON tbl1 PARALLEL 5 WITH SEQUENCE(col2) INCLUDING NEW VALUES PURGE START WITH sysdate() NEXT sysdate() + interval 1 day;查看表
tbl1上物化视图日志的信息。DESC mlog$_tbl1;返回结果如下:
+------------+-------------+------+------+---------+-------+ | Field | Type | Null | Key | Default | Extra | +------------+-------------+------+------+---------+-------+ | col1 | int(11) | NO | PRI | NULL | | | col2 | varchar(20) | YES | | NULL | | | col3 | int(11) | NO | PRI | NULL | | | SEQUENCE$$ | bigint(20) | NO | PRI | NULL | | | DMLTYPE$$ | varchar(1) | YES | | NULL | | | OLD_NEW$$ | varchar(1) | YES | | NULL | | +------------+-------------+------+------+---------+-------+ 6 rows in set
修改物化视图日志
权限要求
执行 ALTER MATERIALIZED VIEW LOG 语句,需要当前用户拥有待操作基表的 ALTER 权限。更多有关 OceanBase 数据库权限的详细介绍,请参见 MySQL 模式下的权限分类。
语法
修改物化视图日志的 SQL 语句格式如下:
ALTER MATERIALIZED VIEW LOG ON [database.]table_name alter_mlog_action_list;
alter_mview_action_list:
alter_mlog_action [, alter_mlog_action ...]
alter_mlog_action:
parallel_clause
| PURGE [[START WITH expr] [NEXT expr]]
| LOB_INROW_THRESHOLD [=] integer
parallel_clause:
NOPARALLEL
| PARALLEL integer
参数说明:
database.:可选项,指定物化视图所在的数据库。如果省略database.,则默认基表在当前会话连接的数据库中。table_name:指定物化视图日志对应的基表名称。alter_mlog_action_list:表示可以对物化视图日志执行修改的操作列表。可以同时指定多个操作,使用英文逗号(,)分隔。
有关修改物化视图日志语法的详细参数说明信息,请参见 ALTER MATERIALIZED VIEW LOG。
示例如下:
创建表
test_tbl1。CREATE TABLE test_tbl1 (col1 INT PRIMARY KEY, col2 VARCHAR(20), col3 INT, col4 TEXT);在
test_tbl1表上创建物化视图日志。CREATE MATERIALIZED VIEW LOG ON test_tbl1 WITH SEQUENCE(col2, col3, col4) INCLUDING NEW VALUES;修改表
test_tbl1上物化视图日志的并行度为 5。ALTER MATERIALIZED VIEW LOG ON test_tbl1 PARALLEL 5;修改表
test_tbl1上物化视图日志从当前日期开始,每隔1天清理一次过期的物化视图日志记录。ALTER MATERIALIZED VIEW LOG ON test_tbl1 PURGE START WITH sysdate() NEXT sysdate() + INTERVAL 1 DAY;修改表
test_tbl1上物化视图日志 LOB 内联存储长度阈值。ALTER MATERIALIZED VIEW LOG ON test_tbl1 LOB_INROW_THRESHOLD 10000;
删除物化视图日志
注意事项
- 删除物化视图日志时,如果基表正处于某个运行的事务中,则直到该事务结束前,删除操作都会阻塞。
- 单独删除物化视图日志的时候,物化视图不会进入回收站。
权限要求
删除物化视图日志需要有 DROP TABLE 权限。更多有关 OceanBase 数据库权限的详细介绍,请参见 MySQL 模式下的权限分类。
语法
删除物化视图日志的 SQL 语句格式如下:
DROP MATERIALIZED VIEW LOG ON [database.] table;
参数说明:
database.:可选项,指定物化视图日志基表所在的数据库。如果省略database.,则默认基表在您自己的数据库中。table:指定物化视图日志对应的基表名称。
示例如下:
删除表 tbl1 上的物化视图日志。
DROP MATERIALIZED VIEW LOG ON tbl1;
示例
本示例将展示如何创建普通表、物化视图日志、增量刷新的物化视图,并且介绍如何删除物化视图日志以及增量刷新物化视图的操作信息。
创建表
test_tbl1。CREATE TABLE test_tbl1 (col1 INT PRIMARY KEY, col2 INT, col3 INT);在
test_tbl1表上创建物化视图日志,指定使用序列号(SEQUENCE)来标识变化的数据,列部分指定了要记录的列,其中包括了col2和col3。CREATE MATERIALIZED VIEW LOG ON test_tbl1 WITH SEQUENCE (col2, col3) INCLUDING NEW VALUES;创建名为
mv_test_tbl1的物化视图,定义物化视图为增量刷新,自动刷新物化视图的间隔为 5 分钟;在查询部分,指定了从test_tbl1表中按照col2列进行分组,并计算每个分组中的记录数(cnt)、非空col3列的记录数(cnt_col3)和col3列的总和(sum_col3)作为物化视图的结果。CREATE MATERIALIZED VIEW mv_test_tbl1 REFRESH FAST ON DEMAND START WITH sysdate() NEXT sysdate() + interval 5 minute AS SELECT col2, COUNT(*) cnt, COUNT(col3) cnt_col3, SUM(col3) sum_col3 FROM test_tbl1 GROUP BY col2;查看表
test_tbl1物化视图日志日志信息。SELECT * FROM oceanbase.DBA_MVIEW_LOGS WHERE MASTER = 'test_tbl1';返回结果如下:
+-----------+-----------+-----------------+-------------+--------+-------------+-----------+----------------+----------+--------------------+--------------------+----------------+-------------+----------------+---------------------+-------------------+-----------------+------------------+-------------+-----------+-----------------+ | LOG_OWNER | MASTER | LOG_TABLE | LOG_TRIGGER | ROWIDS | PRIMARY_KEY | OBJECT_ID | FILTER_COLUMNS | SEQUENCE | INCLUDE_NEW_VALUES | PURGE_ASYNCHRONOUS | PURGE_DEFERRED | PURGE_START | PURGE_INTERVAL | LAST_PURGE_DATE | LAST_PURGE_STATUS | NUM_ROWS_PURGED | COMMIT_SCN_BASED | STAGING_LOG | PURGE_DOP | LAST_PURGE_TIME | +-----------+-----------+-----------------+-------------+--------+-------------+-----------+----------------+----------+--------------------+--------------------+----------------+-------------+----------------+---------------------+-------------------+-----------------+------------------+-------------+-----------+-----------------+ | test_db | test_tbl1 | mlog$_test_tbl1 | NULL | NO | YES | NO | YES | YES | YES | NO | NO | NULL | NULL | 2025-09-03 14:13:06 | 0 | 0 | YES | NO | 1 | 0 | +-----------+-----------+-----------------+-------------+--------+-------------+-----------+----------------+----------+--------------------+--------------------+----------------+-------------+----------------+---------------------+-------------------+-----------------+------------------+-------------+-----------+-----------------+ 1 row in set删除表
test_tbl1上的物化视图日志。DROP MATERIALIZED VIEW LOG ON test_tbl1;删除物化视图
mv_test_tbl1。DROP MATERIALIZED VIEW mv_test_tbl1;