Skip to main content
GET
/
api
/
scan
/
{id}
Get Scan Status
curl --request GET \
  --url https://api.example.com/api/scan/{id}
{
  "id": "<string>",
  "status": "<string>",
  "violation_count": 123,
  "compliance_score": 123,
  "rules_processed": 123,
  "rules_total": 123,
  "created_at": "<string>",
  "completed_at": "<string>",
  "audit_name": "<string>",
  "record_count": 123,
  "policy_id": "<string>",
  "upload_id": "<string>",
  "mapping_id": "<string>",
  "audit_id": "<string>",
  "mapping_config": {},
  "temporal_scale": "<string>",
  "score_history": [
    {
      "score": 123,
      "timestamp": "<string>",
      "action": "<string>",
      "violation_id": "<string>"
    }
  ],
  "delta": {
    "new_count": 123,
    "resolved_count": 123,
    "unchanged_count": 123,
    "previous_scan_id": "<string>",
    "previous_violation_count": 123
  }
}

Overview

Retrieve the current status, progress, and results of a compliance scan. Use this endpoint to poll for completion after triggering a scan via /api/scan/run. Includes delta analysis comparing the current scan with the previous scan for the same policy, showing new, resolved, and unchanged violations.

Path Parameters

id
string
required
The unique scan ID returned from /api/scan/run

Response

id
string
required
The scan’s unique identifier
status
string
required
Current scan status. Possible values:
  • pending - Scan is queued
  • running - Scan is in progress
  • completed - Scan finished successfully
  • failed - Scan encountered an error
violation_count
number
required
Total number of violations detected. Returns 0 for in-progress scans
compliance_score
number
required
Compliance score from 0-100, where 100 is perfect compliance. Returns 0 for in-progress scans
rules_processed
number
required
Number of rules completed. Equals rules_total when status is completed
rules_total
number
required
Total number of rules in the policy
created_at
string
required
ISO 8601 timestamp when the scan was created
completed_at
string
ISO 8601 timestamp when the scan completed. null for in-progress scans
audit_name
string
Human-readable audit name if provided during scan creation
record_count
number
required
Number of records processed in the scan (up to 50,000)
policy_id
string
The policy ID used for this scan
upload_id
string
The upload ID used for this scan
mapping_id
string
The mapping ID used for this scan
audit_id
string
The audit ID if this scan is part of an audit
mapping_config
object
The column mapping configuration used for this scan
temporal_scale
string
The temporal scale used for time-based rules (e.g., “daily”, “monthly”)
score_history
array
Array of score change events showing compliance score evolution
delta
object
Comparison with the previous scan for the same policy. null if no previous scan exists

Example Response - Running

{
  "id": "abc12345-def6-7890-ghij-klmnopqrstuv",
  "status": "running",
  "violation_count": 0,
  "compliance_score": 0,
  "rules_processed": 8,
  "rules_total": 15,
  "created_at": "2024-01-15T10:30:00Z",
  "completed_at": null,
  "audit_name": "Q1 2024 Compliance Audit",
  "record_count": 42000,
  "policy_id": "550e8400-e29b-41d4-a716-446655440000",
  "upload_id": "123e4567-e89b-12d3-a456-426614174000",
  "mapping_id": "789e0123-e45b-67c8-d901-234567890123",
  "audit_id": null,
  "mapping_config": {
    "amount": "Transaction Amount",
    "account": "Account ID",
    "timestamp": "Date"
  },
  "temporal_scale": "daily",
  "score_history": [],
  "delta": null
}

Example Response - Completed

{
  "id": "abc12345-def6-7890-ghij-klmnopqrstuv",
  "status": "completed",
  "violation_count": 23,
  "compliance_score": 87.5,
  "rules_processed": 15,
  "rules_total": 15,
  "created_at": "2024-01-15T10:30:00Z",
  "completed_at": "2024-01-15T10:30:04Z",
  "audit_name": "Q1 2024 Compliance Audit",
  "record_count": 42000,
  "policy_id": "550e8400-e29b-41d4-a716-446655440000",
  "upload_id": "123e4567-e89b-12d3-a456-426614174000",
  "mapping_id": "789e0123-e45b-67c8-d901-234567890123",
  "audit_id": null,
  "mapping_config": {
    "amount": "Transaction Amount",
    "account": "Account ID",
    "timestamp": "Date"
  },
  "temporal_scale": "daily",
  "score_history": [
    {
      "score": 87.5,
      "timestamp": "2024-01-15T10:30:04Z",
      "action": "scan_completed",
      "violation_id": null
    }
  ],
  "delta": {
    "new_count": 5,
    "resolved_count": 12,
    "unchanged_count": 18,
    "previous_scan_id": "prev1234-5678-90ab-cdef-ghijklmnopqr",
    "previous_violation_count": 30
  }
}

Error Responses

404 Not Found

{
  "error": "NOT_FOUND",
  "message": "Scan not found"
}

Delta Analysis

The delta field provides insights into how violations have changed compared to the previous scan:
  • New violations - Issues that appeared in this scan but not the previous one
  • Resolved violations - Issues from the previous scan that no longer appear
  • Unchanged violations - Issues that persist across both scans
Violations are matched using a signature of rule_id:account, meaning the same rule triggered on the same account.

Polling Strategy

Since scans complete synchronously (< 5 seconds), you can poll immediately after creation:
// Start scan
const { scan_id } = await fetch('/api/scan/run', {
  method: 'POST',
  body: JSON.stringify({ policy_id, upload_id, mapping_id })
}).then(r => r.json());

// Poll for completion
const status = await fetch(`/api/scan/${scan_id}`).then(r => r.json());

if (status.status === 'completed') {
  console.log(`Scan complete: ${status.compliance_score}% compliant`);
  console.log(`Found ${status.violation_count} violations`);
}

Build docs developers (and LLMs) love