Splunk Search

How to gather Results based on various variables

Contributor

Still trying to brush the rust off my fingers, I have this search:

index=nitros_servers sourcetype=_json OR sourcetype=xs_json host=isp** "hdr.appName"="*"
| fillnull value="NA" hdr.macaddress
| bucket _time span=1d
| eval Date=strftime(_time,"%m-%d-%Y")
| stats dc(hdr.appVersion) as version_conflict_count values(hdr.appVersion) as Versions values(Date) as Date values(hdr.macaddress) as macaddress by hdr.locId hdr.appName _time
| where version_conflict_count > 1

| stats values(Versions) as Versions count as Days values(Date) as Date values(macaddress) as macaddress by hdr.locId hdr.appName
| where Days> 1
| sort Days desc
| table hdr.locId macaddress hdr.appName Versions Date

alt text

The MAC address list that is being populated is all of the MACS in the specific location but I only want the MACS that are corisponding with the Lower Version number. So in the results there are always at least two "versions" I only want the MACS of the lower of the two versions to be populated in my results, any suggestions on how to accomplish this? The numbers are always different so I can't hard code numbers in, nor do I think that is a good idea. I was thinking a comparision with just greater than/less than but im unsure how this would be put in.

Thank you.

0 Karma

SplunkTrust
SplunkTrust

Here's your base search...

index=nitros_servers sourcetype=_json OR sourcetype=xs_json host=isp* "hdr.appName"="" 
| fillnull value="NA" hdr.macaddress 
| bucket _time span=1d 

This section converts the hdr.appVersion to a format that can be directly compared

| eval appVersion=hdr.appVersion
| rex field=appVersion max_match=4 "((?<vnode>\d*)\.?)" 
| eval vnode2=tostring(tonumber(mvindex(vnode,0))+4096,"hex") 
| eval vnode2=if(mvcount(vnode)<=1,vnode2,mvappend(vnode2,tostring(tonumber(mvindex(vnode,1))+4096,"hex")))
| eval vnode2=if(mvcount(vnode)<=2,vnode2,mvappend(vnode2,tostring(tonumber(mvindex(vnode,2))+4096,"hex")))
| eval vnode2=if(mvcount(vnode)<=3,vnode2,mvappend(vnode2,tostring(tonumber(mvindex(vnode,3))+4096,"hex")))
| nomv vnode2 
| rex mode=sed field=vnode2 "s/\s/_/g" 
| eval appVersion=vnode2." ".myversion

This section calculates what the max appVersion was on that date at that location, and eliminates all records with the highest version, thus also eliminating any locations without conflict on that day. Note that version_conflict_count is the total number of distinct appVersions on that day at that location that are NOT the highest appVersion.

| eventstats max(appVersion) as maxVersion by hdr.locId hdr.appName _time 
| where appVersion!=maxVersion
| stats dc(appVersion) as version_conflict_count, max(maxVersion) as maxVersion, list(appVersion) as appVersion, list(hdr.macaddress) as macaddress by hdr.locId hdr.appName _time 

Now we format and list the Dates, the macaddresses and appVersions in play at a location for an app, then get rid of the hex-sort-prefix on the appVersion. appVersion will be in ascending order by version, and version will be presented conventionally.

| eval Date=strftime(_time,"%Y-%m-%d")
| stats values(appVersion) as Versions, count as Days, values(Date) as Date, values(macaddress) as macaddress by hdr.locId hdr.appName 
| rex mode=sed field=appVersion "s/(0x[0-9a-fA-F]{4}_?)+\s+?//g"

and present the results

| sort Days desc 
| table hdr.locId macaddress hdr.appName Versions Date

However, the max appVersion in play at a particular location may change over time, so I'd suggest something like this to give you all conflicts broken out by what they were conflicting against, and when.

