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

SONiC设备使用pexpect.spawn运行bash脚本触发EOF异常排查

问题概述

在SONiC设备环境中,使用Python pexpect模块的spawn方法调用bash运行/home/admin/eeprom_test_01.sh测试脚本,计划通过expect匹配交互提示、sendline自动输入应答完成自动化测试,初始实现代码如下:

import pexpect
child = pexpect.spawn("/bin/bash", ['/home/admin/eeprom_test_01.sh'])
child.expect("Type 'Continue' to proceed, else abort:")
child.sendline("Continue")
child.expect("Select Capitaine revision\(EVT or DVT\):")
child.sendline("DVT")
child.expect("EEPROM Device: COMe")
return child

运行代码时触发pexpect.exceptions.EOF异常,自动化流程中断,关键报错信息如下:

EOF: End Of File (EOF). Exception style platform.
<pexpect.pty_spawn.spawn object at 0x7fa381be9978>
command: /bin/bash
args: ['/bin/bash', '/home/admin/eeprom_test_01.sh']
before (last 100 chars): b'/bin/bash: /home/admin/eeprom_test_01.sh: No such file or directory\r\n'
exitstatus: 127
flag_eof: True
searcher: searcher_re:
0: re.compile(b"Type 'Continue' to proceed, else abort:")

从报错信息可以确认:bash提示目标脚本路径不存在,子进程退出状态码为127,在匹配首个交互提示前子进程就已终止,触发EOF异常。

根因定位

报错核心指向执行代码的运行上下文中,无法通过代码里写的绝对路径找到目标测试脚本,常见触发场景:

  • 脚本实际存放路径和代码中填写的路径不一致,存在文件名拼写错误、大小写错误、文件被移动/删除的情况
  • 运行Python代码的用户权限不足,无法访问/home/admin目录或目标脚本文件
  • SONiC系统大部分功能运行在隔离容器中,如果这段Python代码是在容器内执行,容器默认不会挂载宿主机的/home/admin目录,会导致容器内的bash找不到对应脚本

注:当前spawn的传参逻辑没有问题,报错中打印的执行参数为['/bin/bash', '/home/admin/eeprom_test_01.sh'],对应执行的命令就是/bin/bash /home/admin/eeprom_test_01.sh,符合预期;且显式调用bash执行脚本不需要脚本本身具备可执行权限,仅需要读权限,权限问题仅会触发Permission denied报错,和当前No such file or directory的报错特征不符。

修复方案

按以下优先级排查修复:

  1. 先进入和Python代码完全一致的运行上下文(同用户、同容器/宿主机环境),手动执行命令验证文件可达性:
    /bin/bash /home/admin/eeprom_test_01.sh
    
    • 如果手动执行同样报No such file or directory:
      • 容器内运行场景:将测试脚本拷贝到容器内的/home/admin路径下,或启动容器时增加挂载参数,把宿主机/home/admin目录映射到容器内相同路径
      • 宿主机运行场景:执行find / -name "eeprom_test_01.sh"定位脚本真实存放路径,将代码中的脚本路径替换为查到的实际绝对路径
  2. 路径问题修复后,优化代码鲁棒性,避免异常直接中断流程,优化后参考代码:
import pexpect
import sys

def run_eeprom_test():
    try:
        # 直接传完整命令字符串写法更简洁不易出错,增加编码、超时配置,开启读日志方便调试
        child = pexpect.spawn(
            "/bin/bash /home/admin/eeprom_test_01.sh",
            encoding="utf-8",
            timeout=60
        )
        child.logfile_read = sys.stdout

        # 每一步expect都把EOF、TIMEOUT加入匹配列表,提前捕获异常
        match_res = child.expect([
            "Type 'Continue' to proceed, else abort:",
            pexpect.EOF,
            pexpect.TIMEOUT
        ])
        if match_res != 0:
            print(f"脚本启动失败,缓冲区输出:{child.before}")
            child.close()
            return None
        child.sendline("Continue")

        match_res = child.expect([
            "Select Capitaine revision\(EVT or DVT\):",
            pexpect.EOF,
            pexpect.TIMEOUT
        ])
        if match_res != 0:
            print(f"确认步骤执行失败,缓冲区输出:{child.before}")
            child.close()
            return None
        child.sendline("DVT")

        match_res = child.expect([
            "EEPROM Device: COMe",
            pexpect.EOF,
            pexpect.TIMEOUT
        ])
        if match_res != 0:
            print(f"版本选择步骤执行失败,缓冲区输出:{child.before}")
            child.close()
            return None
        
        return child
    except Exception as e:
        print(f"测试执行异常:{str(e)}")
        return None

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.26 14:54:19