• 发生时间:2023-04-18

  • 问题描述:

    • 重构代码后,跑测试用例时,报错 文件名、目录名或卷标语法不正确
  • 问题类别:软件重构

  • 原因分析:

    • 通过调试日志,发现是调用 Popen 函数时报错。
    cmd = f"{self._tool} -openprj{self._project} -open{self._firmware},0x8000000 -auto -exit",
    self._logger.info(cmd)
    process = Popen(cmd, shell=True)
    
    • 打印 cmd 的取值,没发现异常。反复折腾了一会,最终发现问题:给 cmd 赋值时末尾多加了一个逗号!
    • 多加逗号后,cmd 的类型由 string 变成了 tuple,导致 Popen 解析输入参数时报错。以下是复现代码。
    >>> import subprocess   
    >>> cmd = 'echo hello world'
    >>> subprocess.Popen(cmd)
    <subprocess.Popen object at 0x000002C292ED3DC0>
    >>> hello world
    >>> cmd = 'echo hello world',
    >>> subprocess.Popen(cmd)     
    Traceback (most recent call last):
      File "<stdin>", line 1, in <module>
      File "C:\Users\minieye\AppData\Local\Programs\Python\Python38\lib\subprocess.py", line 858, in __init__
        self._execute_child(args, executable, preexec_fn, close_fds,
      File "C:\Users\minieye\AppData\Local\Programs\Python\Python38\lib\subprocess.py", line 1311, in _execute_child
        hp, ht, pid, tid = _winapi.CreateProcess(executable, args,
    FileNotFoundError: [WinError 2] 系统找不到指定的文件
    >>> cmd
    ('echo hello world',)
    >>> type(cmd)
    <class 'tuple'>
    
  • 解决方案:去除 cmd 赋值语句最后的逗号

  • 实施结果:去除逗号后,测试用例正常运行。

  • 经验总结:

    • Python 代码里在赋值后面添加一个逗号,可能会改变变量类型,由原来的类型变为 tuple。
    • 一定要写测试用例!这样可以减少重构代码引入新问题的概率。像这个低级错误,就是通过跑测试用例发现的。