Oracle 12c用视图作为IMPORT_TABLE_STATS源报ORA-20000问题咨询
问题原因及解决方案
我之前处理过好几起类似的Oracle版本迁移问题,你的情况本质上是Oracle 12c(从12.1版本开始)对DBMS_STATS.IMPORT_TABLE_STATS的参数校验做了严格收紧,直接禁止了将视图作为stattab参数传入的操作——哪怕这个视图是基于单表创建、结构和统计信息表一致也不行。
具体原因拆解
- 12c的DBMS_STATS行为变更:Oracle在12.1版本更新了
DBMS_STATS的内部逻辑,明确要求stattab参数必须指向一个普通堆表(通常是通过DBMS_STATS.CREATE_STAT_TABLE创建的标准统计信息存储表),视图、临时表、分区表等其他对象类型都不再被允许。官方文档也同步更新了这个限制,只是报错信息“ORA-20000: 对象不存在或权限不足”有点误导人,实际是对象类型不符合要求。 - 11g的宽松校验:在11g中,
DBMS_STATS对stattab的校验逻辑比较松散,只要视图的字段结构和标准统计信息表完全匹配,就能绕过校验执行导入。但这从来不是Oracle官方支持的用法,属于一个未被明确禁止的“灰色操作”,12c直接堵上了这个漏洞。 - 权限不是问题:你作为目标表、视图和基表的所有者,权限肯定是足够的,报错的核心原因就是视图不符合
stattab的对象类型要求。
可行的解决方案
规范方案(推荐):
- 先用
DBMS_STATS.CREATE_STAT_TABLE创建一个标准的统计信息存储表,比如:EXEC DBMS_STATS.CREATE_STAT_TABLE(ownname => '你的用户名', stattab => 'MY_STAT_TABLE'); - 将视图中的统计数据插入到这个新创建的表中:
INSERT INTO MY_STAT_TABLE SELECT * FROM 你的视图名; COMMIT; - 最后调用
IMPORT_TABLE_STATS时,用这个标准表作为stattab参数即可。
- 先用
临时应急方案(不推荐长期使用):
- 如果只是临时需要迁移统计信息,可以创建一个和视图结构一致的普通堆表,把视图数据导入后再作为
stattab使用,用完可以删除这个临时表。
- 如果只是临时需要迁移统计信息,可以创建一个和视图结构一致的普通堆表,把视图数据导入后再作为
内容的提问来源于stack exchange,提问作者Micha艂 Herman
相关产品推荐
相关产品推荐

