Category Archives: WhatsUp

Querying other SQL databases using active script in WhatsUp

This is a script that allows you to query an SQL server other than the WhatsUp DB. It doesn’t require a DSN ODBC entry and is self contained.

Let’s assume we want to run this query:

SELECT cur_latency from MSreplication_monitordata where agent_type='3' and publication_id='2'

against a server named mySQLserver. To do that we can use the ADODB object in VBScript:

Const adOpenStatic = 3
Const adLockOptimistic = 3
Const adUseClient = 3
Set objConnection = CreateObject("ADODB.Connection")
Set objRecordset = CreateObject("ADODB.Recordset")

'We're not using a DSN so specify the connection string
strConnectionString="DRIVER={SQL Server};SERVER=" & strDatabaseServer & ";UID=" & strUsername &_
";PWD=" & strPassword & ";DATABASE=" & strDatabaseName
context.logmessage strConnectionString

objConnection.Open strConnectionString
objRecordset.CursorLocation = adUseClient

This bit of the script creates a Connection object and using the connection string opens a connection to the SQL server. We then use that connection to perform our query:

'This is the query to run
strQuery="SELECT cur_latency from MSreplication_monitordata where agent_type='3' and publication_id='2'"
'Connect to the DB server and run the query
objRecordset.Open strQuery, objConnection, adOpenStatic,adLockOptimistic

The rows returned populate the record set object. We’re only expecting one row for this one so we can get the result by:

If objRecordset.EOF Then
    'No rows returned
    context.logmessage "Record cannot be found."
Else
    'rows returned
    context.logmessage objrecordset("cur_latency") 
    context.setvalue int(cur_latency)
End If

and then close the objects sets.

objRecordset.Close
objConnection.Close

Here’s the full script:

'The database server is kept in an attribute named "DatabaseServerName"
strDatabaseServer="mySQLserver"

'The database that stores the replication configuration is "distribution"
strDatabaseName="distribution"

'This is the query to run
strQuery="SELECT cur_latency from MSreplication_monitordata where agent_type='3' and publication_id='2'"

'Get the logon credentials
strUsername = Context.GetProperty("CredADO:Username")
strPassword = Context.GetProperty("CredADO:Password")

Const adOpenStatic = 3
Const adLockOptimistic = 3
Const adUseClient = 3
Set objConnection = CreateObject("ADODB.Connection")
Set objRecordset = CreateObject("ADODB.Recordset")

'We're not using a DSN so specify the connection string
strConnectionString="DRIVER={SQL Server};SERVER=" & strDatabaseServer & ";UID=" & strUsername &_
";PWD=" & strPassword & ";DATABASE=" & strDatabaseName
context.logmessage strConnectionString

objConnection.Open strConnectionString
objRecordset.CursorLocation = adUseClient

'Connect to the DB server and run the query
objRecordset.Open strQuery, objConnection, adOpenStatic,adLockOptimistic

If objRecordset.EOF Then
    'No rows returned
    context.logmessage "Record cannot be found."
Else
    'rows returned
    context.logmessage objrecordset("cur_latency") 
    context.setvalue int(cur_latency)
End If

objRecordset.Close
objConnection.Close

Download the source from the link:

Download

Advertisements
Tagged , , , , , ,

Collecting crypto VPN traffic info from Cisco routers

Cisco crypto site to site VPNs are quite useful but it is difficult to collect traffic stats when there is no virtual interface for SNMP to track. Instead the stats are held in the Cisco SNMP mibs in various places and you have to cross-reference between those places to work out which SNMP entry refers to which VPN tunnel. This gets harder the more tunnels you have from your router.

With this in mind I’ve created a WhatsUp performance monitor script to collect the traffic receive (rx) and transmit (tx) stats through SNMP. You’ll need to grab the Cisco router mibs and install them into the WhatsUp mibs directory first before this script will work.

On the Cisco side you’ll be setting up a vpnmap entry such as this one:

