从执行上下文开始,让问题变得有意义:
我正在运行在 Linux 的 Windows 子系统中编写的脚本。在这种情况下,编写的脚本有时除了换行符 ( \r\n
) 之外还会累积回车符。
这通常是不可预测的——这可能是我的错误,但我对学习如何不犯这个错误不感兴趣——所以我希望有一种强大的方法来执行带有回车符的脚本。
到目前为止,我想到的是遇到安全层:
<(sed 's/\r//g' script.sh)
bash: /dev/fd/63: 权限被拒绝
在这种情况下,我还没有使文件套接字(或幕后的任何内容)可执行。
bash <(sed 's/\r//g' script.sh) # works
bash <(sed 's/\r//g' foo.py) # ignores foo's hash-bang and fails
第二个选项失败,因为 python 文件顶部的 hash-bang 已被忽略,或者我错过了一些调用步骤。
(临时)选项是:
python3 <(sed 's/\r//g' script.py)
然而,由于 python 二进制文件 ( python<version#>
) 的版本控制,这是有问题的,最好在#! ...
脚本内部的行进行处理。
而且,对于其他 hash-bangables 的生态系统来说,它也会失败——我必须在任何地方都具体化,这对我的小脚本的混乱程度来说是一个很大的障碍。
有没有办法让这个可执行文件不是忽略哈希爆炸,还是以不同的方式解决整体问题的方法?
答案1
在执行之前先修复损坏的文件:
#!/bin/bash
dos2unix script.py
./script.py
对于交互式使用,请在执行文件之前使用包装器脚本来修复该文件。创建一个run_broken_file.sh
包含以下内容的文件名:
#!/bin/bash
dos2unix "$1"
"$@"
然后你就可以运行./run_broken_file.sh ./script.py arg1 arg2 arg3
示例运行:
$ unix2dos script.py
unix2dos: converting file script.py to DOS format...
$ ./script.py
/usr/bin/env: ‘python3\r’: No such file or directory
$ cat -A script.py
#!/usr/bin/env python3^M$
import sys^M$
print(f"hello {sys.argv}")^M$
$ cat run_broken_file.sh
#!/bin/bash
dos2unix "$1"
"$@"
$ ./run_broken_file.sh ./script.py arg1 arg2 'arg3 with spaces'
dos2unix: converting file ./script.py to Unix format...
hello ['./script.py', 'arg1', 'arg2', 'arg3 with spaces']