这在Windows控制台中按预期工作:
set A="qwerty" && echo %A%
输出:"qwerty"
但是当我尝试在NPM脚本中运行相同的命令时:
package.json:
"scripts": {
"qwerty": "set A=\"qwerty\" && echo %A%"
}
> npm run qwerty
输出结果为:%A%
我是否做错了什么或者这种方式在NPM下无法正常工作?
注:Original Answer翻译成“最初的回答”。这在Windows控制台中按预期工作:
set A="qwerty" && echo %A%
输出:"qwerty"
但是当我尝试在NPM脚本中运行相同的命令时:
package.json:
"scripts": {
"qwerty": "set A=\"qwerty\" && echo %A%"
}
> npm run qwerty
输出结果为:%A%
我是否做错了什么或者这种方式在NPM下无法正常工作?
注:Original Answer翻译成“最初的回答”。你的例子 set A="qwerty" && echo %A%
是不正确的。在 cmd
提示符 / 批处理文件中,变量每行 / 命令只会扩展一次:
最初的回答
==> set "A="
==> echo %A%
%A%
==> set A="qwerty" && echo %A%
%A%
==> echo %A%
"qwerty"
在1983年3月,MS-DOS 2.0首次引入了
SET
命令。那个时候,内存和CPU非常有限,每行只能扩展一次变量就足够了。
使用CALL
命令的解决方法:
==> set "A="
==> echo %A%
%A%
==> set A="qwerty" && CALL echo %A%
"qwerty"
为了完整起见,以下批处理脚本详细展示了百分号扩展机制及其与 CALL
命令的组合(请注意批处理文件中的双倍 %
百分号标记:CALL Echo %%_var%%
):
最初的回答已被更新,请查看上方。
@ECHO OFF
SETLOCAL
if NOT "%~1"=="" ECHO ON
echo 1st:
Set "_var=first"
Set "_var=second" & Echo %_var% & CALL Echo %%_var%%
echo 2nd:
Set "_var=first"
Set "_var=second" & CALL Echo %%_var%% & Echo %_var%
Output, echo OFF
:
==> D:\bat\SO\55237418.bat
1st:
first
second
2nd:
second
first
输出,echo ON
:
==> D:\bat\SO\55237418.bat on
==> echo 1st:
1st:
==> Set "_var=first"
==> Set "_var=second" & Echo first & CALL Echo %_var%
first
second
==> echo 2nd:
2nd:
==> Set "_var=first"
==> Set "_var=second" & CALL Echo %_var% & Echo first
second
first
set A="qwerty" && echo %A%
在我的控制台上似乎是有效的,因为之前的运行实际上并没有成功,但我没有注意到这一点,只看到它在后续的运行中起作用。 - undefined"scripts": {
"aaa": "set TMP=test && npm run bbb",
"bbb": "echo %TMP%"
}
npm run aaa
输出:
test
但这个不能工作:
"scripts": {
"aaa": "set TMP=test",
"bbb": "npm run aaa && echo %TMP%"
}
npm run bbb
输出:<仅为空>
看起来需要使用两个独立的npm run
命令才能找到创建的变量:变量应该在第一个npm run
中创建,然后可以在第二个命令中找到。
set "A="
,然后再试一次,你会看到%A%
被回显出来。要在同一行或代码块中写入和读取变量,你需要使用延迟扩展,所以当使用cmd /V:ON
启动命令提示符时,执行set "A=qwerty" & echo(!A!
。另外,你也可以尝试执行set "A=qwerty" & call echo(%^A%
(虽然在某些情况下可能仍然会失败)... - undefined