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

通过Cron执行Python POST请求脚本时出现ConnectionResetError问题求助

解决crontab执行Python POST请求出现ConnectionResetError的问题

看起来你遇到了典型的终端环境与crontab环境差异导致的问题——脚本在终端能正常运行,但定时任务就触发连接重置错误。结合你提供的错误栈(SSL握手阶段失败),我整理了几个针对性的排查和解决方向:

1. 修复crontab的环境变量缺失问题

crontab的运行环境非常精简,默认的PATH和SSL相关环境变量(如CA证书路径)和终端完全不同,这很可能导致SSL握手失败,最终触发连接重置。

解决方法:

  • 方法A:在crontab中指定完整环境变量
    编辑你的crontab任务,开头添加Shell和PATH配置,确保和终端环境一致:

    # 编辑crontab
    crontab -e
    # 添加以下内容在任务上方
    SHELL=/bin/bash
    PATH=/usr/local/sbin:/usr/local/bin:/sbin:/bin:/usr/sbin:/usr/bin
    # 你的定时任务
    * * * * * /usr/bin/python3.6 /location/sa/tb/uc/md/se/sea.py >> ~/Test_log.log 2>&1
    
  • 方法B:在脚本中强制指定SSL证书路径
    如果是CA证书找不到导致的握手失败,可以在requests请求中直接指定系统CA证书的绝对路径:

    import requests
    
    # 替换为你系统的CA证书路径,常见路径如/etc/ssl/certs/ca-bundle.crt或/etc/ssl/certs/ca-certificates.crt
    CA_CERT_PATH = "/etc/ssl/certs/ca-bundle.crt"
    
    try:
        response = requests.post(
            "你的目标URL",
            data={"key": "value"},
            verify=CA_CERT_PATH  # 强制指定证书
        )
        response.raise_for_status()
    except Exception as e:
        print(f"请求失败: {str(e)}")
    

2. 检查crontab的网络访问限制

有些服务器会对crontab进程的网络访问做特殊限制,或者crontab的DNS解析配置和终端不同,导致无法正确连接目标服务器。

排查与解决:

  • 在脚本开头添加DNS解析测试,确认目标域名能正确解析:

    import socket
    
    try:
        ip = socket.gethostbyname("你的目标域名")
        print(f"解析到目标IP: {ip}")
    except socket.gaierror as e:
        print(f"DNS解析失败: {str(e)}")
    

    把这段日志输出到你的Test_log.log,看crontab执行时是否能正常解析域名。

  • 如果是防火墙限制,可以联系运维确认crontab进程是否被允许访问目标端口(通常HTTPS是443)。

3. 添加网络请求重试机制

连接重置(Errno 104)也可能是临时的网络波动导致的——终端执行时刚好避开了波动,但定时任务触发时遇到了。添加重试逻辑可以应对这种情况:

import requests
from requests.adapters import HTTPAdapter
from urllib3.util.retry import Retry

# 创建带重试机制的Session
session = requests.Session()
retry_strategy = Retry(
    total=3,  # 总重试次数
    backoff_factor=1,  # 重试间隔(1秒、2秒、4秒...)
    status_forcelist=[429, 500, 502, 503, 504],  # 需要重试的状态码
    allowed_methods=["POST"]  # 允许重试的请求方法
)
adapter = HTTPAdapter(max_retries=retry_strategy)
session.mount("https://", adapter)
session.mount("http://", adapter)

try:
    response = session.post("你的目标URL", data={"key": "value"})
    response.raise_for_status()
    print("请求成功")
except requests.exceptions.RequestException as e:
    print(f"多次重试后仍失败: {str(e)}")

4. 确保脚本工作目录正确

crontab默认的工作目录是用户的home目录,而终端执行时工作目录是脚本所在目录。如果脚本中有依赖相对路径的资源(比如配置文件、本地证书),会导致加载失败间接影响网络请求。

在脚本开头添加切换工作目录的代码:

import os

# 获取脚本所在的绝对路径
script_dir = os.path.dirname(os.path.abspath(__file__))
# 切换到脚本目录
os.chdir(script_dir)

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.04.29 21:47:34