Recent Discussions
Collection Scripts
hi, Please find my code below import groovy.sql.Sql //@Grab('org.hsqldb:hsqldb:2.7.1:jdk8') //@GrabConfig(systemClassLoader=true) //@Grab("com.sybase.jdbc4.jdbc.SybDriver") Class.forName("com.sybase.jdbc4.jdbc.SybDriver") // Get basic info to connect def hostname = hostProps.get("system.hostname") def user = hostProps.get("sybase.user") def pass = hostProps.get("sybase.pass") def port = 21000 // Construct an SQL instance with a url and a driver def url = "jdbc:sybase:Tds:##hostname##:21000", username=user, password=pass //def url = "jdbc:sybase:Tds:hostname:port", "user", "pass" // sybase SQL Driver def driver = "com.sybase.jdbc4.jdbc.SybDriver" // Create a connection to the SQL server sql = Sql.newInstance(url,user,pass,driver) sql.withTransaction { // Iterate over query results and list the databases sql.eachRow("select name from master..sysdatabases") { name= it.toString().split(":")[1].replace("]","") // Create an instance for each database println name+"##"+name } } sql.close() return 0manthena20202 years agoAdvisor410Views12likes89CommentsIs there a way to set custom property values from your groovy script in your datasource?
Hey there. I’m relatively new to logic monitor and I received a request from a client. The request is as follows. They wanted us to be able to provide not only blocked processes alerts for their SQL dbs but also for us to provide a breakdown of what is blocking what. My solution to this was to edit the datasource that contains the processblocked datapoint. I made some good progress. I was able to create a custom property field for the instances that I’m monitoring. I then edited thescript for the collector attributeso that in theory that if particular datapoint (processessblocked) shows a value of greater than 0, it uses hostSets() to change that custom property value to the blocker session ids using some custom sql script within. When I test it using the test button pointed at my sql server, it works exactly as i expected. It shows the default value of the property unless it hits that block process value of 1 or more. then the property reads with the needed info. However after I save the datasource. And put this in to practice, no matter what the custom property on those instances never update or change. I also tried applying similar logic to the active discovery script with the same results. Seems to work fine through testing but then nothing in the actual instance changes. I can post any or all of the groovy script if need be. Is it something simple like some sort of syntax I’m not getting or am I not even in the right area to do what I’m attempting to do? Any help would be appreciated and like I said, I’ll gladly provide any more info or code if need be. ThanksSolved862Views12likes70CommentsCollection the data metrics where there are unique keys
SPID = 1 BLOCKED = 0 SPID = 3 BLOCKED = 0 SPID = 4 BLOCKED = 0 SPID = 5 BLOCKED = 0 SPID = 6 BLOCKED = 0 SPID = 7 BLOCKED = 0 SPID = 8 BLOCKED = 0 SPID = 9 BLOCKED = 0 SPID = 10 BLOCKED = 0 SPID = 11 BLOCKED = 0 SPID = 12 BLOCKED = 0 SPID = 13 BLOCKED = 0 SPID = 14 BLOCKED = 0 SPID = 17 BLOCKED = 0 SPID = 37 BLOCKED = 0 SPID = 60 BLOCKED = 0 SPID = 107 BLOCKED = 0 SPID = 147 BLOCKED = 0 SPID = 165 BLOCKED = 0 SPID = 183 BLOCKED = 0 SPID = 251 BLOCKED = 0 SPID = 273 BLOCKED = 0 SPID = 319 BLOCKED = 0 SPID = 430 BLOCKED = 0 SPID = 435 BLOCKED = 0 SPID = 466 BLOCKED = 0 SPID = 470 BLOCKED = 0 SPID = 494 BLOCKED = 0 SPID = 522 BLOCKED = 0 SPID = 539 BLOCKED = 0 SPID = 555 BLOCKED = 0 SPID = 584 BLOCKED = 0 SPID = 596 BLOCKED = 0 SPID = 600 BLOCKED = 0 SPID = 651 BLOCKED = 0 SPID = 673 BLOCKED = 0 i want to capture the above data, the above data is my querry result. please tell me the data point settingsmanthena20202 years agoAdvisor398Views4likes58CommentsSQL Certificates
Hello, I am trying to collect the SQL Certificates obtain by "Select name, expiry_date from sys.certificates" to have an alert when their expiration date arrived. I tried by datasource but apparently it is not feasible after consultation with LM Support. I was directed to Property Sources but not finding my way in this new environment... Any groowvy script to be used for that? import com.santaba.agent.groovyapi.expect.Expect; import com.santaba.agent.groovyapi.snmp.Snmp; import com.santaba.agent.groovyapi.http.*; import com.santaba.agent.groovyapi.jmx.*; import org.xbill.DNS.*; import groovy.sql.Sql // needed for SQL connection and query def hostname = hostProps.get("system.hostname"); import groovy.sql.Sql // needed for SQL connection and query def url = "jdbc:sqlserver://" + hostname + ";databaseName=master;integratedSecurity=true"; def driver = "com.microsoft.sqlserver.jdbc.SQLServerDriver"; sql = Sql.newInstance(url, driver) // connects to SQL server def query_result = sql.firstRow("SELECT name, expiry_date from sys.certificates") full_name_certificate = query_result.name full_date_certificate = query_result.expiry_date sql.close() // Close connection ... return 0; This part looks okay but how to get the information in the Alert... ... Thanks, DomSolvedDominique5 years agoAdvisor174Views2likes42CommentsAccessing the LogicMonitor REST API with Postman and LMv1 API Token Authentication
Introduction Postmanis widely used for interacting with various REST APIs such as LogicMonitor's. However, there is no out-of-the-box support for the LMv1 authentication method which we recommend as a best practice. This document describes how to configure Postman to use LMv1 authentication when interacting with our REST API. Overview Postman'spre-request script functionalityprovides the ability to generate the necessary Authorization header for LMv1 authentication. As the name suggests, the pre-request script runs immediately before the request is made to the API endpoint. We set the pre-request script at the collection level in Postman so that it will run automatically for every request that is part of the collection. The script requires three input parameters: a LogicMonitor API token (or ID), its associated key, and the full request URL. These parameters are made available to the script by creating a Postman environment and setting the values as environment variables. If you need to access multiple LogicMonitor accounts (portals), create a separate environment for each to store the applicable API and URL information. Since all API requests to a given account use the same base URL (https://<account>.logicmonitor.com/santaba/rest) it is convenient to store this as an environment variable. The output of the script is the value of the Authorization header. The script writes the header value to an environment variable which is then inserted as the Authorization header value in the request. Instructions 1. Download and installPostman. 2. Launch Postman andcreate a new collectionthat will be used for all LogicMonitor API requests. 3. In the create collection dialog, select the "Pre-request Scripts" section and paste in the following code. // Get API credentials from environment variablesvar api_id = pm.environment.get('api_id');var api_key = pm.environment.get('api_key'); // Get the HTTP method from the requestvar http_verb = request.method; // Extract the resource path from the request URLvar resource_path = request.url.replace(/(^{{url}})([^\?]+)(\?.*)?/, '$2'); // Get the current time in epoch formatvar epoch = (new Date()).getTime(); // If the request includes a payload, included it in the request variablesvar request_vars = (http_verb == 'GET'||http_verb == 'DELETE') ?http_verb + epoch + resource_path : http_verb + epoch + request.data + resource_path; // Generate the signature and build the Auth headervar signature = btoa(CryptoJS.HmacSHA256(request_vars,api_key).toString());var auth = "LMv1 " + api_id + ":" + signature + ":" + epoch; // Write the Auth header to the environment variablepm.environment.set('auth', auth); 4. Create anew environment. Create the environment variables shown below. You do not need to provide a value for the "auth" variable since this will be set by the pre-request script. Be sure to use the api_id, api_key, and url values appropriate for your LogicMonitor account. 5. Create arequestand add it to the collection with the pre-request script. A sample request is shown below with the necessary parameters configured. 1. Set the environment for the request, 2. Set the HTTP method for the request. 3. Use{{url}} to pull the base URL from the environment variable. Add the resource path and any request parameters your API request may require. 4. Add the Authorization header and set the value to{{auth}}to pull the the value from the environment variable. 5. POST, PUT, and PATCH requests only: if your request includes JSON data, be sure to select the Body tab and add it. 6. Press Send to send the request. The response will appear below the request in Postman. Troubleshooting You receive the response "HTTP Status 401 - Unauthorized" Confirm the following: • The proper environment has been specified for the request. • The necessary environment variables have been set and their values are correct. Note that the script relies on the specific variable names used in this document: "api_id", "api_key", "url", and "auth". • The request is a member of the collection configured with the pre-request script. Postman reports "Could not get any response" or "There was an error in evaluating the Pre-request Script: TypeError: Cannot read property 'sigBytes' of undefined" Make sure you have set the proper environment for the request and all necessary environment variables and values are present.Kurt_Huffman7 years agoFormer Employee3.3KViews42likes42CommentsCertificate "IssuedBy" "Daystoexpire" to be displayed...
Hello, I have the discovery script: Quote ##--------------- Discovery ------------------## $pshost = Get-Host # Get the PowerShell Host. $pswindow = $pshost.UI.RawUI # Get the PowerShell Host's UI. $newsize = $pswindow.BufferSize # Get the UI's current Buffer Size. $newsize.width = 800 # Set the new buffer's width to 800 columns. $pswindow.buffersize = $newsize # Set the new Buffer Size as active. $newsize = $pswindow.windowsize # Get the UI's current Window Size. $newsize.width = 800 # Set the new Window Width to 800 columns. $pswindow.windowsize = $newsize # Set the new Window Size as active. $readOnly = [System.Security.Cryptography.X509Certificates.OpenFlags]"ReadOnly" $localMachine = [System.Security.Cryptography.X509Certificates.StoreLocation]"LocalMachine" $store = new-object System.Security.Cryptography.X509Certificates.X509Store( "\\##SYSTEM.SYSNAME##\my", $localMachine ) ##--------------- Discovery ------------------## $pshost = Get-Host # Get the PowerShell Host. $pswindow = $pshost.UI.RawUI # Get the PowerShell Host's UI. $newsize = $pswindow.BufferSize # Get the UI's current Buffer Size. $newsize.width = 800 # Set the new buffer's width to 800 columns. $pswindow.buffersize = $newsize # Set the new Buffer Size as active. $newsize = $pswindow.windowsize # Get the UI's current Window Size. $newsize.width = 800 # Set the new Window Width to 800 columns. $pswindow.windowsize = $newsize # Set the new Window Size as active. $readOnly = [System.Security.Cryptography.X509Certificates.OpenFlags]"ReadOnly" $localMachine = [System.Security.Cryptography.X509Certificates.StoreLocation]"LocalMachine" $store = new-object System.Security.Cryptography.X509Certificates.X509Store( "\\##SYSTEM.SYSNAME##\my", $localMachine ) $store.Open( $readOnly ) $store.Certificates ` | Select-Object { ` $_.Thumbprint + "##" ` + $(If ($_.FriendlyName -eq "") {"Unknown friendly name (" + $_.Thumbprint + ")"} Else {$_.FriendlyName}) + "##" ` + $_.Subject + $(If ($_.Subject -ne "") {"(..." + $_.Thumbprint.SubString($_.Thumbprint.length - 5, 5) + ")"} Else {"Unknown subject (" + $_.Thumbprint + ")"}) + "##" ` + "##" ` + "cert.issuer=" + $_.Issuer ` + "&cert.friendlyname=" + $_.FriendlyName ` + "&cert.serialnumber=" + $_.SerialNumber ` + "&cert.thumbprint=" + $_.Thumbprint ` } ` | Format-Table -HideTableHeaders then the Quote ##-------------- Counters --------------------## $pshost = Get-Host # Get the PowerShell Host. $pswindow = $pshost.UI.RawUI # Get the PowerShell Host's UI. $newsize = $pswindow.BufferSize # Get the UI's current Buffer Size. $newsize.width = 800 # Set the new buffer's width to 800 columns. $pswindow.buffersize = $newsize # Set the new Buffer Size as active. $newsize = $pswindow.windowsize # Get the UI's current Window Size. $newsize.width = 800 # Set the new Window Width to 800 columns. $pswindow.windowsize = $newsize # Set the new Window Size as active. $readOnly = [System.Security.Cryptography.X509Certificates.OpenFlags]"ReadOnly" $localMachine = [System.Security.Cryptography.X509Certificates.StoreLocation]"LocalMachine" $store = new-object System.Security.Cryptography.X509Certificates.X509Store( "\\##SYSTEM.SYSNAME##\my", $localMachine ) $properties = @( # @{n='WildValue';e={"##WildValue##"}}, @{n='CommonName';e={$_.Subject}}, @{n='Thumbprint';e={$_.Thumbprint}}, # @{n='Description';e={"##Description##"}}, @{n='Properties';e={"##Properties##"}}, @{n='IssuedBy';e={($_.Issuer)}}, @{n='daystoexpire';e={($_.NotAfter - [datetime]::Today).Days}} ) $store.Open( $readOnly ) $store.Certificates ` | Where-Object {($_.Thumbprint -like "##WildValue##")} ` | Select-Object $properties ` | Format-Table -HideTableHeaders But when populating the groups I have No Data... and So we see the data in the Raw Request/ Response fields... What is happening? Thanks, DomDominique4 years agoAdvisor33Views1like41CommentsReplace IP by DNS Name
Hello, I got from Eric and Josh a script which is having the basic code to do the task I need. I would like to replace the IP Address/DNS Name by the DNS Name for all our servers. ######################### API Function Script ######################### #------------------------------------------------------------------------------------------------------------ # Prerequisites: # # Requires -Version 3 #------------------------------------------------------------------------------------------------------------ # Initialize Variables <# account info #> $accessId = "1234567890-" $accessKey = '1234567890-' $company = "xxxxxxxx" #------------------------------------------------------------------------------------------------------------ # Functionize the reusable code that builds and executes the query function Send-Request() { Param( [Parameter(position = 0, Mandatory = $true)] [string]$path, [Parameter(position = 1, Mandatory = $false)] [string]$httpVerb = 'GET', [Parameter(position = 2, Mandatory = $false)] [string]$queryParams, [Parameter(position = 3, Mandatory = $false)] [PSObject]$data ) # Use TLS 1.2 [Net.ServicePointManager]::SecurityProtocol = [Net.SecurityProtocolType]::Tls12 <# Construct URL #> $url = "https://$company.logicmonitor.com/santaba/rest$path$queryParams" <# Get current time in milliseconds #> $epoch = [Math]::Round((New-TimeSpan -start (Get-Date -Date "1/1/1970") -end (Get-Date).ToUniversalTime()).TotalMilliseconds) <# Concatenate Request Details #> $requestVars = $httpVerb + $epoch + $data + $path <# Construct Signature #> $hmac = New-Object System.Security.Cryptography.HMACSHA256 $hmac.Key = [Text.Encoding]::UTF8.GetBytes($accessKey) $signatureBytes = $hmac.ComputeHash([Text.Encoding]::UTF8.GetBytes($requestVars)) $signatureHex = [System.BitConverter]::ToString($signatureBytes) -replace '-' $signature = [System.Convert]::ToBase64String([System.Text.Encoding]::UTF8.GetBytes($signatureHex.ToLower())) <# Construct Headers #> $auth = 'LMv1 ' + $accessId + ':' + $signature + ':' + $epoch $headers = New-Object "System.Collections.Generic.Dictionary[[String],[String]]" $headers.Add("Authorization", $auth) $headers.Add("Content-Type", 'application/json') $headers.Add("X-version", '2') <# Make request & retry if failed due to rate limiting #> $Stoploop = $false do { try { <# Make Request #> $response = Invoke-RestMethod -Uri $url -Method $httpVerb -Body $data -Header $headers $Stoploop = $true } catch { switch ($_) { { $_.Exception.Response.StatusCode.value__ -eq 429 } { Write-Host "Request exceeded rate limit, retrying in 60 seconds..." Start-Sleep -Seconds 60 $response = Invoke-RestMethod -Uri $url -Method $httpVerb -Body $data -Header $headers } { $_.Exception.Response.StatusCode.value__ } { Write-Host "Request failed, not as a result of rate limiting" # Dig into the exception to get the Response details. # Note that value__ is not a typo. Write-Host "StatusCode:" $_.Exception.Response.StatusCode.value__ Write-Host "StatusDescription:" $_.Exception.Response.StatusCode $_.ErrorDetails.Message -match '{"errorMessage":"([\d\S\s]+)","errorCode":(\d+),' Write-Host "LM ErrorMessage" $matches[1] Write-Host "LM ErrorCode" $matches[2] $response = $null $Stoploop = $true } default { Write-Host "An Unknown Exception occurred:" Write-Host $_ | Format-List -Force $response = $null $Stoploop = $true } } } } While ($Stoploop -eq $false) Return $response } # Get list of Resources $members = {VRPSCCMRS01} $httpVerb = 'GET' $resourcePath = "/device/devices/$member.id" $queryParams = $null $data = $null $results = Send-Request $resourcePath $httpVerb $queryParams $data foreach ($hostname in $results.items) { $sysname = (($hostname.systemProperties) | Where-Object -Property "Name" -eq "system.sysname").value if ($sysname -match "\.") { $newName = $sysname.split(".")[0] } else { $newName = $sysname } if ($hostname.Name -eq $newName) { Write-Host "Name `"$($hostname.displayName)`" matched no change needed" } else { $httpVerb = 'PATCH' $resourcePath = "/device/devices/$($deviceId)" $queryParams = "?patchFields=Name&opType=replace" $data = @{ Name = $newName } | ConvertTo-Json Send-Request $resourcePath $httpVerb $queryParams $data Write-Host "Changed host id $($hostname.id) Name from `"$($hostname.ips)`" to `"$newName`"." } } but for now I am getting an error: Request failed, not as a result of rate limiting StatusCode: 404 StatusDescription: NotFound LM ErrorMessage HTTP 404 Not Found LM ErrorCode 1400 Any idea of the issue? Test in progress Thanks, DomDominique5 years agoAdvisor253Views1like41CommentsNew VMware modules dropped
Did anybody else notice the ~44 new and ~5 updated modules around VMware dropping in the last hour or so? Does anyone know how to implement these new modules? Since there was talk of making the instances into resources I don’t want to just bring them in without knowing how it’s going to mess with my device list (which is tightly bound to billing for us).Anonymous2 years ago829Views30likes41CommentsUsing Postman to create multiple Websites via API & CSV?
Hi, I’m testing out creating websites (or resources) via the API. I have a standard Post working in Postman just fine. However, when I then try to do the same thing via a CSV file in the Runner section, I’m getting 401 Authorization errors. When I look at the data that’s being sent, it looks the same as what’s sent when I run it manually. Is there something special I need to do when running a Post command via the Runner vs the manual Send command? Thanks.Solved523Views12likes40CommentsPing Failing from collector to device and back?
Hello I am getting errors:“VIPEIEEMP01 is suffering ping loss. 100.0% of pings are not returning, placing the host into critical state.” “The host VIPEIEEMP01 is down. No data has been received” If I do a ping from the command prompt of the Clientto theCollectorit works The firewall is wide opened!!! What did I miss? Thanks, DomDominique3 years agoAdvisor1KViews16likes40Comments