So currently I’m working in a scenario where we’re deploying to servers via roles (specifically our “Web Server” role) that have a different number of servers in each environment.

We’re needing to run certain code only once for each deployment so the idea was to do something akin to the following to get it to work:

$Ids = ($OctopusParameters[“Octopus.Environment.MachinesInRole[‘Web Server’]”] - split “,”) | % { $_.Trim() }
If ($Ids[0] -eq $OctopusParameters[“Octopus.Machine.Id”]) {

Run Code


However, I cannot get the $OctopusParameters[“Octopus.Environment.MachinesInRole[‘Web Server’]”] call to return anything.

I’ve tried several variations but it always returns an empty array.

Can someone give me some guidance here? Because I’m running out of ideas.


Jonathan Hunter

Hi @Jonathan.Hunter ,

Thanks for reaching out. When you mean you want the code to only run once, do you mean once per target, or just one instance of the code running period? If you have a Run a Script step scoped to the Web Server role and then reference the machine name or ID system variable(whichever you need), it should only run once per machine.

If you mean the latter, this is the way I was able to get it working n my local repro:

$machines = $OctopusParameters["Octopus.Environment.MachinesInRole[Web Server]"] 
$machinearray = $machines.Split(",")
foreach ($machine in $machinearray){
write-highlight $machine


I ran this on a worker (it would also work on the server.)

Documentation on system variables in case you haven’t seen it: System variables - Octopus Deploy

Please let me know how it goes or if we need to dig in a bit further.


Hey Jeremy,

So hard coding it without quotes worked for me as well. That was literally the only thing I hadn’t tried yet.

I had it in a variable and it wouldn’t work. I tried single and double quotes, even double double quotes. But this works, so that’s sufficient.

The use case is that the custom step template we use would be updated to perform a specific function for each service/site being deployed across multiple servers, but we only want it to happen once regardless of how many servers are shown in the role for the environment.

Write-Host “Machine Id”
Write-Host $OctopusParameters[“Octopus.Machine.Id”]

Write-Host “MachinesInRole”
$Ids = ($OctopusParameters[“Octopus.Environment.MachinesInRole[Web Server]”] -split “,”) | % { $_.Trim() }
If ($Ids[0] -eq $OctopusParameters[“Octopus.Machine.Id”]) {
// code goes here

So the above works for what I need as long as it’s ran on a server with that role, which is fine. If I run it on a worker without the role, say I wanted to create a variable with the machine id to run on, it will result in an empty string like every other time I tried. Depending on how this is done in the background, it may just be because I was only firing this one step off and another step with the specified role did not exist at that time.

Just for posterity these are the variations I tried that all came back with an empty array/string:

$OctopusParameters[“Octopus.Environment.MachinesInRole[‘Web Server’]”]
$OctopusParameters[“Octopus.Environment.MachinesInRole[”“Web Server”"]"]
$Role = “Web Server”

The following did work when I tried it again when running on a server with the specified role:

$Role = “Web Server”

I did check the System Variables link you posted beforehand, but this is literally all the documentation on how to use it:

Lists the machines in a specified role being deployed to

Wasn’t inherently clear in how to specify the role’s name correctly which lead to a few hours of attempts, web searches, and ultimately the posting of this thread.

The description of “Lists the machines in a specified role being deployed to” also doesn’t make immediate sense as if it only works on a role being deployed to / ran on, why do I have to specify it at all? Why doesn’t this work regardless if it’s running on a machine with the identified role or not?

But like I said, the example you provided of not using any quotes got it work in the necessary scenario so my immediate issue is resolved.

Much appreciated,

Jonathan Hunter

So for curiosity’s sake, I created another step in my test project. This new step would deploy to targets in the Web Server role and the other with the above code pulling the machine ids would run on the worker.

This setup did correctly pull out the machine ids as expected. So as long as the specified role is used in the active deployment it seems to pull back the machine ids without issue.

This functionality was not necessary for my scenario, but good to know for the future and in case anyone else finds this thread.

Hi @Jonathan.Hunter,

That’s correct and by design, that variable will only be populated when the role is in use within the deployment somewhere.

I’ve passed along your feedback about our system variables needing some examples, as I do agree with you there.

Thanks for all the information and please let me know if you have any other questions or concerns.


This topic was automatically closed 31 days after the last reply. New replies are no longer allowed.