crypto map mymap 141 ipsec-isakmp set peer x.x.x.x set transform-set xxxx match address myvpn-acl 

The crypto map number is useful as this is how the script finds the correct VPN tunnel in SNMP:

'The remote peer
strVPNMapNumber="141"

The other variable to alter is whether the statistic to be collected is receive (rx) or transmit (tx) with respect to the router being polled. This is specified by this line:

' The direction of traffic (rx or tx)
strDirection="rx"

How the script works

The script gets a list of all the ipsec tunnels (get_ipsecTunnel_list) which is held at SNMP OID 1.3.6.1.4.1.9.9.172.1.2.1.1.3. It looks down the list for entries which relate to the vpnmap number, 141 in this case and compiles a list of entries. This list is then used to collect the receive or transmit statistics and add the values together for each ipsec tunnel associates with that isakmp tunnel (there can be many ipsec tunnels per isakmp tunnel depending on your match acl setup).

The script in full

'The remote peer
strVPNMapNumber="141"

' The direction of traffic (rx or tx)
strDirection="rx"

ipSecVPNMapIndex = "1.3.6.1.4.1.9.9.172.1.2.1.1.3"
ipSecInOct              = "1.3.6.1.4.1.9.9.171.1.3.2.1.26"
ipSecOutOct             = "1.3.6.1.4.1.9.9.171.1.3.2.1.39"

set objSNMPReq = CreateObject("CoreAsp.SnmpRqst")
strDeviceID = Context.GetProperty("DeviceID")
set objSNMPInit = objSNMPReq.Initialize(strDeviceID)

if objSNMPInit.Failed then
    '.
else
    ' Get a list of indexes which match the VPN map number
    arrIpsecIndex = split(get_ipsecTunnel_list(ipSecVPNMapIndex,strVPNMapNumber),",")

    intFirstReading = get_TrafficSum()
    context.logmessage "FirstReading=" & intFirstReading 
    sleep(1)
    intSecondReading = get_TrafficSum()
    context.logmessage "SecondReading=" & intSecondReading 
    intTotalTrafficReading = intSecondReading - intFirstReading
    'value is in bytes
    Context.SetValue (intTotalTrafficReading * 8)/1000
    context.logmessage "Total=" & (intTotalTrafficReading * 8)/1000
end if

function get_TrafficSum()
    inttmpTotalTrafficReading=0
    context.logmessage ubound(arrIpsecIndex)
    for each ipsecTunnelID in arrIpsecIndex
        context.logmessage "Processing Tunnel ID " & ipsecTunnelID
        if string_compare(strDirection,"rx") then
            strtmpOID=ipSecInOct
        else
            strtmpOID=ipSecOutOct
        end if
        inttmpResult=get_SNMPget(strtmpOID & "." & ipsecTunnelID)
        context.logmessage ipsecTunnelID & "=" & inttmpResult
        inttmpTotalTrafficReading = inttmpTotalTrafficReading + inttmpResult
    next
    get_TrafficSum = inttmpTotalTrafficReading
end function

function get_ipsecTunnel_list (strOID,strtmpTargetValue)
    tmpReturnValue=""
    boolExitWhile=0

    set objtmpSNMPResult = objSNMPReq.GetNext(strOID)

                context.logmessage "Looking for entry index OID for target " & strtmpTargetValue

    While boolExitWhile <> 1
        currSNMPPayload = objtmpSNMPResult.GetValue
        currSNMPIndex=objtmpSNMPResult.GetOID
        context.logmessage currSNMPIndex & "=" & currSNMPPayload 

        if currSNMPPayload = strtmpTargetValue then 
                                    context.logmessage currSNMPPayload & "=" & strtmpTargetValue
            currIndexNum=get_indexFromOID(currSNMPIndex)
            if tmpReturnValue = "" then
                tmpReturnValue=currIndexNum
                                                '    context.logmessage "ipsec index num is " & currIndexNum
            else 
                tmpReturnValue = tmpReturnValue & "," & currIndexNum
                                                '                   context.logmessage "ipsec index num is " & currIndexNum
            end if
            context.logmessage "index num is " & tmpReturnValue
        end if

        if string_compare(strOID,currSNMPIndex) then
            'context.logmessage "Setting next entry after " & currSNMPIndex
            set objtmpSNMPResult = objSNMPReq.GetNext(currSNMPIndex)
        else
            'context.logmessage currSNMPIndex & " isn't in OID " & strOID
            'context.logmessage "Didn't find match for target " & strtmpTargetValue 
            boolExitWhile=1
        end if
    wend
    context.logmessage "Got value=" &  tmpReturnValue
    get_ipsecTunnel_list = tmpReturnValue
