2

How can I return multiple values from a powershell script to the batch file that is calling it?

I have a powershell script that returns multiple values. I want to call it from a batch file and have each individual value go into an individual variable in the batch file.

Only been able to return one value

The powershell code (pstest.ps1):

 $p1=11
 $p2=22
 $p3=33
 exit

The batch file:

 powershell .\pstest.ps1
 :: now I'd like to get those 3 returned values 
 :: into 3 individual variables so that I can do something like this:
 @echo First is %p1%, Second is %p2%, Third is %p3%

So, it should display this:

 First is 11, Second is 22, Third is 33
cashonly
  • 119
  • 9
  • 1
    [This question might be helpful.](https://stackoverflow.com/q/34451444/5096287) Not a duplicate – spicy.dll Jun 12 '19 at 22:09
  • have you looked at setting them as user environment variables? perhaps something done with `[System.Environment]::SetEnvironmentVariable()` would work. – Lee_Dailey Jun 12 '19 at 22:34
  • 2
    @Lee_Dailey: A PowerShell script called from `cmd.exe` invariably runs in a _child process_, so it cannot set environment variables that the caller will see. – mklement0 Jun 12 '19 at 22:49
  • 2
    I may be having a senior moment, but I wasn't expecting that Powershell code to output anything. Surely your just setting values to variables, no output is expected generally in scripting languages when setting variables. – Compo Jun 12 '19 at 23:39
  • @mklement0 - i have used what i showed to have a PoSh shell set an ENV variable that was available after the PoSh script ended. the EnvVar was available in a CMD shell started after the PoSh shell exited. try this in a PoSh shell >>> `[System.Environment]::SetEnvironmentVariable('TestEnvVar', 'Value', 'user')` <<< and then open a CMD shell and type `set`. you will see the EnvVar & its value ... so it seems like it otta work. – Lee_Dailey Jun 13 '19 at 06:27
  • 1
    @Lee_Dailey: Yes, you can _persistently_ set an environment variable for _future_ `cmd.exe` sessions - but that's not the use case at hand. – mklement0 Jun 13 '19 at 11:03
  • 1
    @mklement0 - ah! i thot that created the EnvVar in the parent scope. thanks for the clarification. [*grin*] – Lee_Dailey Jun 13 '19 at 12:10

4 Answers4

2

In the exact same way you get several values from any application: one per line...

@echo off
setlocal EnableDelayedExpansion

set "i=0"
for /F "delims=" %%a in ('powershell "$p1=11; $p2=22; $p3=33; $p1; $p2; $p3"') do (
   set /A i+=1
   set "p!i!=%%a"
)

echo First is %p1%, Second is %p2%, Third is %p3%

I suggest you to read this answer about arrays...

Aacini
  • 65,180
  • 12
  • 72
  • 108
1

For a more flexible solution using delayed expansion that doesn't require making the PowerShell script output all values on a single line and works with a variable number of outputs, see Aacini's helpful answer.


Assuming that the number of values is fixed and known in advance:

  • Make the PowerShell script output a single line containing all the values with a known separator.

  • In the batch file, use for /f "delims=... tokens=..." to capture the values in discrete loop variables, which you can assign to regular variables.

A simplified example that uses a PowerShell command to produce a single-line output with 3 values separated by | (to apply this to your scenario, use -File with your *.ps1 file instead of -c (-Command) with a command string):

@echo off

for /f "delims=| tokens=1,2,3" %%a in ('powershell -c " '11|22|33' "') do set "p1=%%a" & set "p2=%%b" & set "p3=%%c"

:: echo the values of the newly created variables
echo p1: [%p1%]
echo p2: [%p2%]
echo p3: [%p3%]

The above yields:

p1: [11]
p2: [22]
p3: [33]
mklement0
  • 382,024
  • 64
  • 607
  • 775
0

Apart from using environment variables, you could try something like this base on SachaDee's answer here:

PS:

function get-multiplereturnvalues {
  "11"
  "22"
  "33"
}
get-multiplereturnvalues

BATCH/CMD

@echo First is %p1%, Second is %p2%, Third is %p3%
for /f "delims=" %%a in ('powershell .\multi.ps1') do @echo "$Value=%%a"

Which outputs:

"$Value=11"
"$Value=22"
"$Value=33"
wp78de
  • 18,207
  • 7
  • 43
  • 71
  • 1
    The request is _"and have each individual value go into an individual variable in the batch file"_, not just _show_ the values... – Aacini Jun 13 '19 at 16:27
0

Within the PowerShell script I‘d create a temp file with the results. Within the batch file, after calling the PowerShell script, I‘d parse that temp file with FOR /F in order to get the results and set environment variables as required.

fpschultze
  • 153
  • 6