index=nitros_servers sourcetype=_json OR sourcetype=xs_json host=isp* "hdr.appName"="" 
| fillnull value="NA" hdr.macaddress 
| bucket _time span=1d 
| eval appVersion=hdr.appVersion
| rex field=appVersion max_match=4 "((?<vnode>\d*)\.?)" 
| eval vnode2=tostring(tonumber(mvindex(vnode,0))+4096,"hex") 
| eval vnode2=if(mvcount(vnode)<=1,vnode2,mvappend(vnode2,tostring(tonumber(mvindex(vnode,1))+4096,"hex")))
| eval vnode2=if(mvcount(vnode)<=2,vnode2,mvappend(vnode2,tostring(tonumber(mvindex(vnode,2))+4096,"hex")))
| eval vnode2=if(mvcount(vnode)<=3,vnode2,mvappend(vnode2,tostring(tonumber(mvindex(vnode,3))+4096,"hex")))
| nomv vnode2 
| rex mode=sed field=vnode2 "s/\s/_/g" 
| eval appVersion=vnode2." ".myversion
| eventstats max(appVersion) as maxVersion by hdr.locId hdr.appName _time 
| where appVersion!=maxVersion
| eventstats max(appVersion) as maxVersionApp by hdr.locId hdr.appName 
| stats dc(appVersion) as version_conflict_count, max(maxVersion) as maxVersion, list(appVersion) as appVersion, list(hdr.macaddress) as macaddress by hdr.locId hdr.appName _time 
| eval Date=strftime(_time,"%Y-%m-%d")
| stats values(appVersion) as Versions, count as Days, values(Date) as Date, max(Date) as LastDate, values(macaddress) as macaddress by hdr.locId hdr.appName maxVersion
| eventstats sum(Days) as totalDays by hdr.locId hdr.appName
| rex mode=sed field=appVersion "s/(0x[0-9a-fA-F]{4}_?)+\s+?//g"
| sort 0 -totalDays -Lastdate
| table hdr.locId macaddress hdr.appName Versions Date Days totalDays 

You could also include something like this after the second eventstats, if you only wanted to see conflicts against the most recent appVersion in a location.

| where maxVersion=maxVersionApp

Here's a chunk of sample code for you. (it has already been incorporated above.) It's inelegant, but it will convert the version numbers (up to 4 nodes) to a string that can be directly compared. The number 4096 is being added to make sure the hex translations of the node numbers all have the same length. (The code will fail if a version/level/node goes over 61440.)

| makeresults | eval myversion="16.10.0.7 17.1.0.8" |makemv myversion| mvexpand myversion
| rex field=myversion max_match=4 "((?<versionnode>\d*)\.?)" 
| eval versionnode2=tostring(tonumber(mvindex(versionnode,0))+4096,"hex") 
| eval versionnode2=if(mvcount(versionnode)<=1,versionnode2,mvappend(versionnode2,tostring(tonumber(mvindex(versionnode,1))+4096,"hex")))
| eval versionnode2=if(mvcount(versionnode)<=2,versionnode2,mvappend(versionnode2,tostring(tonumber(mvindex(versionnode,2))+4096,"hex")))
| eval versionnode2=if(mvcount(versionnode)<=3,versionnode2,mvappend(versionnode2,tostring(tonumber(mvindex(versionnode,3))+4096,"hex")))
| nomv versionnode2
0 Karma

Explorer

Haven't tried this out yet, but this (https://answers.splunk.com/answers/434960/how-to-edit-my-search-to-compare-software-version.html) looks like a good place. Have it break out the version number into elements and then compare to find your high version number as a sub search and then search for anything that isn't that high number and return the results and stats like you are now.

0 Karma

Contributor

So I tried using | eval result=substr(Versions, 0, 1)

to grab the first two characters of Versions but I am getting nothing in the result column that I added in

0 Karma

SplunkTrust
SplunkTrust

To answer this, we need to know the format of the underlying data. I do not see how you are determining, in that search, that a version conflict exists.

Also, please re-post the code and mark it with the code button (101 010) so that html-like items are not eaten by the web interface. There is probably a * somewhere in "hdr.appName"="" but I don't know where.

Programming note - to directly compare the version number, you are going to have to translate it to a fixed-length format, otherwise 17.2.x.x will be read as greater than 17.11.x.x

0 Karma

Contributor

Any solutions for this? I am at a loss here unfortunately

0 Karma
State of Splunk Careers

Access the Splunk Careers Report to see real data that shows how Splunk mastery increases your value and job satisfaction.

Find out what your skills are worth!