end function

function get_SNMPget(strtmpOID)
    set objtmpSNMPResult = objSNMPReq.Get(strtmpOID)
    strtmpValue=objtmpSNMPResult.GetPayload
    context.logmessage strtmpOID & " returned value " & strtmpValue
    get_SNMPget=strtmpValue
end function

private function string_compare(expression,targetstring)
    set oreg= new regexp
    oReg.pattern=expression
    oReg.IgnoreCase = TRUE
    if ("" = expression OR "" = targetstring) then
        boolSearchResult=0
    end if
    if oReg.test (targetstring) then
        boolSearchResult=1
    else
        boolSearchResult=0
    end if
    string_compare=boolSearchResult
end function

function sleep(intseconds)
    intstarttime = timer()
    while timer() < intstarttime+intseconds
        '.
    wend
end function

function get_indexFromOID(strtmpOID)
    strtmpValue=""

    arrtmpOID=split(strtmpOID,".")
    inttmpSize=ubound(arrtmpOID)
    strtmpValue=arrtmpOID(inttmpSize)
    context.logmessage "get_indexFromOID=" & strtmpValue

    get_indexFromOID=strtmpValue
end function

Download the script (rename to zip)

Tagged , , , , , , , ,

Working with attributes in WhatsUp

About attributes in WhatsUp

You can find the attributes for a device when you go to device properties and then attributes. By default they don’t hold much but they can used as a useful store of information for that device or for storing variables between active monitor/performance monitor polls.

The easiest way to manipulate the attributes is by directly updating the DeviceAttribute table in the WhatsUp database. The table has the following columns:

nDeviceAttributeID The primary key for the table and an incremental integer (1,2,3,4,5 etc)
nDeviceID This is the nDeviceID of the device to which the attribute belongs. It is also an integer
sName The name of the attribute. In WhatsUp this appears as the “Name” column. It is a string.
sValue The value assigned to the specific attribute.  This is also a string.

Attributes can be added, removed and modified by inserting, deleting and updating rows in the table. For example:

UPDATE [WhatsUp].[dbo].[DeviceAttribute] SET sValue ='Windows Server 2003' WHERE (nDeviceID = '100') AND (sName = 'OS')

In this case the attribute named OS is set with the value “Windows Server 2003”.

Similarly to create (INSERT) and remove (DELETE):

INSERT INTO [WhatsUp].[dbo].[DeviceAttribute] (nDeviceID,sName,sValue) VALUES ('100','OS','Windows 2003')
DELETE FROM [WhatsUp].[dbo].[DeviceAttribute] WHERE (nDeviceID='100' AND sName='OS')
Using this in scripts

WhatsUp allows us to use the built-in database object to access the database. To use this we put this at the top of our scripts:

‘ Retrieve DB object for connecting to WhatsUp
Set oDb = Context.GetDB

and then we can use the oDb object when executing SQL code against the database, like this:

INSERT INTO [WhatsUp].[dbo].[DeviceAttribute] (nDeviceID,sName,sValue) VALUES ('100','OS','Windows 2003')
oDb.Execute(sqlQuery)  

If we want to get the output, say do a query and retrieve the result we can do it this way:

