This discussion has been locked. The information referenced herein may be inaccurate due to age, software updates, or external references.
You can no longer post new replies to this discussion. If you have a similar question you can start a new discussion in this forum.

SSL VPN Dashboard

When Covid hit and most of our people started to go remote VPN became more crucial than ever so I designed a dashboard that tracks various statistics (number of connections, CPU, utilization etc.) across our infrastructure. 

There are a few key elements that are used:

  • PerfStack - charts to display most of the data
  • API Pollers - this was a workaround to get data obtained via SWQL to display in PerfStack (as you may know it supports various objects as source, including API Poller Monitored Value). Basically we have an API Poller that returns four metrics returned by a SWQL query to the Orion API (total sessions per region and total global sessions). 
  • Custom HTML (to display status, active connections, peak connections and maximum supported connections for each ASA firewall) and Tall Blank Space (for aligning purposes) widgets.

This is what it ended up looking like (I have also attached a zoomed-out version of the whole dashboard so you get a better idea):

VPN_1.jpg

Prerequisites:

  • Import the attached Custom Poller (or you can use the metrics provided OOTB by Network Insights for ASA; we found that there were some issues with some ASAs so we ended up using custom pollers)
  • (Optional) A custom property named 'VPN_Session_Effective_Limit'; our engineers were not satisfied with the maximum sessions supported numbers collected via the Custom Poller above so they suggested we use other values extracted from device documentation, based on device model. If you choose to stick with the "Max_Sessions_Supported" metric collected by the Custom Poller then you will have to edit the HTML/JS for the widgets (the query returns all of them anyway, I'll talk about that when I get to the code).

Components:

  1. The PerfStack chart at the top contains four metrics collected via an API Poller (in our case we calculate total sessions for each region and then total global connections; it might not make sense in your case so feel free to adapt it to your particular requirements):

API_Poller.JPG

URL: 

https://solarwindsppe.solarwinds.pvt:17778/SolarWinds/InformationService/v3/Json/Query?Content-Type=application/json&query=<QUERY> 

(Make sure to replace https://solarwindsppe.solarwinds.pvt with the URL to your own Orion instance)

where QUERY is (make sure to write it all on the same line; I only expanded it so it looks cleaner):

SELECT 
SUM(a.global) as Total_Sessions_Global, 
SUM(a.nala) as Total_Sessions_NALA, 
SUM(a.emea) as Total_Sessions_EMEA, 
SUM(a.apac) as Total_Sessions_APAC 
FROM 
(SELECT 
(case WHEN AssignmentName <Case_1> then Rate END) as global, 
(case WHEN AssignmentName <Case_2> then Rate END) as nala, 
(case WHEN AssignmentName <Case_3> then Rate END) as emea, 
(case WHEN AssignmentName <Case_4> then Rate END) as apac 
FROM Orion.NPM.CustomPollerStatusOnNodeScalar ) 
as a 

 The criteria used to select statistics for each region are dependent on your network architecture and naming standard (in our case it's 'LIKE '%<Custom_Poller_Name>%<Partial_Hostname>%', where Partial_Hostname is common for all ASAs located in a certain regional DC).

2. Regional VPN charts: In our case we display active connections per ASA, peak receive and transmit bps for the Outside interface and Peak CPU utilization (feel free to use whatever makes sense to you).

3. Custom HTML widgets.

Now comes the fun part:

Each widget (three in total) is aligned next to regional charts (by patiently adjusting the Height parameter on the Tall Blank Space widgets) and contains ASA Hostname, Status, Current Active Sessions, Peak Concurrent Sessions and Max Supported Sessions. Colors also change automatically when warning/critical thresholds are reached (WARNING - yellow - active connections >= 85% max supported AND  active connections < 95% max supported; CRITICAL - red - active connections >= 95% max supported).

Code is attached, the only thing I would highlight is the queries that generate the content of each widget (again, we have three groups of ASAs, one per region; that might not be appropriate to you):

switch(region) 
{ case "NALA": 
    query= "SELECT n.Caption as Hostname,REPLACE(n.StatusIcon,'.gif','') as Status,n.CustomPollerAssignmentOnNode.CustomPollerName,n.CustomPollerAssignmentOnNode.CurrentValue,n.CustomProperties.VPN_Session_Effective_Limit FROM Orion.Nodes n WHERE n.Caption <Case_Region_1> and n.CustomPollerAssignmentOnNode.CustomPollerName LIKE '%_Session%' ORDER BY n.Caption ASC,n.CustomPollerAssignmentOnNode.CustomPollerName ASC"; 
break; 

case "APAC": 
   query= "SELECT n.Caption as Hostname,REPLACE(n.StatusIcon,'.gif','') as Status,n.CustomPollerAssignmentOnNode.CustomPollerName,n.CustomPollerAssignmentOnNode.CurrentValue,n.CustomProperties.VPN_Session_Effective_Limit FROM Orion.Nodes n WHERE n.Caption <Case_Region_2> and n.CustomPollerAssignmentOnNode.CustomPollerName LIKE '%_Session%' ORDER BY n.Caption ASC,n.CustomPollerAssignmentOnNode.CustomPollerName ASC"; 
break; 

case "EMEA": 
     query= "SELECT n.Caption as Hostname,REPLACE(n.StatusIcon,'.gif','') as Status,n.CustomPollerAssignmentOnNode.CustomPollerName,n.CustomPollerAssignmentOnNode.CurrentValue,n.CustomProperties.VPN_Session_Effective_Limit FROM Orion.Nodes n WHERE n.Caption <Case_Region_3> and n.CustomPollerAssignmentOnNode.CustomPollerName LIKE '%_Session%' ORDER BY n.Caption ASC,n.CustomPollerAssignmentOnNode.CustomPollerName ASC"; 
break; 
} 

 In my original code <Case_Region_1> .... <Case_Region_2> use either LIKE (partial hostname) or IN (list of ASAs for each widget). Make sure to edit the queries in the attached code.

The code attached only needs to be inserted in the first Custom HTML widget, the other two contain the following code:

<div id="vpn_EMEA"> </div> 
<div id="vpn_APAC"> </div> 

 The JavaScript from the first Custom HTML populates the other two on load.

And that's pretty much it! Easy, right? 

Let me know if I failed to explain something or the explanation does not make sense.

Stay safe!

attachments.zip