What is this?

This knowledgebase contains questions and answers about PRTG Network Monitor and network monitoring in general.

Learn more

PRTG Network Monitor

Intuitive to Use. Easy to manage.
More than 500,000 users rely on Paessler PRTG every day. Find out how you can reduce cost, increase QoS and ease planning, as well.

Free Download

Top Tags


View all Tags

Using PowerShell For SSH Script Execution

Votes:

1

Introduction

The following script allows you to execute SSH script using an EXE/Script sensor. It will connect to the server, execute the given command and simply return the output to the sensor. That given, it can be used for either EXE/Script, EXE/Script (Advanced) or a EXE notification.

Please have a look at our guide for installing PowerShell based sensors for installation details.

Requirements

  1. Configured Windows credentials in the given host
  2. Configured Linux credentials in the given host
  3. Security context of the sensor is set to Use Windows credentials of parent device

Parameters

ParameterDescription
ComputerNameThe Linux host you want to connect to (can be set to %host)
UsernameThe Linux user you want to use (can be set to %linuxuser)
PasswordThe password of the above user (can be set to %linuxpassword)
KeyFilePathThe path of the keyfile, if you want to use key based authenticaion
CommandThe command you want to execute, including parameters
AutoUpdateFingerPrintSet this when calling the script to automatically update the SSH fingerprints of known devices. Careful, though!

Version History

DateVersionNotes
December 29th, 20161.1Bugfix for new Posh-SSH, where the session is stored differently
AutoUpdateFingerprint works correctly now
Posh-SSH is now installed automatically if not installed already
August 5th, 20151.0Initial Release

Script

# ___ ___ _____ ___
#| _ \ _ \_   _/ __|
#|  _/   / | || (_ |
#|_| |_|_\ |_| \___|
#    NETWORK MONITOR
#-------------------
# Description: This sensor will use Posh-SSH to connect to the server
# Parameters:
# -Computername:    The linux host you want to connect to
# -Username         Your linux username
# -Password         Your linux password
# -Command          The command to execute on your host,
# -AutoUpdateFingerPrint   Set this to when calling the script to automatically update the SSH fingerprints of known devices. 
# Careful, though!
#
##########
#
# Version History
# ----------------------------
# Version Date        Description 
# 1.1     29/12/2016  [Fixed]    Updated session handling
#                     [Improved] Posh-SSH is now automatically installed 
#                     [Fixed]    AutoUpdateFingerPrint works correctly now  
# 1.0     05/2015  Initial Release 
#
# (c) 2015 Stephan Linke | Paessler AG
 
# Parameters
param(  
    $Computername = "",
    $Username = "",
    $Password = "",
    $Port = 22,
    $KeyfilePath = "",
    $Command = "echo '0:Hello World'",
    $AutoUpdateFingerprint = $False
)
 
# Check if our module loaded properly
if (Get-Module -ListAvailable -Name Posh-SSH) { <# do nothing #> }
else { 
    # install the module automatically
    iex (New-Object Net.WebClient).DownloadString("https://gist.github.com/darkoperator/6152630/raw/c67de4f7cd780ba367cccbc2593f38d18ce6df89/instposhsshdev")
 }
 
function This-FingerPrintUpdate(){
    if($AutoUpdateFingerprint)
    { Remove-SSHTrustedHost $Computername }
}
 
# Includes
Import-Module Posh-SSH
 
 
function This-GetSSHCommandOutput(){
	# Create new session and execute the command given
    if($keyfilePath.Length -eq 0){
 
        # Generate credentials object for authentication
	 $nopasswd = New-Object System.Security.SecureString
        $Credential = New-Object System.Management.Automation.PSCredential ($Username, $nopasswd)	
        $Session = New-SSHSession -Computername $Computername -Credential $Credential -Acceptkey -KeyFile $keyfilePath -Port $Port

    }
    else
    { $Session = New-SSHSession -Computername $Computername -Acceptkey $true -KeyFile $keyfilePath -Port $Port }
	
    # Store the output of the command 
    $Output = (Invoke-SSHCommand -SSHSession $Session -Command $Command).Output
	
    # Remove the session after we're done
    Remove-SSHSession -Name $Session | Out-Null 
	
    # return the actual output
    Write-Host $Output.Trim();
 
}

# Automatically update the fingerprint for the given host. 
This-FingerPrintUpdate;

# echo the output to PRTG 
This-GetSSHCommandOutput;

Notes

The %linuxuser and %linuxpassword placeholders can't be used for notifications, you'll need to use a keyfile for authentication. Otherwise, you'll have to use clear text passwords within the parameters of the notification, which is not safe of course :)

The script is provided as is and may or may not work with your installation. If you need any further customizations for your environment, feel free to implement them. If you encounter any bugs, feel free to share them :)