sqlCheck = "SELECT nDeviceAttributeID FROM DeviceAttribute WHERE (nDeviceID = '100') AND (sName = 'OS')"
Set oRecordset = oDb.Execute(sqlCheck) context.logmessage oRecordset("nDeviceAttributeID")

which will print the result of the query to the screen. If an array is returned then this can be handle similarly by specifying the oRecordset(“nDeviceID”), oRecordSet(“sValue”) etc.

Of course when you’re writing your scripts you won’t want to do this every time so it’s easier to put these into get/set functions:

function isAttribExist(tmpDeviceID,tmpAttributeName)
    boolReturn=0
    sqlCheck = "SELECT nDeviceAttributeID FROM DeviceAttribute WHERE (nDeviceID = " & tmpDeviceID & ") AND (sName = N'" & tmpAttributeName & "')"
    Set oRs1 = oDb.Execute(sqlCheck)
    if oRS1.EOF then
        boolReturn=0
    else
        boolReturn=1
    end if
    isAttribExist = boolReturn
end function

function updateAttribute(tmpDeviceID,tmpAttributeName,tmpValue)
    sqlQuery="UPDATE [WhatsUp].[dbo].[DeviceAttribute] SET sValue = '" & tmpValue & "' WHERE (nDeviceID = " & tmpDeviceID & ") AND (sName = N'" & tmpAttributeName & "')"
    context.logmessage sqlQuery
    oDb.Execute(sqlQuery)    
end function

function addNewAttribute (tmpDeviceID,tmpAttributeName,tmpValue)
    sqlQuery="INSERT INTO [WhatsUp].[dbo].[DeviceAttribute] (nDeviceID,sName,sValue) " & _
         "VALUES ('" & tmpDeviceID & "','" & tmpAttributeName & "','" & tmpValue & ")"
    context.logmessage sqlQuery
    oDb.Execute(sqlQuery)    
end function

function setAttribute(tmpDeviceID,tmpAttributeName,tmpValue)
    if isAttribExist(tmpDeviceID,tmpAttributeName) then
        updateAttribute tmpDeviceID,tmpAttributeName,tmpValue
    else
        addNewAttribute  tmpDeviceID,tmpAttributeName,tmpValue
    end if
end function

function getAttribute(tmpDeviceID,tmpAttributeName)
    strReturn=""
    sqlCheck = "SELECT sValue FROM DeviceAttribute WHERE (nDeviceID = " & tmpDeviceID & ") AND (sName = N'" & tmpAttributeName & "')"
    Set oRs1 = oDb.Execute(sqlCheck)
    if oRS1.EOF then
        strReturn=""
    else
        strReturn=oRs1("sValue")
    end if
    getAttribute = strReturn
end function

Get usage:

strResult=getAttribute(DeviceID,attribute name)

e.g.

strResult=getAttribute(100,”OS”)

Set usage:

setAttribute(DeviceID,attribute name,value to set)

e.g.

setAttribute(100,”OS”,”Windows Server 2003″)

Tagged , , , , , ,

Collecting disk usage data from UNC paths

If you’re not using windows or linux devices to present your CIF shares then collecting usage data can be quite tricky. We ran up against this recently while using EMC Celerra devices to present our shares.

The solution we came up with was to mount the UNC on the WhatsUp box, query the drive mount, then disconnect. As you can imagine this is quite costly and if you’re collecting from multiple CIFS shares the monitors can clash and try and use the same drive letter. To get around this we added some randomization and checking to see if a letter is free:

function random_driveletter()
	strReturn="T:"
	Randomize
	intRandom=(int(Rnd()*19))
	strReturn=CHR(70+intRandom)
	'context.logmessage "CHAR=" & strReturn
	random_driveletter=strReturn
end function

function driveexists(strtmpDrive)
	boolReturn=0
	Set objtmpFileSys = CreateObject("Scripting.FileSystemObject")
	If objtmpFileSys.DriveExists(strtmpDrive) Then
		boolReturn=1
		'context.logmessage "Drive is already in use."
	End If
	driveexists=boolReturn
