python-oracledb thin模式连接报DPY-3012字符集不支持错误
问题原因
报错中提到的国家字符集ID 871对应Oracle老版本UTF8字符集,该字符集是基于CESU-8实现的非标准UTF-8编码,和Oracle当前通用的AL32UTF8不是同一套实现。
python-oracledb的免客户端Thin模式为纯Python实现,没有集成Oracle客户端的全量字符集转换能力,目前仅支持国家字符集为AL16UTF16(ID 2000)、AL32UTF8(ID 873)的数据库,检测到数据库配置了ID 871的国家字符集时,无法完成字符集解析逻辑,就会抛出DPY-3012错误。
可行解决方法
- 切换为Thick模式运行
Thick模式是python-oracledb兼容旧版cx_Oracle的运行模式,依赖Oracle Instant Client,支持全部Oracle官方字符集,包括ID 871的UTF8国家字符集。
操作时先下载对应系统版本的Oracle Instant Client Basic包,在连接代码前添加Thick模式初始化逻辑即可,参考代码如下:import oracledb un = 'fred' pwd = 'mypass' host = 'server.mycompany.net' port = 1521 service_name = 'servicea' # 初始化Thick模式,如果Instant Client没加入系统环境变量,添加lib_dir参数指定解压路径即可 # 例:oracledb.init_oracle_client(lib_dir=r"C:\instantclient_19_19") oracledb.init_oracle_client() params = oracledb.ConnectParams(host=host, port=port, service_name=service_name) with oracledb.connect(user=un, password=pwd, params = params ) as connection: with connection.cursor() as cursor: sql = "select * from dim_drug_product" for r in cursor.execute(sql): print(r) - 修改数据库国家字符集配置
如果有数据库管理权限,可以将数据库的NLS_NCHAR_CHARACTERSET参数从UTF8(ID 871)修改为AL32UTF8或者AL16UTF16,修改完成后Thin模式即可正常连接。该操作属于数据库级变更,执行前需要评估对现有业务的影响,提前做好数据备份。 - 升级python-oracledb版本做兼容
若业务查询完全不涉及NCHAR、NVARCHAR2、NCLOB这类国家字符集类型的字段,可以将python-oracledb升级到最新版本,部分新版本对该场景做了降级兼容,会自动使用数据库默认字符集解析字段,不需要额外修改配置。如果查询涉及国家字符集类型字段,该方案会出现乱码或者连接报错,不建议生产环境使用。
内容的提问来源于stack exchange,提问作者smackenzie
相关产品推荐
相关产品推荐

