Hi All, this is my first post and i’m a hack, so please be gentle.
I’ve created a bunch of runspaces manually each with their own variable names etc,
I’d like to make a template script or function to tidy up my code
I assume this would require the use of New-Variable to dynamically generate the variable names,
but I cant work out then how to access the runspace properties assigned to that dynamic variable
Help please
I’ve included working and test code below:
##
#example of working code to create a runspace and run script in new runspace
##
#Create a synchronised hashtable to share variables between runspaces if required
If($sync.count -lt 1){$sync = [hashtable]::Synchronized(@{})}
$myScriptMyRunspace =[runspacefactory]::CreateRunspace()
$myScriptMyRunspace.ApartmentState = "STA"
$myScriptMyRunspace.ThreadOptions = "ReuseThread"
$myScriptMyRunspace.name = "myScriptMyRunspace"
$myScriptMyRunspace.Open()
$myScriptMyRunspace.SessionStateProxy.SetVariable("sync",$sync)
$myScriptCmd = [PowerShell]::Create().AddScript({
#some code here
})
#run script in new runspace
$myScriptCmd.Runspace = $myScriptMyRunspace
$myScriptGUI = $myScriptCmd.BeginInvoke(),"Background"
######################################################################################
##
#Attempting to do this same thing with dynamic naming of the variables, to create a function for creating runspaces
##
$shortName = "myScript"
$runspaceName = $shortName + "MyRunspace"
$scriptCmd = $shortName + "Cmd"
$scriptGUI = $shortName + "GUI"
#create dynamic variable names and assign to runspace
New-Variable $runspaceName -Force
New-Variable $scriptCmd -Force
New-Variable $scriptGUI -Force
#Create Runspace
Set-Variable $runspaceName -Value ([runspacefactory]::CreateRunspace())
(Set-Variable $runspaceName).ApartmentState = "STA"
(Set-Variable $runspaceName).ThreadOptions = "ReuseThread"
(Set-Variable $runspaceName).name = "myScriptMyRunspace"
(Set-Variable $runspaceName).Open()
(Set-Variable $runspaceName).SessionStateProxy.SetVariable("sync",$sync)
Set-Variable $scriptCmd -Value ([PowerShell]::Create().AddScript({
#some code here
})
)
#run script in new runspace
(Set-Variable $ScriptCmd).Runspace = (Get-Variable $runspaceName)
Set-Variable $scriptGUI -Value ($ScriptCmd.BeginInvoke(),"Background")
You need to provide a string to New-Variable, not a variable, so remove the dollar sign. Here’s an example of how to create, capture, and manipulate dynamic variables.
# Create variables, capturing them in another variable to easily reference
$variables = 1..6 | foreach {
New-Variable -Name UniqueName$_ -Value @{Number=$_;Date=Get-Date;Script="Write-Host $_ -foreground cyan"} -PassThru
}
# Use the variables
$variables | foreach {
"This variable is named {0} and its number is {1}" -f $_.name,$_.value.number
}
# Use one like a normal variable
$UniqueName1
# Get the variables if not already captured
$variables = 1..6 | foreach {Get-Variable -Name UniqueName$_}
# Get all the values of the variables
1..6 | foreach {Get-Variable -Name UniqueName$_ -ValueOnly}
# Use the properties
$variables.value | foreach {& $([scriptblock]::create($_.script))}
# Remove the variables
$variables | Remove-Variable
# or
1..6 | foreach {
Remove-Variable -Name "UniqueName$_"
}
Hope it helps
Hi Doug, Thanks for replying
I need to access the dynamically generated variable name directly rather than through an assigned variable name as you’ve done ($variable),
This code let’s me do that, but how to I edit one of the properties, such as set “ThreadOptions = “ReuseThread””, or change the Runspace Name?
thanks
james
#name of runspace set manually or obtained from code
$shortName = "activeUsers"
New-Variable -Name runspace$shortName -PassThru -Force -Value ([runspacefactory]::CreateRunspace())
(Get-Variable -Name runspace$shortName -ValueOnly)
###########################
console output
Name Value
---- -----
runspaceactiveUsers System.Management.Automation.Runspaces.LocalRunspace
Events :
ThreadOptions : Default
JobManager :
Debugger :
RunspaceConfiguration : System.Management.Automation.Runspaces.RunspaceConfigForSingleShell
InitialSessionState :
Version : 5.1.18362.752
RunspaceStateInfo : BeforeOpen
RunspaceAvailability : None
ConnectionInfo :
OriginalConnectionInfo :
LanguageMode :
ApartmentState : Unknown
RunspaceIsRemote : False
InstanceId : 8a205646-e78d-4dc0-8318-f2e1691811ac
DisconnectedOn :
ExpiresOn :
Name : Runspace44
Id : 44
SessionStateProxy : System.Management.Automation.Runspaces.SessionStateProxy
Ahhh, I worked it out
#name of runspace set manually or obtained from code
$shortName = "activeUsers1"
$runspaceName = $shortName + "CPRunspace"
New-Variable -Name $runspaceName -PassThru -Force -Value ([runspacefactory]::CreateRunspace())
(Get-Variable -Name $runspaceName -ValueOnly).ThreadOptions = "ReuseThread"
(Get-Variable -Name $runspaceName -ValueOnly).Name = "$runspaceName"
(Get-Variable -Name $runspaceName -ValueOnly).open()
I see your variable turned into a string,
my mistake.
It seems the ideas have helped nonetheless.
Glad you got it working!
thanks mate, much appreciated