SkillTotal Report Schema

September 15, 2026 · View on GitHub

The JSON report (--json / --output) is the serialization of the core Report model. It is the stable contract intended for the web and SaaS products.

Formal contract: report.schema.json (JSON Schema, report schema version 1.6) is the machine-readable source of truth. Consumers should validate against it. tests/test_report_schema.py guards it: any change to the report shape that is not reflected in the schema fails CI, forcing a deliberate REPORT_SCHEMA_VERSION bump. See releasing.md for version-bump rules.

Top-level shape

{
  "component": {
    "name": "evil-npm-pkg",
    "type": "npm_package",
    "source": "/abs/path/or/url",
    "version": "0.0.1"
  },
  "risk_score": 100,
  "risk_level": "critical",
  "summary": "Risk level CRITICAL (score 100/100). 7 finding(s); capabilities: ...",
  "capabilities": {
    "shell_execution": [ { "file": "...", "line_start": 10, "line_end": 10, "snippet": "..." } ]
  },
  "traits": [ /* behavioral fingerprint + standards crosswalk; see below */ ],
  "findings": [ /* see below */ ],
  "needs_review": [ /* see below */ ],
  "metadata": { /* see below */ }
}

Fields

component

FieldTypeNotes
namestringFrom package.json/pyproject or directory name
typestringnpm_package, python_package, mcp_server, ai_component, directory
sourcestringResolved local path or the original URL
versionstringFrom manifest if available, else ""

risk_score / risk_level

  • risk_score: integer 0–100.
  • risk_level: low (0–24), medium (25–49), high (50–74), critical (75–100).

capabilities

Object keyed by capability name; each value is a list of evidence objects. Possible keys: filesystem_read, filesystem_write, shell_execution, network_egress, install_time_execution, dynamic_code_execution, mcp_tools_detected, prompt_surface_risk. A capability is present only if at least one finding evidences it.

traits[]

A behavioral fingerprint: a higher-level projection over findings that names the traits a component exhibits, each with a machine-readable crosswalk to industry standards. Descriptive only — never affects the score (like capabilities). Added in schema 1.5. Full taxonomy and mapping rationale: trait-crosswalk.md.

FieldTypeNotes
traitstringTrait id (e.g. execution_authority, embedded_credential)
title / descriptionstringHuman-readable name and explanation
emergentbooleantrue for combination traits backed by a synthesized risky-construct (exfil_correlation, instruction_exfil_flow, malware_convergence)
crosswalk.csa_traitstringCloud Security Alliance trait/pattern
crosswalk.csa_riskstringThe CSA named risk for that trait
crosswalk.maestro_layersarrayMAESTRO layer objects { id, name } (empty where none)
crosswalk.atlas_tacticsarrayMITRE ATLAS tactic names (empty where no honest fit)
evidencearrayNon-empty evidence objects proving the trait

findings[]

FieldTypeNotes
idstringStable rule id (e.g. ST-SHELL-PY)
severitystringcritical / high / medium / low
categorystringe.g. shell_execution, mcp, exfiltration_path
titlestringShort human title
descriptionstringWhat was detected (interprets evidence only)
evidencearrayNon-empty list of evidence objects (invariant)
recommendationstringActionable guidance
threat_classstringmalicious_indicator (drives the malicious verdict), risky_construct (scored), exposure (a shipped credential: reported, not scored; added in 1.6), capability (informational)

evidence[] (inside findings and capabilities)

FieldTypeNotes
filestringPath relative to the component root (POSIX style)
line_startinteger1-based, inclusive
line_endinteger1-based, inclusive, >= line_start
snippetstringThe matched source line(s), truncated if very long

needs_review[]

Low-confidence or un-evidenced signals. Never affects the score.

FieldTypeNotes
categorystringSource category
titlestringShort title
reasonstringWhy it could not be confirmed as a finding
filestring | nullFile if known, else null

metadata

FieldTypeNotes
skilltotal_versionstringEngine version (= ENGINE_VERSION)
schema_versionstringReport schema version (= REPORT_SCHEMA_VERSION)
ruleset_versionintegerDetection ruleset version (= RULESET_VERSION)
generated_atstringISO-8601 UTC timestamp
files_indexedintegerFiles analyzed
files_skipped_binaryintegerBinary files skipped
files_skipped_largeintegerFiles over the size cap skipped
scanners_runarrayScanner names that ran
findings_by_severityobjectCounts per severity
suppressed_countintegerEvidence occurrences removed via --baseline

Alternative format: SARIF

--sarif emits a SARIF 2.1.0 document instead of the native JSON (for GitHub Code Scanning / IDEs). Severity maps to SARIF level (critical/higherror, mediumwarning, lownote) plus a numeric security-severity property. Each evidence occurrence becomes one SARIF result anchored to its file/line.

Invariants (guaranteed by the engine)

  1. Every object in findings[] has a non-empty evidence[].
  2. Every evidence object has all four fields with valid line numbers.
  3. Items that cannot be evidenced appear only in needs_review[].
  4. risk_score is the capped sum of the severity weights of malicious_indicator and risky_construct findings; risk_level is derived from it. exposure and capability findings never change it.