必须同时修改SQLNET.ALLOWED_LOGON_VERSION_SERVER和SQLNET.ALLOWED_LOGON_VERSION_CLIENT两个参数,推荐值均为12,以兼顾安全与兼容性,且需在数据库服务器端$ORACLE_HOME/network/admin/sqlnet.ora中配置。
sqlnet.ora里必须改哪两个参数
ora-28040 的核心原因是 oracle 19c 默认拒绝旧版认证协议,而 sqlnet.allowed_logon_version_server 和 sqlnet.allowed_logon_version_client 这两个参数共同控制协议兼容性。只改其中一个没用,必须同时设置。
推荐值为 12,既满足 Oracle 19c 安全要求,又兼容 Navicat 常用的 OCI 或 JDBC 驱动(如 Instant Client 12.1+、ojdbc7):
sqlnet.allowed_logon_version_server = 12sqlnet.allowed_logon_version_client = 12
不要设成 8 或 10——虽然能连上,但会绕过密码哈希强度校验,DBA 通常不允许。
sqlnet.ora 文件在哪改、怎么确认生效
文件路径在数据库服务器端:$ORACLE_HOME/network/admin/sqlnet.ora。不是 Navicat 本地的配置文件,改错位置毫无作用。
修改后必须重启监听器(lsnrctl stop && lsnrctl start),部分环境还需重启数据库实例(shutdown immediate; startup;)才能加载新参数。
验证是否生效的方法:
- 连接数据库后执行:
SELECT * FROM v$parameter WHERE name LIKE 'sqlnet%logon%'; - 或直接查监听日志:
tail -f $ORACLE_HOME/network/log/listener.log,连一次看有没有 “Authentication protocol rejected” 类提示
为什么改了 sqlnet.ora 还是报 ORA-28040
常见干扰项比参数本身还容易让人误判:
- Navicat 没用上你配的服务器参数——它走的是 JDBC Thin 模式(默认),不读
sqlnet.ora,此时必须换驱动(如用ojdbc6.jar)或切 OCI 模式 - 客户端用了新版
ojdbc8.jar,它强制要求 AES 加密,而服务器没开SQLNET.ENCRYPTION_SERVER = REQUIRED,就会静默失败 - 参数写错格式:比如写成
SQLNET.ALLOWED_LOGON_VERSION=12(漏了_SERVER后缀),Oracle 直接忽略该行 - 文件编码是 UTF-8 with BOM,Oracle 读取失败,参数未加载——建议用
vi或 Notepad++ 保存为 ANSI/UTF-8 no BOM
OCI 模式下 sqlnet.ora 还管不管用
管用,但前提是 Navicat 真正加载了你指定的 OCI 库,且该库版本 ≥ 12.1。
检查方式:
- Navicat 中:工具 → 选项 → 环境 → OCI 环境,路径必须指向含
oci.dll(Windows)或libclntsh.so(Linux)的目录 - 该目录下必须有配套的
sqlnet.ora(可复制服务器端的过来),否则 OCI 会 fallback 到默认策略 - 启动 Navicat 前,确保系统环境变量
TNS_ADMIN没指向其他冲突的sqlnet.ora
最稳妥的做法:把服务器端那份 sqlnet.ora 复制到 OCI 客户端目录,并确认其中 sqlnet.allowed_logon_version_server 已设为 12。


