end function

Drives in this case are chose from between E (ASCII character number 70) and Y (ASCII character 89). We can then cycle until we get a free letter. We’ve added in some extra checking if we cycle through too many times that will try and clear up all the drive letters so the script shouldn’t cycle through until the script times out:

numAttempts=0
do
	strDrive=random_driveletter() & ":"
	context.logmessage strDrive
	numAttempts = numAttempts+1
	if numAttempts > intCleanupThreshold then
		cleanupdriveletters()
	end if
loop while driveexists(strDrive)

The script uses the “DisplayName” field in the WhatsUp device to get the UNC path so you’ll need to setup a new device per share (or at least filesystem). To get the DisplayName field we query the WhatsUp database:

function getDisplayNamefromID(strtmpDeviceID)
	dim strReturn
	' Get the DB instance used by WhatsUp
	set objDatabase = Context.GetDB
	' Check it worked OK
	if "" = objDatabase then
		Context.SetResult  1, "Problem connecting to database"
	else
		' We need to find the reference used for this device in the PivotStatisticalMonitorTypeToDevice table first
		strQuery = "SELECT sDisplayName FROM  [WhatsUp].[dbo].[Device] where nDeviceID=" & strtmpDeviceID
		objResultSet =  objDatabase.Execute(strQuery)
		strReturn = objResultSet(0)
	end if
	getDisplayNamefromID=strReturn
end function

Then use

UNCpath=getDisplayNamefromID(Context.GetProperty("DeviceID"))

to get the path to use to map. This way we can create a single performance monitor script that is used on many shares. The advantage of this is that we can use it in Alert Center to create a single threshold configuration that includes all our CIFS shares.

Here’s the full script:

intCleanupThreshold=5

ipAddress=Context.GetProperty("Address")
UNCpath=getDisplayNamefromID(Context.GetProperty("DeviceID"))

' Get the Windows credentials for the device
strWindowsUsername = Context.GetProperty("CredWindows:DomainAndUserid")
strWindowsPassword = Context.GetProperty("CredWindows:Password")

strComputer="."
strDriveMap=UNCpath

'Timestamp
startTime = Timer()

numAttempts=0

do
	strDrive=random_driveletter() & ":"
	context.logmessage strDrive
	numAttempts = numAttempts+1
	if numAttempts > intCleanupThreshold then
		cleanupdriveletters()
	end if
loop while driveexists(strDrive)

context.logmessage strDrive & " " & strDriveMap & " took " & numAttempts & " attempts to get a free letter"

startMapTime = Timer()

Set objNetwork = CreateObject("WScript.Network")

numAttempts=0
do
	err.clear
	on error resume next
	objNetwork.MapNetworkDrive strDrive, strDriveMap,0,strWindowsUsername,strWindowsPassword
	tmpStatus=err.number
	if tmpStatus <> 0 then
		context.logmessage err.Description & " mapping drive " & strDrive & " to " & strDriveMap
		cleanupdriveletters()
	end if
	context.logmessage "err.num=" & tmpStatus
	numAttempts=numAttempts+1
	if numAttempts > intCleanupThreshold then exit do
loop while tmpStatus <> 0

endMapTime = Timer()
intMapDuration=int((endMapTime-startMapTime)*1000)
context.logmessage "Took " & intMapDuration & "ms to map " & strDrive & " to " & strDriveMap

Set objWMIService = GetObject("winmgmts:" _
    & "{impersonationLevel=impersonate}!\\" & strComputer & "\root\cimv2")
