简体   繁体   English

从命令行使用带引号的参数执行Powershell脚本

[英]Executing Powershell script from command line with quoted parameters

I am automating the build of a legacy MS Access application, and in one of the steps, I am trying to make an Access executable (.ADE). 我正在自动化旧版MS Access应用程序的构建,并且在其中一个步骤中,我试图使Access可执行文件(.ADE)。 I have come up with the following code, which is stored in a file (PSLibrary.ps1): 我想出了以下代码,该代码存储在文件(PSLibrary.ps1)中:

Add-Type -AssemblyName Microsoft.Office.Interop.Access

function Access-Compile {
param (
    [Parameter(Mandatory=$TRUE,Position=1)][string]$source,
    [Parameter(Mandatory=$TRUE,Position=2)][string]$destination
)
    Write-Output "Starting MS Access"
    $access = New-Object -ComObject Access.Application
    $access.Visible = $FALSE
    $access.AutomationSecurity = 1

    if (!(Test-Path $source)) { Throw "Source '$source' not found" }
    if ((Test-Path $destination)) {
        Write-Output "File '$destination' already exists - deleting..."
        Remove-Item $destination
    }

    Write-Output "Compiling '$source' to '$destination'"
    $result = $access.SysCmd(603, $source, $destination)

    $result

    Write-Output "Exiting MS Access"
    $access.quit()
}

If I go into the PowerShell ISE and run the command below, then everything works fine, and the expected output is created: 如果我进入PowerShell ISE并运行以下命令,则一切正常,并创建了预期的输出:

PS C:>& "C:\Temp\PSLibrary.ps1"
PS C:>Access-Compile "C:\Working\Project.adp" "C:\Working\Project.ade"

However, I can't seem to generate the right hocus-pocus to get this running from the command line, as I would in an automated build. 但是,我似乎无法像在自动构建中那样,生成正确的轨迹来从命令行运行它。 For instance, 例如,

powershell.exe -command "& \"C:\\Temp\\PSLibrary.ps1\" Access-Compile \"C:\\Temp\\Project.adp\" \"C:\\Temp\\Project.ade\""

What am I doing wrong? 我究竟做错了什么?

For complex parameters, you can use Powershell's -EncodedCommand parameter. 对于复杂的参数,可以使用Powershell的-EncodedCommand参数。 It will accept a Base64 encoded string. 它将接受Base64编码的字符串。 No escaping is needed for quotes, slashes and such. 引号,斜杠等不需要转义。

Consider a test function that will print its parameters. 考虑一个将打印其参数的测试功能。 Like so, 像这样

function Test-Function {
param (
    [Parameter(Mandatory=$TRUE,Position=1)][string]$source,
    [Parameter(Mandatory=$TRUE,Position=2)][string]$destination
)
    write-host "src: $source"
    write-host "dst: $destination"
}

Create command to load the script and some parameters. 创建命令以加载脚本和一些参数。 Like so, 像这样

# Load the script and call function with some parameters
. C:\Temp\Calling-Test.ps1;  Test-Function "some\special:characters?" "`"c:\my path\with\spaces within.ext`""

After the command syntax is OK, encode it into Base64 form. 命令语法确定后,将其编码为Base64形式。 Like so, 像这样

[System.Convert]::ToBase64String([System.Text.Encoding]::UNICODE.GetBytes('. C:\Temp\Calling-Test.ps1;  Test-Function "some\special:characters?" "`"c:\my path\with\spaces within.ext`""'))

You'll get a Base64 string. 您将获得一个Base64字符串。 Like so, 像这样

LgAgAEMAOgBcAFQAZQBtAHAAXABDAGEAbABsAGkAbgBnAC0AVABlAHMAdAAuAHAAcwAxADsAIAAgAFQAZQBzAHQALQBGAHUAbgBjAHQAaQBvAG4AIAAiAHMAbwBtAGUAXABzAHAAZQBjAGkAYQBsADoAYwBoAGEAcgBhAGMAdABlAHIAcwA/ACIAIAAiAGAAIgBjADoAXABtAHkAIABwAGEAdABoAFwAdwBpAHQAaABcAHMAcABhAGMAZQBzACAAdwBpAHQAaABpAG4ALgBlAHgAdABgACIAIgA=

Finally, start Powershell and pass the encoded string as a parameter. 最后,启动Powershell并将编码后的字符串作为参数传递。 Like so, 像这样

# The parameter string here is abreviated for readability purposes.
# Don't do this in production
C:\>powershell -encodedcommand LgAgA...
Output
src: some\special:characters?
dst: "c:\my path\with\spaces within.ext"

Should you later want to reverse the Base64 encoding, pass it into decoding method. 如果您以后想要反转Base64编码,请将其传递给解码方法。 Like so, 像这样

$str = " LgAgA..."
[Text.Encoding]::Unicode.GetString([System.Convert]::FromBase64String($str))
# Output
. C:\Temp\Calling-Test.ps1;  Test-Function "some\special:characters?" "`"c:\my path\with\spaces within.ext`""

PowerShell like Bash can take single or double quotes Bash之类的PowerShell可以使用单引号或双引号

PS C:\Users\Steven> echo "hello"
hello
PS C:\Users\Steven> echo 'hello'
hello

this can alleviate some of the headache, also I think you can use the literal backslashes without escaping. 这可以减轻一些麻烦,我想您也可以在不逃脱的情况下使用文字反斜杠。

To run PowerShell, choose 要运行PowerShell,请选择

Start Menu Programs Accessories Windows Powershell Windows Powershell 开始菜单 程序 附件 Windows Powershell Windows Powershell

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM