How to passing external argument by call other powershell script? - powershell

I want to call another powershell script with external argument. I try this but return error. anyone can help please
$direct = "D:\Learn"
Start-Process powershell.exe -WindowStyle Minimized ".\Testing.exe" -Path $direct
Testing.exe
Param(
[parameter(mandatory=$true)][string]$Loc
)
Get-Content $Loc\API.txt
Pause

The Start-Process cmdlet has a -AgumentList parameter:
$direct = "D:\Learn"
Start-Process powershell.exe -WindowStyle Minimized ".\Testing.exe" -ArgumentList "-Path $direct"

If you want to just run a File with some arguments
$filepath = ".\Testing.exe"
$direct = "D:\Learn"
Start-Process -FilePath $filepath -ArgumentList $direct -Wait -NoNewWindow

I think they all were arguments of powershell.exe.
The whole argument can be wrapped in one double quote in argumentlist.
Start-Process "powershell.exe" -ArgumentList "-windowstyle minimized '.\testing.exe' -path $direct"
Or even it can be done without start-process:
& "powershell.exe -windowstyle minimized '.\testing.exe' -path $direct"

Related

How to add variables in a call to Start-Process

I'm building a PowerShell script to run the following command on various servers:
arapx acc, Export ExportFile=\"C:\\Temp\\DEV_Refresh\\AccExport.txt\"
This code works:
Start-Process -FilePath '\\<fileserver>\Bin\arapx' -argumentList 'acc, Export ExportFile=\"C:\\Temp\\DEV_Refresh\\AccExport.txt\"'
Different servers have different paths for the output file so I tried to set a variable. But this fails:
$Dest_Folder="DEV_Refresh"
Start-Process -FilePath '\\<fileserver>\Bin\arapx' -argumentList 'acc, Export ExportFile=\"C:\\Temp\\${Dest_Folder}\\AccExport.txt\"'
This fails:
$Dest_Folder="DEV_Refresh"
Start-Process -FilePath '\\<fileserver>\Bin\arapx' -argumentList 'acc, Export ExportFile=\"C:\\Temp\\$(Dest_Folder)\\AccExport.txt\"'
And this fails:
$Dest_Folder="DEV_Refresh"
$argumentList = "'acc, Export ExportFile=\""C:\\Temp\\" + $Dest_Folder + "\\AccExport.txt\""'"
Start-Process -FilePath '\\<fileserver>\Bin\arapx' -argumentList $argumentList
Can anyone help me get the command to work with a varable?
The solution from zett42 works:
$Dest_Folder="DEV_Refresh"
Start-Process -FilePath '\\<fileserver>\Bin\arapx' -argumentList ('acc, Export ExportFile=\"C:\\Temp\\' + $Dest_Folder + '\\AccExport.txt\"')

powershell start-process doesn't accept two commands in ArgumentList because they have a same parameter

I want to launch a admin powershell with two commands :
$command1 = "Set-ItemProperty -Path 'HKLM:\SYSTEM\CurrentControlSet\Services\Tcpip\Parameters\Interfaces\{example}' -Name DHCPClassId -Value National"
$command2 = "Restart-NetAdapter -Name Ethernet"
Start-Process powershell -Verb 'RunAs' -ArgumentList "-NoExit","-Command &{$command1,$command2}"
And i have an error : he don't want to execute these two because they have a same parameter (-Name), so, what can i do ?
PowerShell's statement separator is ;, not , (the latter constructs arrays).
Also:
Even though passing arguments individually, as elements of an array to Start-Process is conceptually clean, it should be avoided due to a long-standing bug: pass a single string encoding all arguments to -ArgumentList - see this answer for more information.
When using PowerShell's CLI, -Command & { ... } is never necessary - just use -Command ...; that is, there is no reason to construct a script block ({ ... }) that you must then invoke with & - all commands given are directly executed by default.
To put it all together:
$command1 = "Set-ItemProperty -Path 'HKLM:\SYSTEM\CurrentControlSet\Services\Tcpip\Parameters\Interfaces\{example}' -Name DHCPClassId -Value National"
$command2 = "Restart-NetAdapter -Name Ethernet"
Start-Process powershell -Verb RunAs "-NoExit -Command $command1; $command2"

How to pass arguments to MSI file with PowerShell

I've read that you can pass arguments to a .msi file, but I have no idea how to do it correctly. I've tried the following, where $ArgumentList is an array.
$ArgumentList = #("/i .\NSClient v67.msi", "/norestart", "/quiet", "/l*v '$directory'", "token=$token", "host=$_host", "mode=$mode")
Start-Process "msiexec" -ArgumentList $ArgumentList -Wait -NoNewWindow
This is part of my script, where I'm trying to install NetSkope on my machine by executing a command.
In theory, the command should look like msiexec /i "NSClient v67.msi" token=loremipsum host=bryan.goskope.com mode=peruserconfig /norestart /quiet /l*v "C:\Temp\NetskopeInstallation.log.
#Find file path
$rawPath = Invoke-Expression -Command 'C:\Windows\System32\WHERE /r C:\Users\ /f NSClient*.msi'
#Extract the directory
$filePath = Invoke-Expression -Command "cmd.exe --% /c FOR /f ""tokens=1"" %A IN ($rawPath) DO (ECHO
'%~dpA')"
#Cast $filePath to work with string methods
$filePath = Out-String -InputObject $filePath
$filePath = $filePath.split("'")[1]
Invoke-Expression -Command "cmd.exe --% /c cd $filePath"
$ArgumentList = #("/i .\NSClient v67.msi", "/norestart", "/quiet", "/l*v '$directory'",
"token=$token", "host=$_host", "mode=$mode")
Start-Process "msiexec" -ArgumentList $ArgumentList -Wait -NoNewWindow
I would also recommend using the Powershell MSI Module
Concerning Start-Process:
-Argumentlist expects string as a type. I don't think you can just pass an array.
You also need to surround the parameters that require a space with escaped double quotes. The escape character is powershell is the grave-accent(`).
Another problem is that the variable $directory will never be expanded, because it is surrounded with single quotes. You need to remove those.
The following should work for your example, but I personally would just remove the space in the file name, since you don't need to do weird stuff with escaping.
Without escaping:
$ArgumentList = "/i .\NSClientv67.msi /norestart /quiet /l*v $directory token=$token host=$_host mode=$mode"
With escaping:
$ArgumentList = "/i `".\NSClient v67.msi`" /norestart /quiet /l*v $directory token=$token host=$_host mode=$mode"
Here's a slightly different syntax:
$MSIArguments = #(
"/x"
"`"C:\path with spaces\test.msi`""
"/qb"
"/norestart"
"/l*v"
"`"C:\path with spaces\test.log`""
)
Start-Process "msiexec.exe" -ArgumentList $MSIArguments -Wait -NoNewWindow

Start-Process not running

I have been trying to re-write the following PowerShell code as I need it to wait until completion before carrying on so assumed Start-Process with -Wait would be sufficient however I can't seem to get it to actually run...
Original code which works, but won't wait until it's finished before carrying on with the script.
function ZipAndDeleteFile([string] $file, [string] $saveLocation)
{
$command = [string]::Format("`"{0}`" a -ep -df `"$saveLocation`" `"$file`"", $winrarPath);
iex "& $command";
}
My attempt at re-writing which isn't running as expected, does nothing so far...
function ZipAndDeleteFile([string] $file, [string] $saveLocation)
{
Start-Process -FilePath $winrarPath -ArgumentList "a -ep -df $saveLocation $file" -Wait
}
Fixed with the following... knew it was something silly.
Start-Process -FilePath $winrarPath -ArgumentList "a -ep -df `"$saveLocation`" `"$file`"" -Wait

In Powershell how can I pass an array as an argument, which is one of multiple arguments to Start-Process -ArgumentList

ScriptToInvoke.ps1:
[CmdletBinding()]
param (
[Parameter(Mandatory=$True)]
[string[]]$StringArray,
[ValidateSet('Mode1', 'Mode2', 'Mode3')]
[string]$Mode = 'Mode1'
)
$count = $StringArray.Count
Write-Verbose ("String array count ($count): $StringArray")
ScriptCallingStartProcess.ps1:
$stringArray = #('String1','String2','String3')
Start-Process powershell -Verb RunAs
-ArgumentList "-NoExit -File ScriptToInvoke.ps1 -StringArray ""$stringArray"" -Mode Mode3 -Verbose"
In this case the $stringArray is treated as an array containing one element:
screen capture of script run output
I have tried multiple variations passing the $stringArray argument:
-StringArray $stringArray
-StringArray #($stringArray)
-StringArray #(,#($stringArray))
each with the same error:
A positional parameter cannot be found that accepts argument 'String2'
As I understand it the double quotes around the ArgumentList value result in any variable being parsed. Is it possible to prevent this from happening? Or is there an alternative approach?
My use case involves attempting to re-run the Powershell script with elevated permissions to uninstall a Windows update, which is why I use Start-Process with -Verb RunAs.
Here's one way. ScriptCallingStartProcess.ps1:
$stringArray = #('String1','String2','String3')
$OFS=","
Start-Process powershell.exe -Verb Runas "-NoExit -File \ScriptToInvoke.ps1 $stringArray -Mode Mode3 -Verbose"
ScriptToInvoke.ps1:
[CmdletBinding()]
param (
[Parameter(Mandatory=$True)]
[String] $InputData,
[ValidateSet('Mode1', 'Mode2', 'Mode3')]
[string]$Mode = 'Mode1'
)
$StringArray = $InputData -split ','
$count = $StringArray.Count
Write-Verbose ("String array count ($count): $StringArray")
(that is, pass a comma-delimited string as first parameter, then split inside second script)
I escaped the double quotes, and it seems to work ok:
Start-Process powershell -Verb RunAs -ArgumentList "-NoExit -File test.ps1 -StringArray `"$stringArray`" -Mode Mode3 -Verbose"