Set colDisks = objWMIService. _
    ExecQuery("Select * from Win32_MappedLogicalDisk  where Caption = """ & strDrive & """")

For Each objDisk In colDisks
	floatPercUsed=percentage_used(objDisk.Size,objDisk.FreeSpace)
	endTime=Timer()
	intDuration=int((endTime-startTime)*1000)
	context.setvalue floatPercUsed
Next

startMapTime = Timer()
objNetwork.RemoveNetworkDrive strDrive
endMapTime = Timer()
intMapDuration=int((endMapTime-startMapTime)*1000)
context.logmessage "Took " & intMapDuration & "ms to unmap " & strDrive & " from " & strDriveMap

function percentage_used(strDiskSize,strFreeSpace)
	floatReturn=0
	floatReturn=100-Round((strFreeSpace/strDiskSize)*100,1)
	percentage_used=floatReturn
end function

function random_driveletter()
	strReturn="T:"
	Randomize
	intRandom=(int(Rnd()*19))
	'context.logmessage intRandom

	strReturn=CHR(70+intRandom)
	'context.logmessage "CHAR=" & strReturn
	random_driveletter=strReturn
end function

function driveexists(strtmpDrive)
	boolReturn=0
	Set objtmpFileSys = CreateObject("Scripting.FileSystemObject")
	If objtmpFileSys.DriveExists(strtmpDrive) Then
		boolReturn=1
		'context.logmessage "Drive is already in use."
	End If 

	driveexists=boolReturn
end function

function cleanupdriveletters()
	context.logmessage "Cleaning up driveletters to free space"
	Set objtmpNetwork = CreateObject("WScript.Network")
	for i=70 to 89 step 1
		tmpDriveLetter=CHR(i) & ":"
		context.logmessage "Processing letter " & tmpDriveLetter
		on error resume next
		objtmpNetwork.RemoveNetworkDrive tmpDriveLetter
		if err.number then
			context.logmessage tmpDriveLetter & " (" & Replace(Replace(err.description, CHR(13),""),CHR(10),"") & ")"
			err.clear
		else
			context.logmessage "Removed " & tmpDriveLetter
		end if
	next
end function

function getDisplayNamefromID(strtmpDeviceID)
	dim strReturn

	' Get the DB instance used by WhatsUp
	set objDatabase = Context.GetDB

	' Check it worked OK
	if "" = objDatabase then
		Context.SetResult  1, "Problem connecting to database"
	else
		'context.logmessage "Connected to DB OK"

		' We need to find the reference used for this device in the PivotStatisticalMonitorTypeToDevice table first
		strQuery = "SELECT sDisplayName FROM  [WhatsUp].[dbo].[Device] where nDeviceID=" & strtmpDeviceID
		objResultSet =  objDatabase.Execute(strQuery)
		strReturn = objResultSet(0)
	end if
	getDisplayNamefromID=strReturn
end function
Tagged , , , ,

Using command-line tools with WhatsUp Active and Performance monitors

Sometimes you just can’t get the information you’re looking for from SNMP or WMI and need to use proprietary command-line tools.

Here’s a way using VBScript to run those command line tools and get the information from them into WhatsUp.

This script uses the “exec” method to launch navicli to collect the utilization on a Clariion storage processor.

'The command-line will run on the local server
strComputer = "127.0.0.1"

strOptions="getcache -busy"
intCommandTimeoutinSecs=3

'This is the address of the EMC SAN device
strEMCAddress = Context.GetProperty("Address")

'This is the path to the navi CLI on the monitoring server
strNaviCLIbin="""C:\Program Files\EMC\Navisphere CLI\NaviSECCli.exe"""

' Use the Windows credentials for the command line from within WhatsUp
strUsername = Context.GetProperty("CredWindows:DomainAndUserid")
strPassword = Context.GetProperty("CredWindows:Password")

'Chop off the domain from the username
arrtmpUsername=split(strUsername,"\")
strUsername=arrtmpUsername(1)

'The command to send
strCommand= strNaviCLIbin & " -t " & intCommandTimeoutinSecs & " -User " & strUsername & " -Password " & strPassword & " -Scope 0 -Address " & strEMCAddress & " " & strOptions

'Timestamp before starting the script
startTime = Timer()

'Run the command to collect
strRawOutput=runCommand(strCommand)

'Create an array from the data returned so we can pick out the value
arrRawOutput=split(strRawOutput," ")

'Pick out the value from the text returned (chomping off the carriage return)
strResult=replace(arrRawOutput(ubound(arrRawOutput)),vbcrlf,"")

context.logmessage "Value=" & strResult

'Timestamp at the end of the script
endTime = Timer()

' Work out how long it took
Duration = Int((endTime-startTime)*1000)

context.logmessage "Got value " & strResult & " (script took=" & Duration & "ms)"

'Set the result to graph
Context.SetValue strResult

function runCommand(strCommand)

	Set objShell = CreateObject("wscript.Shell")
	context.logmessage strCommand
	Set objExec = objShell.Exec (strCommand)

	Do Until objExec.Status
		 sleep 1
	Loop 

	'context.logmessage objExec.StdOut.ReadAll()
	runCommand=objExec.StdOut.ReadAll()
end function

function sleep(intseconds)
	intstarttime = timer()
	while timer() < intstarttime+intseconds
		'.
	wend
end function

We’ve had to parse the output a little to get the value from the text that the command-line returned.

Tagged , , , ,

APC UPS run time remaining

It’s useful to plot (or alert on) the amount of battery left on your APC UPS. Here’s a script that uses SNMP and parses the string output to work out how many minutes remain on the battery.

This one is a performance monitor (since it sets the “context.SetValue”) but you should easily be able to tweak it as an active monitor.

' Contains run time statistics for APC UPS
runtimeTable =  "1.3.6.1.4.1.318.1.1.1.2.2.3.0"

'Initialize SNMP
set objSNMPReq = CreateObject("CoreAsp.SnmpRqst")
strDeviceID = Context.GetProperty("DeviceID")
set objSNMPInit = objSNMPReq.Initialize(strDeviceID)

if objSNMPInit.Failed then
              	Context.logmessage "Failed to initialize SNMP (" & objSNMPInit.GetErrorMsg & ")"
else
	strRunTimeRemaining=get_SNMPget(runtimeTable)
	'Result has the form "0days 00:43:00.00"
	floatRunTimeRemaining=getHoursfromTimeticks(strRunTimeRemaining)

	context.logmessage "Runtime = " & floatRunTimeRemaining
	Context.SetValue floatRunTimeRemaining
end if

function getHoursfromTimeticks(strtmpTimeticks)
	intReturn=0	
	intDays=left(strtmpTimeticks,instr(strtmpTimeticks,"day")-1)
	arrtmpTime=split(right(strtmpTimeTicks,(len(strtmpTimeTicks) - instr(strtmpTimeTicks,CHR(32)))),":")
	intHours=int(arrtmpTime(0))
	intMinutes=int(arrtmpTime(1))
	intSeconds=int(arrtmpTime(2))
	context.logmessage "Days=" & intDays & ",hours=" & intHours & ",mins=" & intMinutes & ",Secs=" & intSeconds

	floatRunTimeinMinutes=(intDays*24*60)+(intHours*60)+(intMinutes)
	floatReturn=floatRunTimeinMinutes
	getHoursfromTimeticks=floatReturn
end function

function get_SNMPget(strtmpOID)
	set objtmpSNMPResult = objSNMPReq.Get(strtmpOID)
	strtmpValue=objtmpSNMPResult.GetPayload
	context.logmessage strtmpOID & " returned value " & strtmpValue
	get_SNMPget=strtmpValue
end function
Tagged , ,

Recording how long VBscripts take to run

Quite often it’s useful to have some idea how long scripts are taking to run. A simple way to do that is to use the Timer() function in VBscript.

Near the start of your script record the current value returned by Timer():

'Timestamp at the start of the script
startTime = Timer()

and then near the end take it again:

'Timestamp at the end of the script
endTime = Timer()

You can then work out how long the script took to run between these two points is milliseconds by using:

' Work out how long it took
Duration = Int((endTime-startTime)*1000)

which of course you can then output on completion:

context.SetResult 0,"Completed Successfully. (Script took " & Duration & " ms)"
Tagged ,