Playing with Tenable.sc Analysis endpoint

Playing with Tenable.sc Analysis endpoint

Today we are going to play with the analysis API endpoint of Tenable.sc using filters directly, no pre-saved queries. That gives us the same flexibility as working on the GUI.

GUI

The tricky part is getting the structure of the requests right; I’ll give a detailed explanation of how to do it in PowerShell so you don’t have to suffer yourself πŸ™‚

As usual, I’m going to use PowerShell for the whole process.

FILTERS

To build the request, first we build the filters object -where we actually define which data we want to obtain in our request, which it has to be an array of hash tables - dictionaries. We need 1 dictionary per filter, with 3 keys - which are case sensitive.

  1. operator: =, >, <. >=, <=
  2. value: actual value to filter by
  3. filterName: one of the filters available in analysis endpoint to base the search on.

Some of the most useful filters are: cveID, cvssV3BaseScore, dnsName, exploitAvailable, familyID, firstSeen, ip, lastSeen, mitigatedStatus, patchPublished, pluginID, pluginName, pluginText, pluginType, port, protocol, repositoryIDs, severity, tcpport, udpport, ExploitAvailable (true or false), severity [0(Info), 1(low), 2(medium), 3(high), 4(critical)]

Example

Filter example to get all vulnerabilities seen in the last seven days with severity critical and exploits available:

$filters = @(

    @{"filterName"="lastSeen"; "operator"="="; "value"="0:7"},
    @{"filterName"="severity"; "operator"="="; "value"="4"},
    @{"filterName"="exploitAvailable"; "operator"="="; "value"="true"}

)

This would be equivalent to this in the GUI:

Filters

QUERY

We have a filter, let’s do the query now. The query is a hash table or dictionary with the following keys:

  1. tool: this is the view in the Analysis tab. The one with more information is vulndetails

This is the complete list of tools: cceipdetail, cveipdetail, iavmipdetail, iplist, listmailclients, listservices, listos, listsoftware, listsshservers, listvuln, listwebclients, listwebservers, sumasset, sumcce, sumclassa, sumclassb, sumclassc, sumcve, sumdnsname, sumfamily, sumiavm, sumid, sumip, summsbulletin, sumprotocol, sumremediation, sumseverity, sumuserresponsibility, sumport, trend, vulndetails, vulnipdetail, vulnipsummary

And these are the ones I most use: iplist, vulndetails(Vulnerability Detail List ), vulnipsummary, listvuln(Vulnerability List), sumid(Vulnerability Summary)

  1. sourceType: cumulative or patched - Optional, patched means mitigated database.
  2. type: Set always to vuln
  3. createdTime, modifiedTime: Set always to 0
  4. name, description, context: can be set to an empty string
  5. sortField: Optional, which field you’d like to sort output
  6. startOffset, endOffset: number of records to retrieve from the total that match the filters, if you want all results use something like 0 and 9999
  7. filters: here goes the object we created before.

Example

Example query to get the vulnerabilities matching our filter from avobe: last 7 days, critical, exploit available.

# We use the 'vulndetails' tool to get the most data back
$query = @{"tool"="vulndetails";
            "createdTime"=0;
            "modifiedTime"=0;
            "name"="";
            "description"="";
            "type"="vuln";
            "sortDir"="desc";
            "context"="";
            "startOffset"=0;
            "endOffset"=5000;
            "sortField"="severity";
            "filters"=$filters
}

BODY

We have the query with the filter set, next step is the body for the POST request. This is another hash table with following keys:

  1. sourceType: cumulative or patched
  2. type: in our case alway vuln
  3. sortDir: asc or desc - Not mandatory
  4. sortField: any valid field returned in results of query ( i.e. severity) - Not necessary but if present must be accompanied of sortDir

Then we have to convert to JSON to send to the API endpoint.

Example

Example of body to make the request with the query we just built

$body = @{"sourceType"="cumulative";"type"="vuln";"query"=$query} | ConvertTo-Json -Compress -Depth 5

REQUEST

We have the body, let’s make the actual request. For the login process details, refer to previous post about the topic

$scURL = 'https://192.168.5.12'
$accessKey = $env:TENABLE_ACCESS
$secretKey = $env:TENABLE_SECRET

#request headers
$headers = @{}
$headers.Add("x-apikey", "accessKey=$accessKey;secretKey=$secretKey")

# request
$request = Invoke-RestMethod -Uri $scURL/rest/analysis -Method Post -Headers $headers -Body $body -UseBasicParsing | select -ExpandProperty "response" | select -ExpandProperty "results"

And we can see the contents of the output in one of the records retrieved:

Output

Conclusion

Now we can convert the output to CSV or any other format to process the data. We can play with the filters as well to obtain any data as we would in the GUI; I hope you found this useful πŸ™‚.

For a practical example of using the analysis endpoint, you can see how to find which known exploited vulnerabilities - as provided by CISA - are in your scan data following this post

tenable  api 

See also