requests.get()证书验证失败求助:已用公证书仍报错
解决requests指定CA证书仍报SSL验证失败的问题
问题场景
执行Python代码requests.get('https://website.com')时触发SSL验证错误:
HTTPSConnectionPool(host='www.website.com', port=443): Max retries exceeded with url: /file.php (Caused by SSLError(SSLCertVerificationError(1, '[SSL: CERTIFICATE_VERIFY_FAILED] certificate verify failed: unable to get local issuer certificate (_ssl.c:1129)')))
使用wget --ca-certificate=certificate.crt https://website.com可以成功访问,但改用requests.get('https://website.com', verify='/path/to/cert')仍出现相同报错,且不希望使用verify=False这类不安全的绕过方式。
可能的解决方法
1. 确保证书包含完整信任链
很多时候单独下载的站点证书缺少中间CA或根CA证书,导致requests无法完成完整的信任验证。可以通过以下步骤获取完整证书链:
- 执行openssl命令导出站点的完整证书链:
openssl s_client -connect website.com:443 -showcerts > full_chain.crt - 打开生成的
full_chain.crt,保留所有从-----BEGIN CERTIFICATE-----到-----END CERTIFICATE-----的段落(包括中间CA和根CA),删除其他无关内容。 - 用这个完整链文件作为
verify参数的值:requests.get('https://website.com', verify='/path/to/full_chain.crt')
2. 验证证书路径正确性
确认verify参数指定的路径是有效路径:
- 用Python代码检查路径是否存在:
import os cert_path = "/path/to/your/certificate.crt" print(os.path.isfile(cert_path)) # 输出True表示路径有效 - 优先使用绝对路径,避免相对路径带来的目录歧义。
3. 更新依赖库版本
旧版本的requests或urllib3可能存在证书处理逻辑的bug,更新到最新版本:
pip install --upgrade requests urllib3
4. 合并系统CA池与自定义证书
如果需要同时信任系统默认CA和自定义证书,可以合并两者:
import certifi import requests # 读取系统默认CA证书 with open(certifi.where(), 'rb') as sys_cert_file: sys_certs = sys_cert_file.read() # 读取自定义证书 with open('/path/to/your/certificate.crt', 'rb') as custom_cert_file: custom_cert = custom_cert_file.read() # 合并证书并写入临时文件 combined_cert_path = 'combined_certs.crt' with open(combined_cert_path, 'wb') as combined_file: combined_file.write(sys_certs + b'\n' + custom_cert) # 使用合并后的证书请求 response = requests.get('https://website.com', verify=combined_cert_path)
内容的提问来源于stack exchange,提问作者lkotlus
相关产品推荐
相关产品推荐

