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

解决Django调用外部API时出现的SSLError问题

解决Django站点调用外部API出现"No cipher can be selected" SSL错误

核心原因

这个错误源于生产服务器与API服务器的SSL加密套件无法匹配——生产服务器支持的加密套件列表中,没有API服务器认可的选项,而本地环境的SSL配置包含兼容套件,因此能正常运行。

排查与解决步骤

1. 核对双方支持的SSL加密套件

  • 在生产服务器执行以下命令,查看本地支持的所有加密套件:
    openssl ciphers -v
    
  • 查看API服务器支持的加密套件,执行:
    openssl s_client -connect <你的API_HOST>:443
    
    从输出中找到Cipher字段对应的内容,对比本地列表是否有匹配项。

2. 在requests请求中强制指定兼容的加密套件

如果生产服务器无法快速更新SSL配置,可以在代码中自定义SSL上下文,指定API服务器支持的加密套件:

import requests
import ssl
from requests.adapters import HTTPAdapter
from urllib3.poolmanager import PoolManager
from django.core.exceptions import EmptyResultSet
import json

class CipherAdapter(HTTPAdapter):
    def init_poolmanager(self, *args, **kwargs):
        ctx = ssl.create_default_context()
        # 替换为API服务器支持的加密套件,可从openssl s_client结果中选取
        ctx.set_ciphers('ECDHE-RSA-AES256-GCM-SHA384:ECDHE-RSA-AES128-GCM-SHA256')
        kwargs['ssl_context'] = ctx
        return super().init_poolmanager(*args, **kwargs)

# 使用自定义Adapter发送请求
session = requests.Session()
session.mount('https://', CipherAdapter())

try:
    r = session.post(url, data=json.dumps(dados), headers=headers, timeout=30)
except requests.exceptions.Timeout:
    raise EmptyResultSet(f'Erro API TIMEOUT')
if r.status_code == requests.codes.ok:
    search = r.json()
else:
    search = []

3. 检查依赖库版本兼容性

当前使用的requests 2.28.1和urllib3 1.26.11可能存在SSL相关的已知问题,尝试升级到稳定版:

pip install --upgrade requests==2.31.0 urllib3==2.0.7

升级前务必在测试环境验证,避免影响现有功能。

4. 调整生产服务器的系统SSL配置

检查Linux服务器的/etc/ssl/openssl.cnf文件,找到CipherSuite配置项,确保包含API服务器支持的加密套件。修改后重启Django运行的服务(如uWSGI、Gunicorn)使配置生效。


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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.24 23:54:41