windows 将参数传递给 powershell 脚本
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/19055778/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Passing parameters to powershell script
提问by desto
I'm trying to run a powershell script from the run dialog (will be used as a scheduled task), and I'm having troubles passing parameters.
我正在尝试从运行对话框运行 powershell 脚本(将用作计划任务),但在传递参数时遇到了麻烦。
The script will take in two parameters, named title and msg.
The script is located in: D:\Tasks Scripts\Powershell\script.ps1
该脚本将接受两个参数,名为 title 和 msg。该脚本位于:D:\Tasks Scripts\Powershell\script.ps1
This is what I'm trying to do:
这就是我想要做的:
powershell.exe -noexit 'D:\Tasks Scripts\Powershell\script.ps1' -title 'Hello world' -msg 'This is a test message'
But it fails upon reading the parameters.
但是读取参数失败。
Running .\script.ps1 -title 'Hello world' -msg 'This is a test message'
on powershell works fine.
运行.\script.ps1 -title 'Hello world' -msg 'This is a test message'
在PowerShell的正常工作。
采纳答案by Nate Hekman
Use -file
before the path to your script:
-file
在脚本路径之前使用:
powershell.exe -noexit -file 'D:\Tasks Scripts\Powershell\script.ps1' etc...
回答by robert4
I usually run powershell scripts from cmd.exe because this is portable (works out-of-the-box on others' computers, like developer folks or clients): no need to worry about Set-ExecutionPolicy or associating the .ps1 extension.
我通常从 cmd.exe 运行 powershell 脚本,因为它是可移植的(在其他人的计算机上开箱即用,例如开发人员或客户端):无需担心 Set-ExecutionPolicy 或关联 .ps1 扩展名。
I create the file with .cmd extension (instead of .ps1), and copy&paste a short,
constant code to the first line(s) that invokes powershell.exe and passes the rest
of the file to it.
Passing arguments is tricky. I have multiple variants of the constant code
because the general case is painful.
我创建了带有 .cmd 扩展名(而不是 .ps1)的文件,然后将一个简短的常量代码复制并粘贴到调用 powershell.exe 并将文件的其余部分传递给它的第一行。
传递参数很棘手。我有多个常量代码的变体,因为一般情况很痛苦。
when not passing arguments, the .cmd file looks like this:
@powershell -c ".(iex('{#'+(gc '%~f0' -raw)+'}'))" & goto :eof # ...arbitrary PS code here... write-host hello, world!
This uses the -Command argument of powershell.exe. Powershell reads the .cmd file as text, puts it in a ScriptBlock with the first line commented out, and evaluates it with the '.' command. Further command line argumentscan be added to the Powershell invocation as required (e.g. -ExecutionPolicy Unrestricted, -Sta etc.)
when passing arguments that do not contain spaces or are 'single-quoted' (which is non-standard in cmd.exe), the one-liner is this:
@powershell -c ".(iex('{#'+(gc($argv0='%~f0') -raw)+'}'))" %* & goto :eof write-host this is $argv0 arguments: "[$($args -join '] [')]"
param()
declarations could be used as well,$args
is not obligatory.$argv0
is used to compensate for the missing$MyInvocation.PS*
info.
Examples:G:\>lala.cmd this is G:\lala.cmd arguments: [] G:\>lala.cmd "1 2" "3 4" this is G:\lala.cmd arguments: [1] [2] [3] [4] G:\>lala.cmd '1 2' '3 4' this is G:\lala.cmd arguments: [1 2] [3 4]
when passing arguments that are "double-quoted" but do not contain the & and ' characters, I use a two-liner to replace all " with '
@echo off& set A= %*& set B=@powershell -c "$argv0='%~f0';.(iex('{' %B%+(gc $argv0|select -skip 2|out-string)+'}'))" %A:"='%&goto :eof write-host this is $argv0 arguments: "[$($args -join '] [')]"
(Note that the space is important in the
A= %*
assignment for the argument-less case.)
Results:G:\>lala.cmd this is G:\lala.cmd arguments: [] G:\>lala.cmd "1 2" "3 4" this is G:\lala.cmd arguments: [1 2] [3 4] G:\>lala.cmd '1 2' '3 4' this is G:\lala.cmd arguments: [1 2] [3 4]
the most general case passes the arguments via environment variables thus Powershell's
param()
declaration does not work. In this case the arguments are expected to be "double-quoted" and may contain ' or & (except for the path of the .cmd file itself):;@echo off & setlocal & set A=1& set ARGV0=%~f0 ;:loop ;set /A A+=1& set ARG%A%=%1& shift& if defined ARG%A% goto :loop ;powershell -c ".(iex('{',(gc '%ARGV0%'|?{$_ -notlike ';*'}),'}'|out-string))" ;endlocal & goto :eof for ($i,$arg=1,@(); test-path -li "env:ARG$i"; $i+=1) { $arg += iex("(`${env:ARG$i}).Trim('`"')") } write-host this is $env:argv0 arguments: "[$($arg -join '] [')]" write-host arg[5] is ($arg[5]|%{if($_){$_}else{'$null'}})
(Note that in the first line
A=1&
must not contain space.)
Result:G:\>lala.cmd "a b" "c d" "e&f" 'g' "h^j" this is G:\lala.cmd arguments: [a b] [c d] [e&f] ['g'] [h^j] arg[5] is $null
不传递参数时,.cmd 文件如下所示:
@powershell -c ".(iex('{#'+(gc '%~f0' -raw)+'}'))" & goto :eof # ...arbitrary PS code here... write-host hello, world!
这使用 powershell.exe 的 -Command 参数。Powershell 将 .cmd 文件作为文本读取,将其放入 ScriptBlock 并注释掉第一行,并使用“.”对其进行评估。命令。 可以根据需要将更多命令行参数添加到 Powershell 调用中(例如 -ExecutionPolicy Unrestricted、-Sta 等)
当传递不包含空格或“单引号”(在 cmd.exe 中是非标准的)的参数时,单行是这样的:
@powershell -c ".(iex('{#'+(gc($argv0='%~f0') -raw)+'}'))" %* & goto :eof write-host this is $argv0 arguments: "[$($args -join '] [')]"
param()
声明也可以使用,$args
不是强制性的。$argv0
用于补偿丢失的$MyInvocation.PS*
信息。
例子:G:\>lala.cmd this is G:\lala.cmd arguments: [] G:\>lala.cmd "1 2" "3 4" this is G:\lala.cmd arguments: [1] [2] [3] [4] G:\>lala.cmd '1 2' '3 4' this is G:\lala.cmd arguments: [1 2] [3 4]
当传递“双引号”但不包含 & 和 ' 字符的参数时,我使用两行将所有 " 替换为 '
@echo off& set A= %*& set B=@powershell -c "$argv0='%~f0';.(iex('{' %B%+(gc $argv0|select -skip 2|out-string)+'}'))" %A:"='%&goto :eof write-host this is $argv0 arguments: "[$($args -join '] [')]"
(请注意,空格在
A= %*
无参数情况下的赋值中很重要。)
结果:G:\>lala.cmd this is G:\lala.cmd arguments: [] G:\>lala.cmd "1 2" "3 4" this is G:\lala.cmd arguments: [1 2] [3 4] G:\>lala.cmd '1 2' '3 4' this is G:\lala.cmd arguments: [1 2] [3 4]
最一般的情况是通过环境变量传递参数,因此 Powershell 的
param()
声明不起作用。在这种情况下,参数应该是“双引号”并且可能包含 ' 或 &(.cmd 文件本身的路径除外):;@echo off & setlocal & set A=1& set ARGV0=%~f0 ;:loop ;set /A A+=1& set ARG%A%=%1& shift& if defined ARG%A% goto :loop ;powershell -c ".(iex('{',(gc '%ARGV0%'|?{$_ -notlike ';*'}),'}'|out-string))" ;endlocal & goto :eof for ($i,$arg=1,@(); test-path -li "env:ARG$i"; $i+=1) { $arg += iex("(`${env:ARG$i}).Trim('`"')") } write-host this is $env:argv0 arguments: "[$($arg -join '] [')]" write-host arg[5] is ($arg[5]|%{if($_){$_}else{'$null'}})
(注意第一行
A=1&
不能包含空格。)
结果:G:\>lala.cmd "a b" "c d" "e&f" 'g' "h^j" this is G:\lala.cmd arguments: [a b] [c d] [e&f] ['g'] [h^j] arg[5] is $null