Mantis360 Public API

Mantis360 · API v1 · Base URL https://api.360.mantisops.net

The Mantis360 Public API is a simple REST/JSON interface for reading your discovered assets, vulnerability findings, and sites programmatically — for dashboards, SIEM/ticketing integrations, and reporting. Every request is authenticated with an API key and scoped to the tenant that issued it.

Overview

Authentication

Create keys in the Customer Portal (portal.mantisops.net) → API keys → Create API key. Account owners and admins can create keys. Set Mantis360 to Read or Write (and the other products to None unless the integration needs them), choose any limits (below), check the Review step, and create the key. Confirming it's you is required. If you grant more than one product, you get one key per product.

The key is shown once. Copy it, then click Run test from here or run the curl command shown to check it works. It can't be shown again. If a key is lost or exposed, revoke it and create a new one. Mantis360 keys begin with m3_live_.

Keys are created only in the Customer Portal. In Mantis360, Settings → API keys shows your existing keys and their limits, and you can revoke a key there.

Pass the key in the Authorization header as a Bearer token:

curl https://api.360.mantisops.net/public/v1/assets \ -H "Authorization: Bearer m3_live_xxxxxxxxxxxxxxxxxxxxxxxx"

Verify a key and see its scopes with the ping endpoint:

curl https://api.360.mantisops.net/public/v1/ping \ -H "Authorization: Bearer m3_live_..." { "ok": true, "product": "360", "version": "v1", "tenant": "t_abc123", "scopes": ["read"] }
⚠
Keys are stored only as a hash. MantisOps cannot recover a key for you — if it's lost, revoke it and create a new one. Treat keys like passwords and never commit them to source control.

Key limits

You set these when you create a key in the Customer Portal. To change them later, choose Edit limits… in the key's row menu: you can change the companies, allowed IP addresses and expiry; the key itself stays the same. The name and permissions can't be changed: create a new key instead.

LimitWhat it does
Expires30 days, 90 days (the default), 1 year, a date up to 3 years away, or Never. From the expiry time the key is refused with 401 { "error": "API key expired" }. The key's creator and the account's owners and admins get a reminder email 14 days and 3 days before it expires, and one more after it expires.
Allowed IP addressesUp to 50 IPv4 or IPv6 addresses or CIDR ranges. A call from any other address is refused with 403 { "error": "API key not allowed from this IP address" }.
CompaniesAll companies or Only some. A limited key only sees and changes those companies' assets, findings, sites, probes and scans: lists are filtered, and a single item outside them returns 404. ping also returns the key's allowedCompanies.

The key list in the Portal shows when each key was last used and from which IP address, and warns about keys that have expired, expire within 14 days or have never been used.

Scopes

Each key is granted one of two scopes when created. In the Customer Portal, Read gives read and Write gives read & write.

ScopeGrants
readAll GET endpoints — list and read assets, findings, and sites.
read & writeEverything read allows, plus write endpoints — currently POST /public/v1/findings/{id}/status. More write endpoints are added over time.

A request to a write endpoint with a read-only key returns 403. Grant the narrowest scope an integration needs.

ℹ
Rate limit: 120 requests / 60 s per key (429 + Retry-After when exceeded). CORS is enabled (Access-Control-Allow-Origin: *) so browser apps can call the API with a key.
ℹ
Pagination: list endpoints accept ?limit=N&offset=M (limit capped at 1000). Omit limit to receive the full list (default — unchanged behavior). List responses include limit, offset, hasMore, and (on most endpoints) total alongside the items — page by incrementing offset until hasMore is false.

Errors

Errors use standard HTTP status codes and a JSON body of the form { "error": "message" }.

StatusMeaning
400Malformed request (e.g. a required field is missing).
401Missing, malformed, revoked, or unknown API key: { "error": "Invalid or missing API key" }.
401The key has expired: { "error": "API key expired" }. Give it a later expiry with Edit limits in the Portal, or create a new key.
403The key is valid but lacks the required scope: { "error": "Insufficient scope: 'write' required" }.
403The call came from an address that isn't on the key's allowed IP list: { "error": "API key not allowed from this IP address" }.
404The resource (e.g. an asset) was not found, or it's outside the companies the key is limited to.
429Rate limit exceeded (120 requests / 60 s per key). Wait for the number of seconds in Retry-After.

