Retrieve findings
This guide explains how to query, filter, paginate, and export security findings discovered by S4E scans.
Prerequisites
- A valid API token with
findings:readpermissions. - At least one completed scan that produced findings.
Endpoint
Required Headers
| Header | Value | Description |
|---|---|---|
| Authorization | Bearer <token> |
Your API authentication token. |
| Accept | application/json |
Expected response format. |
Query Parameters
All parameters are optional. When omitted, the endpoint returns the most recent findings across all assets.
| Parameter | Type | Default | Description |
|---|---|---|---|
| asset_id | string | - | Filter findings to a specific asset UUID. |
| severity | string | - | Comma-separated list: critical, high, medium, low, info. |
| status | string | - | Finding status: open, resolved, accepted, false_positive. |
| scan_id | string | - | Return only findings from a specific scan run. |
| page | integer | 1 | Page number (1-based). |
| per_page | integer | 25 | Results per page. Maximum 100. |
| sort_by | string | severity |
Sort field: severity, cvss, created_at, title. |
| sort_order | string | desc |
Sort direction: asc or desc. |
Note
The severity parameter accepts multiple values separated by commas. For example, severity=critical,high returns only critical and high findings.
Response Format
A successful request returns 200 OK with a JSON body:
{
"findings": [
{
"id": "f-00112233-4455-6677-8899-aabbccddeeff",
"title": "SQL Injection in login form",
"severity": "critical",
"cvss": 9.8,
"status": "open",
"description": "The login endpoint is vulnerable to SQL injection through the username parameter.",
"remediation": "Use parameterized queries or an ORM to construct SQL statements.",
"asset": {
"id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
"name": "app.example.com",
"type": "web_application"
},
"scan_id": "s-aabbccdd-1122-3344-5566-778899001122",
"created_at": "2026-04-27T10:15:00Z",
"updated_at": "2026-04-27T10:15:00Z",
"references": [
"https://cwe.mitre.org/data/definitions/89.html"
]
}
],
"pagination": {
"page": 1,
"per_page": 25,
"total_items": 142,
"total_pages": 6
}
}
Finding Object Fields
| Field | Type | Description |
|---|---|---|
| id | string | Unique finding identifier. |
| title | string | Human-readable finding title. |
| severity | string | One of critical, high, medium, low, info. |
| cvss | float | CVSS v3.1 base score (0.0 -- 10.0). |
| status | string | Current status of the finding. |
| description | string | Detailed description of the vulnerability. |
| remediation | string | Recommended fix or mitigation. |
| asset | object | Embedded asset summary (id, name, type). |
| scan_id | string | The scan that discovered this finding. |
| created_at | string | ISO 8601 timestamp when the finding was first detected. |
| updated_at | string | ISO 8601 timestamp of the last status change. |
| references | string[] | External reference URLs (CWE, CVE, vendor advisories). |
Pagination Headers
In addition to the pagination object in the response body, the API sets the following response headers for convenience:
| Header | Example | Description |
|---|---|---|
| X-Total-Count | 142 | Total number of matching items. |
| X-Total-Pages | 6 | Total number of pages. |
| X-Current-Page | 1 | Current page number. |
| X-Per-Page | 25 | Items returned per page. |
Filtering by Severity and Status
Combine query parameters to narrow results. Filters are applied with AND logic.
This returns all open findings with critical or high severity, sorted by CVSS score in descending order.
Warning
Requesting large result sets without filters can be slow and may trigger rate limiting. Always scope queries to a specific asset, scan, or severity range when possible.
Exporting Findings
To export findings as a downloadable file, append the export query parameter:
Supported export formats:
| Format | Content-Type | Description |
|---|---|---|
| csv | text/csv |
Comma-separated values. |
| json | application/json |
Full JSON array of finding objects. |
application/pdf |
Formatted PDF report. |
Tip
The PDF export includes executive summary charts and is suitable for sharing with non-technical stakeholders.
Examples
curl
# Retrieve critical and high findings for a specific asset
curl -s "https://api.s4e.io/api/findings?asset_id=a1b2c3d4-e5f6-7890-abcd-ef1234567890&severity=critical,high&status=open&page=1&per_page=50" \
-H "Authorization: Bearer $S4E_API_TOKEN" \
-H "Accept: application/json" | python3 -m json.tool
# Export findings as CSV
curl -s "https://api.s4e.io/api/findings?asset_id=a1b2c3d4-e5f6-7890-abcd-ef1234567890&export=csv" \
-H "Authorization: Bearer $S4E_API_TOKEN" \
-o findings.csv
Python
import requests
BASE_URL = "https://api.s4e.io"
HEADERS = {
"Authorization": "Bearer <your-token>",
"Accept": "application/json",
}
params = {
"asset_id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
"severity": "critical,high",
"status": "open",
"page": 1,
"per_page": 50,
"sort_by": "cvss",
"sort_order": "desc",
}
all_findings = []
while True:
resp = requests.get(f"{BASE_URL}/api/findings", params=params, headers=HEADERS)
resp.raise_for_status()
data = resp.json()
all_findings.extend(data["findings"])
pagination = data["pagination"]
if pagination["page"] >= pagination["total_pages"]:
break
params["page"] += 1
print(f"Retrieved {len(all_findings)} findings in total.")
for finding in all_findings:
print(f"[{finding['severity'].upper()}] {finding['title']} (CVSS {finding['cvss']})")
Note
The Python example above iterates through all pages automatically. For very large result sets, consider streaming results or using the CSV export endpoint instead.