是否可以将脚本通过管道传输到 WScript?

nik*_*iks 5 windows stdin wsh

我想执行由我的应用程序使用 Windows 脚本宿主(wscript.exe 或 cscript.exe)生成的简单 VBScript/JScript,而不生成临时脚本文件。

我没有找到从标准输入流读取脚本的命令行选项,但我确实在 WWW 中找到了几个记录 WScript 错误消息“无法从标准输入读取脚本”的地方。

MSDN Windows 脚本宿主参考 - 错误消息

那么是否有一个隐藏的命令行选项可以从标准中读取脚本?

目前我的程序生成一个小脚本并将其写入临时文件。然后它创建一个子进程 running cscript.exe,等待它完成,然后再次删除临时文件。如果可能的话,我想删除临时文件并将脚本直接传递给脚本宿主。(例如,将其cscript.exe通过管道传递给或将其作为类似于 /c 命令行选项的命令行参数的一部分传递cmd.exe

Lan*_*art 5

不幸的是,简短的回答是否定的。WScript 引擎不提供通过管道或命令参数传递脚本的方法,唯一的选择是使用StdIn来解释和处理命令(在下面对此进行扩展)


使用StdIn来解释和执行命令行代码的直接

不确定自己,但想测试一下......

值得注意的是,下面的测试仍然需要一个脚本来解释输入,这可能不符合要求,但非常通用,我不会将其归类为临时脚本。

我可以看到的问题是,您想要传递的代码越复杂,就越难通过管道传递给cscript.exe程序。

这是一个简单的例子,它只是通过管道MsgBox()调用cscript.exe.

命令行:

echo MsgBox("test piping") | cscript.exe /nologo "test.vbs"
Run Code Online (Sandbox Code Playgroud)

的内容 test.vbs

echo MsgBox("test piping") | cscript.exe /nologo "test.vbs"
Run Code Online (Sandbox Code Playgroud)

在命令行上处理多行

从管道中插入多行echo并不容易,如果您使用字符作为分隔符在传入命令后将命令分开,它可能会更好地工作。例如;

Dim stdin: Set stdin = WScript.StdIn
Dim line: line = stdin.ReadAll

Call ExecuteGlobal(line)
Run Code Online (Sandbox Code Playgroud)

然后使用

Split(stdin.ReadAll, "^")
Run Code Online (Sandbox Code Playgroud)

分解要执行的命令行。


这是一个更复杂的例子;

命令行:

echo MsgBox("test piping")^^^^Msgbox("test Complete") | cscript.exe /nologo "test.vbs"
Run Code Online (Sandbox Code Playgroud)

内容test.vbs

Split(stdin.ReadAll, "^")
Run Code Online (Sandbox Code Playgroud)

通过^用作分隔符为我自己的背部制作了一个杆,因为这在命令行中具有特殊含义并且需要转义(恰好是^),此外在通过管道传输时它必须再次转义,因此^^^^.

意识到分解行并单独执行它们可能会导致更多问题(例如Function定义会失败)。这让我重新思考了这个方法,发现它应该更简单。

echo Dim i: i = 1^^^^i = i + 2^^^^MsgBox("i = " ^^^& i) | cscript /nologo "test.vbs"
Run Code Online (Sandbox Code Playgroud)