Endpoints

GET/public/v1/pingread

Verify an API key and return the tenant it belongs to plus its scopes. Useful as a connection test.

curl https://api.360.mantisops.net/public/v1/ping \ -H "Authorization: Bearer m3_live_..." 200 OK { "ok": true, "product": "360", "version": "v1", "tenant": "t_abc123", "scopes": ["read"] }
GET/public/v1/assetsread

List every discovered asset in your tenant. Returns an array of asset objects and a total count. Add ?siteId=<id> to return only assets in one site.

curl "https://api.360.mantisops.net/public/v1/assets?siteId=site_1a2b" \ -H "Authorization: Bearer m3_live_..." 200 OK { "count": 2, "assets": [ { "id": "as_9f2c...", "ip": "10.0.1.14", "hostname": "win-svr-01", "os": "Windows Server 2022", "deviceType": "server", "openPorts": [22, 443, 3389], "macAddress": "00:1a:2b:...", "riskScore": 87, "siteId": "site_1a2b", "probeId": "pr_77...", "agentInstalled": true, "agentVersion": "1.3.51", "firstSeenAt": 1751200000000, "lastSeenAt": 1751990400000, "lastScannedAt": 1751988000000 } ] }
GET/public/v1/assets/{id}read

Fetch a single asset by its id. Returns 404 if no such asset exists in your tenant.

curl https://api.360.mantisops.net/public/v1/assets/as_9f2c... \ -H "Authorization: Bearer m3_live_..." 200 OK { "id": "as_9f2c...", "ip": "10.0.1.14", "hostname": "win-svr-01", "os": "Windows Server 2022", "deviceType": "server", "openPorts": [22, 443, 3389], "riskScore": 87, "siteId": "site_1a2b" }
GET/public/v1/findingsread

List open vulnerability findings (status open or in_progress), most severe first. Returns an array of finding objects and a total count. Add ?siteId=<id> to scope to one site.

curl https://api.360.mantisops.net/public/v1/findings \ -H "Authorization: Bearer m3_live_..." 200 OK { "count": 1, "findings": [ { "id": "vf_5d1e...", "assetIp": "10.0.1.14", "assetId": "as_9f2c...", "hostname": "win-svr-01", "port": 443, "service": "https", "title": "TLS 1.0 enabled", "cve": "CVE-2011-3389", "severity": "HIGH", "cvssScore": 7.4, "epssScore": 0.42, "remediationStatus": "open", "firstSeenAt": 1751200000000, "lastSeenAt": 1751990400000, "siteId": "site_1a2b" } ] }
GET/public/v1/sitesread

List every site in your tenant. Use a site's id to filter the assets and findings endpoints.

curl https://api.360.mantisops.net/public/v1/sites \ -H "Authorization: Bearer m3_live_..." 200 OK { "count": 1, "sites": [ { "id": "site_1a2b", "name": "HQ Network", "createdAt": 1751000000000 } ] }
GET/public/v1/probesread

List your probes with online status. Fields: id, name, status, online, lastSeenAt, companyId. A probe is online if it checked in within the last 10 minutes.

curl https://api.360.mantisops.net/public/v1/probes \ -H "Authorization: Bearer m3_live_..." 200 OK { "count": 1, "probes": [ { "id": "pr_77...", "name": "HQ probe", "status": "ok", "online": true, "lastSeenAt": 1751990400000, "companyId": null } ] }
GET/public/v1/identity-findingsread

List open Active Directory / Entra identity-posture findings, most severe first. Fields: id, source, targetType, targetName, category, severity, title, remediation, siteId, status, firstSeenAt, lastSeenAt.

