Can *.ps1 scripts run as background jobs themselves execute *.ps1 scripts?

让人想犯罪 __ 提交于 2019-12-04 04:46:14

问题


I want to run 15 instances of a script that pipelines 5 scripts together, and so far I'm missing the pixie dust. I've boiled the problem down to a test case with a master script that calls a slave script that in turn calls a sub_slave script (no pipelines are necessary to reproduce the failure.)

If master.ps1 calls slave.ps1 each background job hangs indefinitely at the point slave.ps1 calls to sub_slave.ps1. If I comment out the call in slave.ps1 to sub_slave.ps1, master.ps1 runs to completion. And if I start slave.ps1 directly, it runs the call to sub_slave.ps1 just fine. The problem seems intractable, though if I try the double-chain. I've not seen anything in the docs saying you cannot daisy chain these scripts past some arbitrary depth, but maybe I'm not reading deeply enough?

You'll see I'm tracking progress through the script by add-content to a simple text file.

d:\jobs\master.ps1

$indexes = @(0,1,2)

$initString = "cd $pwd"
$initCmd = [scriptblock]::create($initString)

set-content -path out.txt -value "Master started"
foreach ($index in $indexes)
{
    add-content -path out.txt -value "job  starting"
    start-job -filepath slave.ps1 -InitializationScript $initCmd -ArgumentList @("master index $index originated")
}

add-content -path out.txt -value "master completed"

d:\jobs\slave.ps1

#requires -version 2.0

param (
    [parameter(Mandatory=$false)]
    [string]$message = "slave_originated"
)

begin
{
    Set-StrictMode -version Latest
    add-content -path out.txt -value "slave beginning in $pwd"
}

process
{
    add-content -path out.txt -value "slave processing $message"
    invoke-expression "D:\jobs\sub_slave.ps1 -message $message" 
}

end
{
    add-content -path out.txt -value "slave ending"
}

d:\jobs\sub_slave.ps1 #requires -version 2.0

param (
    [parameter(Mandatory=$false)]
    [string]$message = "sub_slave originated"
)

begin
{
    Set-StrictMode -version Latest

    add-content -path out.txt -value "sub_slave beginning"
}

process
{
    add-content -path out.txt -value "sub_slave processing $message"
}

end
{
    add-content -path out.txt -value "sub_slave ending"
}

When the code is run as written, without anything commented out, I get this in out.txt: d:\jobs\out.txt

Master started
job  starting
job  starting
job  starting
master completed
slave beginning in D:\jobs
slave processing master index 0 originated
slave beginning in D:\jobs
slave processing master index 1 originated
slave beginning in D:\jobs
slave processing master index 2 originated

Note that the very next command after each farewell message is the call to sub_slave.ps1 and that no message from sub_slave.ps1 appears at all. The system will hang with 3 powershell.exe processes running happily forever. Get-job reports the 3 processes are still Running and HasMoreData.

The only clue I've got is that if I crash dump the hung processes, I see:

Number of exceptions of this type:        2
Exception MethodTable: 79330e98
Exception object: 012610fc
Exception type: System.Threading.ThreadAbortException
Message: <none>
InnerException: <none>
StackTrace (generated):
<none>
StackTraceString: <none>
HResult: 80131530
-----------------

Number of exceptions of this type:        2
Exception MethodTable: 20868118
Exception object: 01870344
Exception type: System.Management.Automation.ParameterBindingException
Message: System error.
InnerException: <none>
StackTrace (generated):
<none>
StackTraceString: <none>
HResult: 80131501
-----------------

Perhaps I'm having some sort of parameter issue? If I remove all parameters from sub_slave.ps1 the behaviour is unchanged, so I kind of doubt that, but it's possible. I'm open to any idea.


回答1:


You are calling sub_slave.ps1 wrong. This:

invoke-expression "D:\jobs\sub_slave.ps1 -message $message" 

Should be this:

D:\jobs\sub_slave.ps1 -message $message

The message was getting evaluated and became multiple arguments.




回答2:


Just taking a guess here, but having multiple threads/jobs write to the same file out.txt could be causing issues.



来源:https://stackoverflow.com/questions/5186384/can-ps1-scripts-run-as-background-jobs-themselves-execute-ps1-scripts

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!