如何解决Oracle用户在修改密码时提示与历史密码重复?

作者:袖梨 2026-07-07
不行,ORA-28007报错时直接用ALTER USER IDENTIFIED BY "old_password"会失败;Oracle校验的是历史哈希记录是否在PASSWORD_REUSE_TIME和PASSWORD_REUSE_MAX约束范围内,而非明文比对。

ORA-28007报错时直接改回原密码行不行?

不行,alter user user identified by "old_password" 会触发校验,哪怕密码完全一致也会失败。oracle不是比对明文,而是检查历史哈希记录是否在 password_reuse_timepassword_reuse_max 约束范围内。只要策略启用,就拦住。

绕过重用限制的三种实操路径

核心思路是避开明文校验逻辑,分场景选择:

  • 知道原密码且只想“重置为相同值”:用 IDENTIFIED BY VALUES 直接写入哈希值。先查 SELECT spare4 FROM user$ WHERE name = 'USER_NAME',拿到类似 S:ABC... T:DEF... 的哈希串,再执行 ALTER USER user IDENTIFIED BY VALUES 'S:ABC...'
  • 想彻底禁用重用限制:修改 profile,把两个关键参数设为 UNLIMITEDALTER PROFILE default LIMIT password_reuse_time UNLIMITEDALTER PROFILE default LIMIT password_reuse_max UNLIMITED。注意:二者必须同时设为 UNLIMITED,只设一个反而会让密码永远无法重置
  • 临时绕过(仅限DBA操作):用 CREATE USER temp_user IDENTIFIED BY "desired_password" 创建临时用户,查其 spare4 哈希,再用该哈希更新目标用户。此法不依赖 profile 修改,但需有 SELECT ANY TABLE 权限访问 user$

profile修改后为什么还要执行一次ALTER USER?

很多人以为改完 profile 就万事大吉,结果 JDBC 连接仍报错。这是因为 Oracle 的密码有效期和重用策略是“惰性生效”的——只有在真正执行 ALTER USER ... IDENTIFIED BY 时才会刷新内部状态。即使新旧密码相同,也必须触发一次显式修改,否则连接层仍按旧策略校验。

容易被忽略的兼容性坑

哈希值格式必须匹配客户端版本。12c+ 默认用 T: 开头的新哈希,但老应用可能只认 S:。如果用 spare4 查到的是 T: 哈希,而客户端是 11g,IDENTIFIED BY VALUES 可能静默失败或登录报 ORA-01017。此时得确认 SQLNET.ALLOWED_LOGON_VERSION_SERVER 设置,并考虑降级哈希生成方式(如用 11g 实例导出再导入)。

相关文章

精彩推荐