powershell ssh ssh-script ssh-script-advanced-sensor

Created on Oct 26, 2016 1:26:40 PM by  Stephan Linke [Paessler Support]

Last change on Oct 16, 2019 11:17:04 AM by  Stephan Linke [Paessler Support]



9 Replies

Votes:

0

Hi,

i'm using something similar to this script but i encounter a strange behaviour. New-SSHSession throws me that "the registry key access is not allowed" when there is no real session openned on the probe server. I guess script tries to read the trusted hosts, which are stored as well in the current user branch and also in the user's SSID one. But i don't really understand why this is going like this...

Any idea maybe?

Thanks, Nicolas

Created on Jan 11, 2017 9:35:02 AM



Votes:

0

Probably the user executing the script doesn't have sufficient permissions? Or does it happen when you execute it in the PowerShell ISE as well?

Created on Jan 11, 2017 9:39:04 AM by  Stephan Linke [Paessler Support]



Votes:

0

The user has enough permissions. I use it in the PS ISE console without any problems. This is also the same user set within prtg sensor. Sensor is working fine, i mean PRTG executes the script correctly, collects data from its execution, but as soon as i log out the user from the probe, the sensor falls down with such error...

I'm used to execute powershell scripts with PRTG, setting envirronement variables when needed, but this time it's quite different. Import module works properly, but the New-SSHSession call fails as i described before.

Created on Jan 11, 2017 1:25:49 PM



Votes:

0

Could you post the complete script? Maybe I find something...

Created on Jan 11, 2017 2:16:06 PM by  Stephan Linke [Paessler Support]



Votes:

0

#Import mandatory module
$env:PSModulePath = $env:PSModulePath + ";C:\Program Files (x86)\WindowsPowerShell\Modules"
Push-Location
Import-Module Posh-SSH

#Initialize variables
$username = "root"
$password = cat "C:\Program Files (x86)\PRTG Network Monitor\Tools\credentials\rootesx.txt" | convertto-securestring
$cred = new-object -typename System.Management.Automation.PSCredential -argumentlist $username, $password
$cacheName = $args[0]
$esx = $args[1]

#Create temporary console
ping localhost -n 1 | Out-Null
[Console]::OutputEncoding = [System.Text.Encoding]::UTF8
$output=""

#Open ssh session to target esx using credentials
$sshcnx = New-SSHSession -ComputerName $esx -Credential $cred

#send commands through ssh pipeline
#first: get list of vflash caches
$stats = Invoke-SSHCommand -Index $sshcnx.SessionId -Command "esxcli storage vflash cache stats get -c '$cacheName'"

#shutdown session
$sshEnd = Remove-SSHSession -Index $sshcnx.SessionId

#Manage result to figure it out in PRTG
$tabChannels = $stats.Output.split("`n")

#Format output for PRTG
$output+="<?xml version=`"1.0`" encoding=`"UTF-8`" ?>"
$output+="<prtg>"

$output+="<Result>"
$output+="<Channel>Cache Hit Rate</Channel>"
$output+="<Unit>Percent</Unit>"
$output+="<Value>$($tabChannels[1].substring(43))</Value>"
$output+="</Result>"

$output+="<Result>"
$output+="<Channel>Mean IOPS</Channel>"
$output+="<Unit>Custom</Unit>"
$output+="<CustomUnit>#</CustomUnit>"
$output+="<Value>$($tabChannels[6].substring(20))</Value>"
$output+="</Result>"

$output+="<Result>"
$output+="<Channel>Max observed IOPS</Channel>"
$output+="<Unit>Custom</Unit>"
$output+="<CustomUnit>#</CustomUnit>"
$output+="<Value>$($tabChannels[7].substring(28))</Value>"
$output+="</Result>"

$output+="<Result>"
$output+="<Channel>Cache usage rate</Channel>"
$output+="<Unit>Percent</Unit>"
$output+="<Value>$($tabChannels[16].substring(39))</Value>"
$output+="</Result>"

$ssdFailedIOS = [int]$tabChannels[17].substring(26)
$output+="<Result>"
$output+="<Channel>Total failed SSD I/Os</Channel>"
$output+="<Unit>Custom</Unit>"
$output+="<CustomUnit>#</CustomUnit>"
$output+="<Value>$($ssdFailedIOS)</Value>"
$output+="<Mode>Difference</Mode>"
$output+="</Result>"

$diskFailedIOS = [int]$tabChannels[18].substring(27)
$output+="<Result>"
$output+="<Channel>Total failed disk I/Os</Channel>"
$output+="<Unit>Custom</Unit>"
$output+="<CustomUnit>#</CustomUnit>"
$output+="<Value>$($diskFailedIOS)</Value>"
$output+="<Mode>Difference</Mode>"
$output+="</Result>"

$output+="</prtg>"

[Console]::WriteLine($output)

Pop-Location

Created on Jan 11, 2017 2:50:32 PM

Last change on Jan 12, 2017 8:14:41 AM by  Stephan Linke [Paessler Support]



Votes:

0

I think you would be better of with using a keyfile instead. Did you try that already? If you still want to go the username/password way, use this approach:

param(
    [string] $sshUser = "root",
    ## For the initial password setup, call it with -SetupPasswords
    [switch] $SetupPasswords = $false
)

## store the passwords
function Passwords([ValidateSet("Get","Set")][string]$action){

       $passFile = "C:\Program Files (x86)\PRTG Network Monitor\Custom Sensors\EXEXML\SSH.pass";
       $keyFile  = "C:\Program Files (x86)\PRTG Network Monitor\Custom Sensors\EXEXML\SSH.key";

    }
    if($action -eq "set"){
        $Key = New-Object Byte[] 32
        [Security.Cryptography.RNGCryptoServiceProvider]::Create().GetBytes($Key)
        $Key | out-file $keyFile
        Read-Host "Enter Password for the target server" -AsSecureString |  ConvertFrom-SecureString -key $Key | Out-File $passFile
    }
    if($action -eq "get"){
       $Key = Get-Content $KeyFile
       $Credentials = New-Object -TypeName System.Management.Automation.PSCredential -ArgumentList $sshUser, (Get-Content $passFile | ConvertTo-SecureString -Key $key)
       return $Credentials;
    }
}

# Get credentials
$Credentials = (Passwords -Action Get)

Using it like this makes sure that the password gets encrypted with an independent key, rather than the key stored within your windows account. However, as mentioned, a keyfile would be the easiest approach here.

Created on Jan 12, 2017 8:27:41 AM by  Stephan Linke [Paessler Support]

Last change on Jan 12, 2017 8:27:53 AM by  Stephan Linke [Paessler Support]



Votes:

0

It looks like there is a new Posh-SSH version: I fixed the login with KeyFile. The credential parameter is mandatory now. And the "-Acceptkey" is a flag and needs no value anymore.

        $nopasswd = New-Object System.Security.SecureString
        $Credential = New-Object System.Management.Automation.PSCredential ($Username, $nopasswd)	
        $Session = New-SSHSession -Computername $Computername -Credential $Credential -Acceptkey -KeyFile $keyfilePath -Port $Port 

Created on Oct 14, 2019 10:41:37 AM



Votes:

0

Thanks for the update on this one. I updated the script accordingly :)

Created on Oct 16, 2019 11:17:26 AM by  Stephan Linke [Paessler Support]



Votes:

0

If you are using Windows Server 2019, you can install Posh-SSH like this:

Install-Module PowershellGet -Force
Install-Module -Name Posh-SSH -AllowPrerelease

Created on Aug 26, 2020 6:14:54 AM by  Timo Dambach [Paessler Support]




Disclaimer: The information in the Paessler Knowledge Base comes without warranty of any kind. Use at your own risk. Before applying any instructions please exercise proper system administrator housekeeping. You must make sure that a proper backup of all your data is available.