curl https://api.360.mantisops.net/public/v1/identity-findings \ -H "Authorization: Bearer m3_live_..." 200 OK { "count": 1, "findings": [ { "id": "if_...", "source": "ad", "targetName": "svc-backup", "category": "kerberoast", "severity": "HIGH", "title": "Kerberoastable service account", "status": "open" } ] }
GET/public/v1/complianceread

List recent STIG/CIS compliance audit runs, most recent first. Fields: id, agentId, hostname, bundleId, bundleName, runAt, scorePct, satisfied, failed, notApplicable, notCheckable, unknown.

curl https://api.360.mantisops.net/public/v1/compliance \ -H "Authorization: Bearer m3_live_..." 200 OK { "count": 1, "runs": [ { "id": "run_...", "agentId": "as_9f2c...", "hostname": "win-svr-01", "bundleName": "CIS Windows Server 2022", "runAt": 1751988000000, "scorePct": 82, "satisfied": 210, "failed": 46 } ] }
GET/public/v1/scansread

List scheduled scans with their last/next run. Fields: id, siteId, probeId, scanType, schedule, targets, enabled, lastRunAt, nextRunAt, lastAttemptAt, lastError, timezone, createdAt.

curl https://api.360.mantisops.net/public/v1/scans \ -H "Authorization: Bearer m3_live_..." 200 OK { "count": 1, "scans": [ { "id": "sc_...", "siteId": "site_1a2b", "probeId": "pr_77...", "scanType": "netscan", "schedule": "0 2 * * *", "enabled": true, "lastRunAt": 1751904000000, "nextRunAt": 1751990400000, "lastError": null } ] }
POST/public/v1/findings/{id}/statuswrite

Set a finding's remediation status. Requires a read & write key. Body: { "status": "open" | "in_progress" | "resolved" | "accepted" | "false_positive", "notes"?: "…" }. Returns 404 if no such finding exists in your tenant.

curl -X POST https://api.360.mantisops.net/public/v1/findings/vf_.../status \ -H "Authorization: Bearer m3_live_..." \ -H "Content-Type: application/json" \ -d '{ "status": "accepted", "notes": "Risk accepted — legacy appliance" }' 200 OK { "ok": true, "id": "vf_...", "status": "accepted" }

Asset object

Fields returned for an asset. Optional fields are omitted when not available for a device.

FieldTypeDescription
idstringUnique asset identifier.
ipstringPrimary IP address (unique per tenant).
hostnamestringResolved / reported hostname.
osstringDetected operating system.
deviceTypestringClassified device type (e.g. server, workstation, router).
openPortsnumber[]Open TCP ports.
udpPortsnumber[]Open UDP ports, when scanned.
macAddressstringPrimary MAC address, when discoverable.
tagsstring[]Operator-assigned tags.
riskScorenumberComposite risk score (higher = more risk).
siteId / probeId / companyIdstringOrganizational placement + the probe that discovered it.
agentInstalledbooleanWhether a Mantis360 agent is present on the host.
agentVersionstringInstalled agent version, if any.
agentLastSeenAtnumberAgent's last check-in (Unix epoch ms).
firstSeenAt / lastSeenAtnumberFirst and most-recent discovery (Unix epoch ms).
lastScannedAtnumberLast full scan of the asset (Unix epoch ms).

Finding object

Fields returned for a vulnerability finding.

FieldTypeDescription
idstringUnique finding identifier.
assetIpstringIP of the affected asset.
assetIdstringID of the affected asset, when it still resolves.
hostnamestringHostname of the affected asset.
port / servicenumber / stringAffected port and detected service.
titlestringHuman-readable finding title.
cvestringAssociated CVE identifier, when applicable.
severitystringCRITICAL, HIGH, MEDIUM, LOW, or INFO.
cvssScorenumberCVSS base score (0–10).
epssScorenumberEPSS exploit-probability score (0–1), when available.
remediationstringSuggested remediation text.
remediationStatusstringopen or in_progress (resolved findings are not returned).
firstSeenAt / lastSeenAtnumberFirst and most-recent detection (Unix epoch ms).
siteIdstringSite the finding belongs to.
💡
More endpoints are on the roadmap. Need one that isn't here yet? Let us know.