Skip to content

Clarify SARIF formatter boundaries: framework-generic vs OSPS-specific #360

Description

@mlieberman85

Background

The SARIF formatter currently lives in packages/darnit-baseline/src/darnit_baseline/formatters/ and mixes:

  • Framework-generic SARIF emission (mapping CheckResult to SARIF result objects, run metadata, rule metadata lookup from TOML).
  • OSPS-baseline-specific pieces (control ID conventions, help URL patterns, severity mapping choices).

Problem

Other implementations (darnit-gittuf, darnit-reproducibility) that want SARIF output either reimplement the generic parts or import from darnit-baseline, which would violate the plugin isolation intent.

Proposal

Split the formatter along the boundary:

  • Move framework-generic SARIF emission into packages/darnit/src/darnit/formatters/sarif.py.
  • Leave OSPS-baseline-specific mapping in darnit-baseline as a thin adapter over the framework formatter.
  • Other implementations gain a shared base without cross-plugin imports.

Enforce boundary via test: the framework formatter must not reference OSPS control IDs or baseline-specific constants.

Scope

Refactor, no behavior change. Existing SARIF output for OSPS should be byte-identical (or documented deltas) after the split.

Related

  • Architecture review that surfaced this (Aug 2026)
  • Rule 1 (framework never imports implementations) in CLAUDE.md

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions