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

Customer Powershell Script Returns no response

Votes:

0

Hello,

I have the following script which returns me the values I want when I run it manually on the server from ad administrative PS shell.

$manufacturer = Get-WmiObject Win32_Computersystem | select manufacturer
$manufacturer = $manufacturer.manufacturer
$model = Get-WmiObject Win32_Computersystem | select model
$model = $model.model
$OS = Get-WmiObject Win32_OperatingSystem | select caption
$OS = $OS.caption
$age = Get-WmiObject Win32_OperatingSystem | select InstallDate
$age = $age.Installdate

$hostname = $env:computername
$drives = get-psdrive -psprovider 'FileSystem' | select root
$drives = $drives.root

ForEach ($drive in $drives) 
    {$path = $drive + "XYZ\ZYX\Plugins\startup_plugin.xml"
     if (test-path $path)
     {$startup = $path}
    }

[xml]$XmlDocument = Get-Content  $startup 
$databases = $xmldocument.BVSManager.StartupData.DBEntries.Database | where { $_.Server -eq $hostname} 
$databases = $databases.Path
$DB1Name = (get-item $databases[0]).FullName
$DB2Name = (get-item $databases[1]).FullName
$DB1Size = (get-item $databases[0]).Length
$DB2Size = (get-item $databases[1]).Length


write-host "<prtg>"
write-host "<result>"
write-host "<channel>Make</channel>"
write-host "<value>"
write-host $manufacturer
write-host "</value>"
write-host "</result>"
write-host "<result>"
write-host "<channel>Model</channel>"
write-host "<value>"
write-host $model
write-host "</value>"
write-host "</result>"
write-host "<result>"
write-host "<channel>OS Version</channel>"
write-host "<value>"
write-host $OS
write-host "</value>"
write-host "</result>"
write-host "<result>"
write-host "<channel>Build Date</channel>"
write-host "<value>"
write-host $age
write-host "</value>"
write-host "</result>"
write-host "<result>"
write-host "<channel>DB1</channel>"
write-host "<value>"
write-host $DB1Name
write-host "</value>"
write-host "</result>"
write-host "<result>"
write-host "<channel>DB2</channel>"
write-host "<value>"
write-host $DB2Name
write-host "</value>"
write-host "</result>"
write-host "<result>"
write-host "<channel>DB1 Size</channel>"
write-host "<value>"
write-host $DB1Size
write-host "</value>"
write-host "<result>"
write-host "<channel>DB2 Size</channel>"
write-host "<value>"
write-host $DB2Size
write-host "</value>"
write-host "</result>"
write-host "</result>"
write-host "</prtg>"

However, when I add this custom sensor, what I get as a response is simply "0 #" . What is tehe problem? If the problem is not having administrative PS shell, how can I make this happen?

custom-script-exe powershell xml

Created on May 11, 2016 6:39:21 PM

Last change on May 18, 2017 11:07:30 AM by  Luciano Lingnau [Paessler]



Best Answer

Accepted Answer

Votes:

0

You're absolutely correct:

PRTG will always run any script locally on the Probe that monitors the said device/sensor. This is desirable in some cases and to run the script on a remote system you need to use some sort of remoting, for instance powershell offers:

Invoke-Command -ComputerName $host [...]

Within PRTG you can pass the %host parameter to the custom-script sensor to use it within the script later. The same applies to the other parameters (%windowsdomain, %windowsuser, %windowspassword, ...)

Please note that the remote system must also be configured to accept powershell-remoting connections.

More details are available here PRTG Manual: Custom Sensors.

Please check the custom-script-exe tagged posts, they may provide examples or further details about remoting.

Best Regards,

Created on May 16, 2016 7:58:43 AM by  Luciano Lingnau [Paessler]

Last change on Jul 24, 2018 7:47:07 AM by  Brandy Greger [Paessler Support]



6 Replies

Votes:

0

Hello mbaybarsk,
we appreciate your contact.

As for not having values, please be aware that channel values must be numerical, example result:

<prtg>
<result>
<channel>CPU Core #1</channel>
<value>34</value>
<Unit>Temperature</Unit>
</result>
<result>
<channel>CPU Core #2</channel>
<value>42</value>
<Unit>Temperature</Unit>
</result>
<result>
<channel>CPU Package</channel>
<value>42</value>
<Unit>Temperature</Unit>
</result>
</prtg>

Make sure that all values are numerical. You can check the actual result received by PRTG by enabling the Write EXE result to disk setting within the sensor, the log will be stored on the probe which runs the sensor under this folder:

C:\ProgramData\Paessler\PRTG Network Monitor\Logs (Sensors)

Best Regards,

Created on May 12, 2016 12:06:11 PM by  Luciano Lingnau [Paessler]



Votes:

0

If I'm only allowed numerical sensors with this type of sensor. Is there any way I can use WQL scripts to get string results? Or any other type?

Created on May 12, 2016 1:46:33 PM



Votes:

0

You can use the <text> element to return text within a sensor, but please be aware that:

  1. The text is for the whole sensor (Sensor's message), it can't be assigned to channels. See output below for example.
  2. PRTG will not perform further evaluation upon the text, any warning/error related status processing will have to be done in the script itself, see second example.
            <prtg>
            <result>
            <channel>First channel</channel>
            <value>10</value>
            </result>
            <result>
            <channel>Second channel</channel>
            <value>20</value>
            </result>
            <text>This is the sensors text</text>
            </prtg>

Example output to set force the sensor into error (Down) :

              <prtg>
              <error>1</error>
              <text>Your error message</text>
              </prtg>
  • It's also possible to set the whole sensor to a Warning status by appending it to one of the <channel> entries (In contrast to the <error>1</error> which must be used outside of the <result>):
            <prtg>
            <result>
            <channel>First channel</channel>
            <value>10</value>
            <Warning>1</Warning>
            </result>
            <result>
            <channel>Second channel</channel>
            <value>20</value>
            </result>
            <text>This is the sensors text</text>
            </prtg>

Please check the API's documentation for further details.

Best Regards,

Created on May 13, 2016 8:36:15 AM by  Luciano Lingnau [Paessler]

Last change on Jul 24, 2018 7:47:59 AM by  Brandy Greger [Paessler Support]



Votes:

0

Hello,

I get it, I will have to use WMI for those text based values. However, the problem with other numerical values continue. Here's a better version of the same script.

Get-Content : Cannot bind argument to parameter 'Path' because it is null.
$output = "<prtg>"
$hostname = $env:computername
$drives = get-psdrive -psprovider 'FileSystem' | select root
$drives = $drives.root

ForEach ($drive in $drives) 
    {$path = $drive + "BroadView\ServerManager\Plugins\startup_plugin.xml"
     if (test-path $path)
     {$startup = $path}
    }

[xml]$XmlDocument = Get-Content  $startup 
$databases = $xmldocument.BVSManager.StartupData.DBEntries.Database | where { $_.Server -eq $hostname} 
$databases = $databases.Path
$numberofdbs = $databases.count 



for  ($i=0; $i -le $numberofdbs; $i++)
{
$size = (get-item($databases[$i])).Length
$output = $output + "<result><channel>" + $i + "</channel><value>" + $size + "</value></result>" 
}

$output += "</prtg>"
write-host $output

When I run this script manually on the destination servers, it runs perfectly fine & gives me the XML I want but the script fails when run as a sensor. Here are the error messages:

Get-Content : Cannot bind argument to parameter 'Path' because it is null.
At C:\Program Files (x86)\PRTG Network Monitor\custom 
sensors\EXEXML\BVS_Clients.ps1:12 char:34
+ [xml]$XmlDocument = Get-Content  $startup
+                                  ~~~~~~~~
    + CategoryInfo          : InvalidData: (:) [Get-Content], ParameterBinding 
   ValidationException
    + FullyQualifiedErrorId : ParameterArgumentValidationErrorNullNotAllowed,M 
   icrosoft.PowerShell.Commands.GetContentCommand
 
Cannot index into a null array.
At C:\Program Files (x86)\PRTG Network Monitor\custom 
sensors\EXEXML\BVS_Clients.ps1:21 char:1
+ $size = (get-item($databases[$i])).Length
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    + CategoryInfo          : InvalidOperation: (:) [], RuntimeException
    + FullyQualifiedErrorId : NullArray
 
<prtg><result><channel>0</channel><value></value></result></prtg>

I believe the reason for that is PRTG is simply running this locally. How can I make PRTG run this script on the host that has this sensor setup?

Created on May 13, 2016 5:09:49 PM

Last change on May 16, 2016 7:49:57 AM by  Luciano Lingnau [Paessler]



Accepted Answer

Votes:

0

You're absolutely correct:

PRTG will always run any script locally on the Probe that monitors the said device/sensor. This is desirable in some cases and to run the script on a remote system you need to use some sort of remoting, for instance powershell offers:

Invoke-Command -ComputerName $host [...]

Within PRTG you can pass the %host parameter to the custom-script sensor to use it within the script later. The same applies to the other parameters (%windowsdomain, %windowsuser, %windowspassword, ...)

Please note that the remote system must also be configured to accept powershell-remoting connections.

More details are available here PRTG Manual: Custom Sensors.

Please check the custom-script-exe tagged posts, they may provide examples or further details about remoting.

Best Regards,

Created on May 16, 2016 7:58:43 AM by  Luciano Lingnau [Paessler]

Last change on Jul 24, 2018 7:47:07 AM by  Brandy Greger [Paessler Support]



Votes:

1

Thanks for the response, it all works as I wanted other than having the ability to have strings as a value on powershell scripts.

Here's the final form of my script if anybody needs an example on how to make this conversion.

param(
    [string]$device = 'xxx' ,
    [string]$smdevice = 'xxx' ,
    [string]$domain = 'domain',
    [string]$username = 'user',
    [string]$password = 'password'
    )

$combination = $domain + "\" + $username
$pass = ConvertTo-SecureString -AsPlainText $password -Force
$Cred = New-Object System.Management.Automation.PSCredential -ArgumentList $combination,$pass

$result = Invoke-Command -ComputerName $smdevice -ScriptBlock {  

param(
    [string]$device
    )

$drives = get-psdrive -psprovider 'FileSystem' | select root
$drives = $drives.root

ForEach ($drive in $drives) 
    {$path = $drive + "xyz\ServerManager\Plugins\startup_plugin.xml"
     if (test-path $path)
     {$startup = $path}
    }

[xml]$XmlDocument = Get-Content  $startup 
$databases = $xmldocument.BVSManager.StartupData.DBEntries.Database | where { $_.Server -eq $device}
$databases = $databases.Path 
return $databases

} -credential $cred -ArgumentList $device


Invoke-Command -ComputerName $device -ScriptBlock { 
param(
    [array]$result
    ) 

$databases = $result
$numberofdbs = $databases.count

$output = "<prtg>"

for  ($i=0; $i -lt $numberofdbs; $i++)
{
$size = (get-item($databases[$i])).Length
if ($databases[$i]) {$channelname = $databases[$i]} else {$channelname = 'unknown'}
$output = $output + "<result><channel>" + $channelname + "</channel><value>" + $size + "</value></result>" 
}

$output += "</prtg>"
return $output


} -credential $cred -ArgumentList (,$result) 

Created on May 16, 2016 2:47:34 PM

Last change on May 16, 2016 7:08:08 PM by  Luciano Lingnau [Paessler]




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.