You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Pydap调用open_url访问ORNL DAAC数据报UnicodeDecodeError如何解决?

问题根因

从报错堆栈可以定位到问题出在老版本pydap的dap.py模块逻辑:当服务端返回的HTTP响应头没有明确指定charset编码时,老版本pydap会强制将响应编码设为ascii,但ORNL DAAC的Thredds服务返回的响应要么是UTF-8编码的元数据,要么默认开启了gzip压缩(错误里的0x8b就是gzip文件的开头魔数),用ascii解码就会触发UnicodeDecodeError。

可行解决方案

方案1:升级pydap版本(优先推荐)

这个硬编码编码的问题是pydap的已知历史bug,新版本已经完成修复。直接执行命令升级pydap即可:

pip install --upgrade pydap

升级完成后直接运行原有代码即可正常请求ORNL的OPeNDAP接口。

方案2:手动修改pydap源码(无法升级版本时用)

如果你的环境有依赖冲突不能升级pydap,可以直接修改本地安装的pydap源码:
找到报错日志里的对应文件路径 ~/bc/lib/python3.8/site-packages/pydap/handlers/dap.py,将第56行的

r.charset = 'ascii'

修改为

r.charset = 'utf-8'

保存后重新运行代码即可生效。

方案3:请求时禁用gzip压缩(无需改源码/升级版本)

在创建认证session之后,给session增加禁用压缩的请求头,让服务端返回纯文本的未压缩响应,就可以避开ascii解码失败的问题:

from pydap.client import open_url
from pydap.cas.urs import setup_session

dataset_url = 'https://thredds.daac.ornl.gov/thredds/dodsC/ornldaac/1840/daymet_v4_daily_na_dayl_2009.nc'
session = setup_session(username='****', password='****', check_url=dataset_url)
# 新增下面这行,禁用gzip压缩
session.headers.update({'Accept-Encoding': 'identity'})
dataset = open_url(dataset_url, session=session)
额外注意事项

检查你的业务代码是否把创建好的带认证的session参数正确传给了open_url方法,从报错堆栈来看出错的代码行没有传入session参数,未通过EarthData认证的请求会收到服务端返回的错误响应,也可能触发解码异常。

内容的提问来源于stack exchange,提问作者mbexhrs3

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.28 16:15:06