Oracle限制CPU需配置消费者组、计划指令和映射规则三要素,缺一不可;ALTER PROFILE的cpu_per_session在12c+已废弃,仅当资源管理器启用且用户归属指定组时才生效。
oracle 没有“资源队列”这个概念——这是 postgresql 或 greenplum 的术语。你要的其实是 resource_manager 里的消费者组(consumer_group)+ 计划指令(plan_directive),它才是 oracle 唯一能对用户 cpu 做硬性调度控制的机制。
为什么 ALTER PROFILE cpu_per_session 不起作用
你改了 CPU_PER_SESSION 却发现大查询照样吃满 CPU,根本原因是:该字段在 12c+ 已废弃,仅保留兼容性;它单位是“十分之一秒”(如值 3600 = 360 秒),但前提是用户必须落在一个被显式分配了 CPU_P1 等指令的 CONSUMER_GROUP 中,且整个资源管理器已启用。否则,它只统计、不干预,更不会中断运行中语句。
- 常见错误现象:
v$session中该用户的consumer_group是OTHER_GROUPS - 根本原因:没建组、没设映射、没启用
resource_manager_plan - 验证命令:
SELECT value FROM v$parameter WHERE name = 'resource_manager_plan'—— 返回空值即未启用
必须配齐三要素才能让 CPU 限制生效
缺一不可:消费者组、计划指令、映射规则。漏掉任意一个,用户自动 fallback 到 OTHER_GROUPS,而该组默认无任何 CPU 配额。
- 建组不能动
DEFAULT_CONSUMER_GROUP:它是系统保留组,必须用DBMS_RESOURCE_MANAGER.CREATE_CONSUMER_GROUP新建 - 计划指令必须显式指定
CPU_P1(或CPU_P2…CPU_P8):数值是该优先级内可分配的 CPU 百分比上限,不是保证值;未用完部分会下放给低一级 - 映射要设优先级:
DBMS_RESOURCE_MANAGER.SET_CONSUMER_GROUP_MAPPING_PRI(oracle_user => 1),否则可能被client_id或service_name覆盖 - 所有操作前必须
CREATE_PENDING_AREA(),提交后必须SUBMIT_PENDING_AREA(),否则全是内存草稿,重启即丢
如何让限制真正作用到目标用户
光配好组和指令还不够,用户得能切进去。Oracle 默认不允许用户自行切换 consumer group,必须显式授权。
- 执行授权:
DBMS_RESOURCE_MANAGER_PRIVS.GRANT_SWITCH_CONSUMER_GROUP('your_user', 'YOUR_GROUP', FALSE) - 确认用户已映射:
SELECT username, consumer_group FROM dba_users u JOIN v$session s ON u.username = s.username WHERE u.username = 'YOUR_USER' - 启用 plan 是硬门槛:在
CDB$ROOT中执行ALTER SYSTEM SET resource_manager_plan = 'DEFAULT_PLAN' SCOPE=BOTH(DEFAULT_PLAN是 Oracle 自带的基础计划,支持用户级控制) - 注意:自定义 plan 若未显式包含
PDB_DIRECTIVE或GROUP_OR_SUBPLAN指令,配了也白配
最容易被忽略的是:resource_manager_plan 必须非空,且用户 session 必须真实落在你配置的 consumer group 下——这两点不满足,后面所有参数都只是纸面配置。


















