junton
junton

Reputation: 43

Script to reboot multiple Macs over a network in AppleScript or PowerShell?

I'm trying to write a script to reboot Macs in a range of IP addresses. Doing it through PowerShell works, but the process waits until each machine reboots before it moves on to the next machine. I'm finding ssh'ing into each machine and rebooting it using sudo shutdown -S shutdown -r now is faster...it's just manual. Here's what I have so far in PowerShell:

$serverRoot = "xxx.xxx.xxx."
$startVal = 100
$stopVal = 150

for ($i=$startVal; $i -le $stopVal; $i++)
{
    $User="username"
    $Password="password"

    $SecurePass=ConvertTo-SecureString -string $Password -AsPlainText -Force

    $Credential = New-Object System.Management.Automation.PSCredential $User, $SecurePass

    $session = New-SSHSession -ComputerName ($serverRoot + $i) -Credential $Credential  -AcceptKey
    Invoke-SSHCommand -SSHSession $session -Command "echo $Password | sudo -S shutdown -r now"   
    Remove-SSHSession -SSHSession $session -Verbose

}

Is there something I can add which will just kick the reboot process off on all the machines at once? Should I use AppleScript?

Upvotes: 4

Views: 378

Answers (3)

Erti-Chris Eelmaa
Erti-Chris Eelmaa

Reputation: 26268

If you wrap it to workflow, you can kick it as parallel:

workflow Kill-All {
  param([string[]]$computers)

  foreach -parallel ($computer in $computers) {
      InlineScript {
         # Your powershell stuff.
      }
  }
}

Kill-All -Computers "132.134.123.1", "123.4.53.12"

Alternatively, you can put your stuff to bat file, and use powershell to invoke the bat file. This way you can invoke the bat files without waiting one to finish, before proceeding to the next one.

The best way, as answered by rae1, is to just invoke New-SSHSession directly, as it supports parallelization by default.

Here is a one liner:

$sessions  = New-SSHSession -ComputerName (1..254 | %{ "xxx.xxx.xxx.$_"})

More information: http://blogs.technet.com/b/heyscriptingguy/archive/2012/11/20/use-powershell-workflow-to-ping-computers-in-parallel.aspx

http://community.spiceworks.com/topic/341776-call-a-ps-script-from-another-and-don-t-wait-for-it-to-finish

Upvotes: 3

rae1
rae1

Reputation: 6144

Actually, the -ComputerName param for New-SSHSession can take a collection of servers, and will invoke the command in parallel for all servers by default,

$serverRoot = "xxx.xxx.xxx."
$startVal = 100
$stopVal = 150

# First start with creating a collection
$servers = @()
for ($i = $startVal; $i -le $stopVal; $i++)
{
    $servers += ($serverRoot + $i)
}

# Then, pass the $servers variable directly when creating the session
$session = New-SSHSession -ComputerName $servers -Credential $credential -AcceptKey

And voilá!

Upvotes: 3

Mark Setchell
Mark Setchell

Reputation: 207455

You could use plink.exe along these lines (untested):

plink [email protected] secret "shutdown -S shutdown -r now" &
plink [email protected] secret "shutdown -S shutdown -r now" &
plink [email protected] secret "shutdown -S shutdown -r now" &
plink [email protected] secret "shutdown -S shutdown -r now" &

Or like this

for %%a in (...) do plink root@%%a -pw secret "shutdown -S shutdown -r now" &

Upvotes: 0

Related Questions