TenantAtlas/specs/284-provider-neutral-artifact-source-taxonomy/spec.md
ahmido 75ebade345 feat: implement provider-neutral artifact source taxonomy (#343)
## Summary

Implements Spec 284 for provider-neutral artifact source taxonomy.

- add shared artifact source descriptor, resolver, taxonomy, and provider-detail support
- update findings, evidence snapshots, stored reports, inventory items, and tenant review surfaces to disclose descriptor-first artifact summaries
- add bounded Pest unit, feature, guard, and browser coverage for the taxonomy slice
- include the completed Spec 284 package artifacts under `specs/284-provider-neutral-artifact-source-taxonomy/`

## Notes

- branch: `284-provider-neutral-artifact-source-taxonomy`
- commit: `bf8d59e0`
- this PR was created as part of the requested commit/push/PR flow against `platform-dev`

Co-authored-by: Ahmed Darrazi <ahmed.darrazi@live.de>
Reviewed-on: #343
2026-05-08 23:47:31 +00:00

44 KiB

Feature Specification: Provider-neutral Artifact Source Taxonomy

Feature Branch: 284-provider-neutral-artifact-source-taxonomy
Created: 2026-05-08
Status: Implementation Ready
Input: User description: "Follow the next-best-prep workflow for reserved slot 284 and prepare the Provider-neutral Artifact Source Taxonomy v1 package without implementing application code."

Implementation Acceptance Update (2026-05-09): Runtime implementation is now explicitly requested. The prior SCOPE-001 prerequisite block is resolved for this slice by repo truth: Specs 281, 282, and 283 are present on the implementation branch, Spec 279 records the approved managed-environment core exception, and the touched artifact tables now carry the established workspace plus managed-environment ownership boundary. No new table, ownership plane, descriptor columns, or backfill is introduced by this status update.

Spec Candidate Check

  • Problem: TenantPilot already stores and renders artifact truth through finding_type, source, report_type, policy_type, source_kind, provider-owned payload fields, and ad hoc canonical-control bindings, but those seams still let Microsoft-specific type names behave like platform-core truth. Findings, evidence snapshots, stored reports, inventory metadata, and review sections describe the same artifact lineage in parallel vocabularies instead of one provider-neutral source contract.
  • Today's failure: Operators and contributors must reinterpret the same artifact through different discriminator families. FindingsSummarySource treats permission_posture, entra_admin_roles, and deviceCompliancePolicy as if they were interchangeable core-domain truth; StoredReport persists report_type as the main summary noun; EvidenceSourceProvider only exposes source_kind plus raw record type or id; and inventory still treats policy_type as the top-level metadata key even where the platform already differentiates governed-subject vocabulary from provider-owned detail.
  • User-visible improvement: Findings, evidence, reports, inventory items, and review or support summaries expose one canonical source descriptor first: source family, target, detector, and control summary. Microsoft-specific object types, report types, Graph-facing detector details, and legacy policy_type values remain available, but they become provider-owned detail instead of the first thing an operator or contributor must decode.
  • Smallest enterprise-capable version: Introduce one bounded artifact-source descriptor across existing finding, evidence, stored-report, and inventory seams; pin the initial source_family, source_kind, and source_target_kind inventories; separate inventory canonical_type, provider_object_type, and provider_display_type; and align touched evidence or review presenters to disclose the canonical descriptor before provider detail. Do not add a new artifact table, no compliance engine, no full detector catalog, no control-catalog expansion, and no historical backfill.
  • Explicit non-goals: No new compliance engine, no full control-catalog expansion, no historical backfill, no provider framework, no package-execution runtime, no workspace-first RBAC rewrite from Spec 285, no copy or localization neutralization from Spec 286, no no-legacy enforcement pack from Spec 287, and no UI-polish-first redesign.
  • Permanent complexity imported: One bounded artifact-source descriptor contract, one pinned inventory for source_family, source_kind, and source_target_kind, one narrow normalizer or presenter seam if existing helpers cannot carry the contract cleanly, one inventory type descriptor split, and focused unit, feature, guard, and browser proof. No new table or independent persisted entity is imported.
  • Why now: Specs 279 through 283 already moved the platform toward workspace-first managed environments, provider-neutral connection scope, artifact-surface ownership, and provider capability truth. The remaining gap is artifact lineage and artifact-type semantics. If 284 does not land now, later package-output work and later copy neutralization will still inherit Microsoft-shaped artifact truth.
  • Why not local: The drift is shared across models, evidence-source contracts, stored-report readers, inventory metadata, review sections, and operator surfaces. A local rename in one page or one service would immediately diverge from the other artifact consumers.
  • Approval class: Core Enterprise
  • Red flags triggered: New taxonomy, new shared abstraction, and derived descriptor scope fields. Defense: the repo already has multiple real consumers and conflicting artifact vocabularies. 284 is intentionally bounded to one descriptor contract, a small pinned inventory, and the minimum surface convergence needed to make current-release artifacts provider-neutral.
  • Score: Nutzen: 2 | Dringlichkeit: 2 | Scope: 2 | Komplexitaet: 1 | Produktnaehe: 2 | Wiederverwendung: 2 | Gesamt: 11/12
  • Decision: approve

Spec Scope Fields

  • Scope: workspace, tenant
  • Primary Routes:
    • workspace-first findings resource list and detail surfaces
    • workspace-first evidence snapshot list and detail surfaces
    • workspace-first stored-report list and detail surfaces
    • workspace-first inventory item list and detail surfaces
    • workspace-first tenant-review detail surfaces and shared review sections that already summarize canonical controls and supporting evidence
  • Data Ownership:
    • Finding, EvidenceSnapshotItem, StoredReport, and InventoryItem remain tenant-owned persisted truth bound to the established workspace plus tenant scope at authorization time; current repo truth reaches that scope through existing workspace_id columns where present and through managed_environment_id relations everywhere else
    • the shared artifact-source descriptor remains a derived read-model or presenter contract over those existing records in 284 v1; no new descriptor columns, no second descriptor payload, and no new table or ledger are introduced
    • provider_connection_id may be persisted or derived only where current artifact truth already knows the connection; 284 does not invent a new provider-connection ownership model
    • package_run_id remains an optional nullable reference in the shared descriptor contract only; 284 does not create package-execution truth or package artifacts
  • RBAC:
    • workspace membership remains the first 404 boundary
    • managed-environment entitlement remains the second 404 boundary
    • existing view capabilities for findings, evidence, reports, inventory, and tenant reviews remain authoritative
    • 284 introduces no new destructive action and no new authorization plane

Cross-Cutting / Shared Pattern Reuse

  • Cross-cutting feature?: yes
  • Interaction class(es): evidence/report viewers, read-only detail sections, inventory metadata, status messaging, support-diagnostic and AI source descriptors
  • Systems touched: EvidenceSourceProvider, EvidenceSnapshotService, FindingsSummarySource, stored-report producers and readers, InventoryPolicyTypeMeta, TenantReviewSectionFactory, ArtifactTruthPresenter, and existing support or AI source_family consumers
  • Existing pattern(s) to extend: PlatformVocabularyGlossary, GovernanceSubjectTaxonomyRegistry, CanonicalControlResolutionRequest, CanonicalControlResolver, InventoryPolicyTypeMeta, ArtifactTruthPresenter, and the existing support or AI source_family naming precedent
  • Shared contract / presenter / builder / renderer to reuse: CanonicalControlResolutionRequest, CanonicalControlResolver, InventoryPolicyTypeMeta, EvidenceSnapshotService, TenantReviewSectionFactory, and ArtifactTruthPresenter
  • Why the existing shared path is sufficient or insufficient: the repo already has vocabulary, control-binding, and presenter seams, but it still lacks one shared artifact-source descriptor that all artifact families can carry without page-local or service-local remapping
  • Allowed deviation and why: one bounded ArtifactSourceDescriptor or equivalent normalizer or presenter seam is allowed if the current helpers cannot carry the pinned descriptor fields without duplication
  • Consistency impact: findings, evidence snapshots, stored reports, inventory summaries, review sections, and touched support or AI bundles must expose the same source_family, source_kind, source_target_kind, and descriptor semantics before disclosing provider detail; control_key stays mandatory for touched findings, evidence, stored reports, and review sections, while inventory keeps the shared descriptor plus the canonical and provider type split as its primary summary
  • Review focus: verify that no touched page, presenter, or service rebuilds the descriptor locally and that Microsoft-specific nouns remain nested provider detail rather than new shared platform truth

OperationRun UX Impact

  • Touches OperationRun start/completion/link UX?: no
  • Shared OperationRun UX contract/layer reused: N/A
  • Delegated start/completion UX behaviors: N/A
  • Local surface-owned behavior that remains: N/A
  • Queued DB-notification policy: N/A
  • Terminal notification path: N/A
  • Exception required?: none

Provider Boundary / Platform Core Check

  • Shared provider/platform boundary touched?: yes
  • Boundary classification: mixed
  • Seams affected: Finding discriminator fields, EvidenceSourceProvider result shape, EvidenceSnapshotItem persisted source metadata, StoredReport report typing, inventory metadata, canonical-control binding inputs, review-section evidence summaries, and support or AI source_family consumers if touched
  • Neutral platform terms preserved or introduced: workspace_id, tenant_id, managed_environment_id, source_family, source_kind, source_target_kind, source_target_identifier, provider_key, provider_connection_id, canonical_type, detector_key, and control_key
  • Provider-specific semantics retained and why: finding_type, report_type, policy_type, Microsoft object types, report domains, Graph-facing detector keys, and provider display labels remain provider-owned because the platform still needs to preserve Microsoft-native evidence and because 284 is not a fake generic rewrite of the adapters
  • Why this does not deepen provider coupling accidentally: the shared descriptor moves provider detail out of the top-level artifact summary instead of expanding Microsoft-specific semantics. It adds one neutral envelope over already existing provider detail and rejects new provider registries or fake multi-provider engines.
  • Follow-up path: package-execution adoption remains for later work, broader copy neutralization remains in Spec 286, and no-legacy enforcement remains in Spec 287

UI / Surface Guardrail Impact

Surface / Change Operator-facing surface change? Native vs Custom Shared-Family Relevance State Layers Touched Exception Needed? Low-Impact / N/A Note
Findings resource summary and detail copy yes Native Filament + existing shared presenters findings, evidence, review page, detail no summary fields and presenter ordering only
Evidence snapshot resource summary and item detail yes Native Filament + shared artifact truth presenters evidence, reports, reviews page, detail no read-only evidence surface
Inventory item list and detail metadata yes Native Filament inventory metadata, governed-subject labeling page, detail no descriptor and type-label split only
Stored report list and detail summary yes Native Filament + shared artifact truth presenters reports, evidence, support page, detail no read-only reporting surface
Tenant review detail sections that summarize supporting artifacts yes Mixed native Filament + shared review factory reviews, evidence, reports detail no section summary and disclosure order only

Decision-First Surface Role

Surface Decision Role Human-in-the-loop Moment Immediately Visible for First Decision On-Demand Detail / Evidence Why This Is Primary or Why Not Workflow Alignment Attention-load Reduction
Findings resource Primary Decision Surface Decide whether the finding needs follow-up now Canonical source family, governed subject or source target, detector summary, control summary, severity, status Provider object type, raw legacy finding type, low-level evidence payload Primary because findings are already an operator decision queue Follows governance-review workflow Removes the need to decode Microsoft-only type names before triage
Evidence snapshot resource Tertiary Evidence / Diagnostics Surface Inspect which supporting artifacts prove the current state Canonical source descriptor and control summary per item Raw payloads, record ids, provider object types, legacy report or finding types Not primary because it explains evidence after a decision surface points here Follows evidence-inspection workflow Keeps diagnostic depth available without making it the first summary
Inventory item resource Secondary Context Surface Inspect what provider object the platform currently knows about Canonical type, provider display type, lifecycle timestamps Raw provider object type, legacy policy_type, low-level metadata Not primary because inventory is an inspection surface, not the first decision queue Follows inventory-inspection workflow Removes ambiguity between platform type and provider object type
Stored report resource Tertiary Evidence / Diagnostics Surface Inspect a generated provider report behind other summaries Canonical source family, report summary, control summary when present Provider-native report type, payload, provider detail Not primary because reports are evidence or reporting artifacts Follows diagnostics and reporting workflow Keeps report meaning readable without turning report_type into platform truth
Tenant review detail sections Secondary Context Surface Cross-check which supporting artifacts justify the review state Canonical source summary and control summary Raw artifact payloads and provider-native identifiers Not primary because the review decision already exists at the review level Follows review workflow Prevents section summaries from restating provider-native detail as the main conclusion

Audience-Aware Disclosure

Surface Audience Modes In Scope Decision-First Default-Visible Content Operator Diagnostics Support / Raw Evidence One Dominant Next Action Hidden / Gated By Default Duplicate-Truth Prevention
Findings resource operator-MSP, support-platform canonical source family, governed subject, detector summary, control summary, severity, status provider display type, legacy finding type, related operation or review links raw payloads and provider-native evidence Open finding detail or the existing remediation path raw payload excerpts remain collapsed or lower on the page finding summary states artifact meaning once; detail adds proof rather than a second competing label
Evidence snapshot resource operator-MSP, support-platform source descriptor per snapshot item, completeness state, control summary provider object type, source record references, freshness detail raw evidence payloads Inspect evidence item payload detail remains secondary canonical item summary stays aligned with findings and review sections
Inventory item resource operator-MSP, support-platform canonical type and provider display type provider object type, source timestamps, sync provenance raw metadata Open inventory item raw meta_jsonb remains diagnostics-only canonical type is shown once and not duplicated as a second headline
Stored report resource operator-MSP, support-platform source family, report headline, latest freshness provider-native report type, detector detail, fingerprints raw payload Open report detail raw JSON remains hidden or lower priority report summary uses canonical source family once and nests provider detail
Tenant review detail sections operator-MSP, support-platform artifact source summary and control summary inside each section provider object type, legacy type names, supporting links raw evidence bundles and payloads Inspect related artifact raw provider detail remains gated to deeper disclosure section summary stays aligned with the owning review summary instead of restating a second truth

UI/UX Surface Classification

Surface Action Surface Class Surface Type Likely Next Operator Action Primary Inspect/Open Model Row Click Secondary Actions Placement Destructive Actions Placement Canonical Collection Route Canonical Detail Route Scope Signals Canonical Noun Critical Truth Visible by Default Exception Type / Justification
Findings resource Monitoring / Queue / Workbench Queue / Review Surface Open the finding and decide follow-up Full-row open to detail required Existing contextual actions stay in row More or detail header existing destructive-like mutations remain grouped and confirmation-protected workspace-first findings list workspace-first finding detail workspace, managed environment, severity, status Finding canonical source family, governed subject, and control summary none
Evidence snapshot resource List / Table / Bulk Read-only Registry / Report Surface Open the snapshot item that proves a state Existing list or detail page required Existing safe links remain contextual none workspace-first evidence list workspace-first evidence detail workspace, managed environment, completeness state Evidence snapshot source descriptor and control summary none
Inventory item resource List / Table / Bulk Read-only Registry / Report Surface Open the provider object behind the canonical type Full-row open to detail required Existing safe links remain contextual none workspace-first inventory item list workspace-first inventory item detail workspace, managed environment, canonical type Inventory item canonical type and provider display type none
Stored report resource List / Table / Bulk Read-only Registry / Report Surface Open the report that explains the current posture Full-row open to detail required Existing safe links remain contextual none workspace-first stored-report list workspace-first stored-report detail workspace, managed environment, freshness Stored report source family and report summary none
Tenant review detail sections Record / Detail / Edit Detail-first Operational Surface Open the related artifact or supporting evidence Existing review detail section links n/a Contextual related links only none workspace-first tenant-review list workspace-first tenant-review detail workspace, managed environment, review status Review section evidence canonical artifact source and control summary none

Operator Surface Contract

Surface Primary Persona Decision / Operator Action Supported Surface Type Primary Operator Question Default-visible Information Diagnostics-only Information Status Dimensions Used Mutation Scope Primary Actions Dangerous Actions
Findings resource Tenant operator Decide whether the finding needs action Queue / Review Surface What artifact triggered this finding and what control does it affect? source family, governed subject, detector summary, control summary, severity, status raw payloads, provider-native ids, legacy type names lifecycle, severity, governance state existing finding workflow only existing inspect and remediation actions existing closure or governance actions only
Evidence snapshot resource Tenant operator Inspect which artifacts prove the current evidence state Read-only Registry / Report Surface Which artifact family produced this evidence and what control does it support? source descriptor, control summary, freshness, completeness raw payloads, source record references evidence completeness, freshness read-only existing inspect links none
Inventory item resource Tenant operator Inspect inventory classification and provider provenance Read-only Registry / Report Surface What canonical thing is this item, and what provider object produced it? canonical type, provider display type, platform, timestamps raw provider object type, legacy metadata freshness, sync recency read-only existing inspect links none
Stored report resource Tenant operator Inspect a report backing another summary Read-only Registry / Report Surface What report family is this and what artifact lineage does it represent? source family, freshness, summary headline raw payload, fingerprints, provider report type freshness, availability read-only existing inspect links none
Tenant review detail sections Tenant operator Inspect supporting artifact context behind the review Detail-first Operational Surface Which artifact family and control summary justify this review section? canonical artifact summary and control summary raw evidence bundles, provider-native ids review lifecycle, evidence completeness existing review workflow only existing inspect links none

Proportionality Review

  • New source of truth?: no new persisted source of truth; one derived shared contract over existing artifact truth
  • New persisted entity/table/artifact?: no
  • New abstraction?: yes
  • New enum/state/reason family?: yes
  • New cross-domain UI framework/taxonomy?: yes, but only as a bounded artifact-source and inventory-type taxonomy tied to current-release artifact seams
  • Current operator problem: the same artifact lineage is currently described with Microsoft-specific nouns in one surface and platform-adjacent summaries in another, which makes evidence, reports, findings, inventory, and reviews harder to interpret safely
  • Existing structure is insufficient because: current helpers already normalize vocabulary, control bindings, or display order in isolation, but no shared contract pins what an artifact source is across findings, evidence, reports, and inventory metadata
  • Narrowest correct implementation: add one descriptor contract, one inventory type split, and the smallest normalizer or presenter seam necessary to derive them from existing records, current payloads, and presenters
  • Ownership cost: additive migrations or payload shape updates, translator or presenter upkeep, legacy-row interpretation rules, and focused proof for both read models and touched Filament surfaces
  • Alternative intentionally rejected: page-local aliasing or report-local mapping was rejected because it would keep artifact meaning inconsistent; a larger detector catalog or provider framework was rejected because it is future-facing and not required for current repo truth
  • Release truth: current-release provider-neutral artifact interpretation over existing Microsoft-first artifacts, not a speculative package engine or cross-provider platform rewrite

Compatibility posture

This feature assumes a pre-production environment.

Backward compatibility, legacy aliases, migration shims, historical fixtures, and compatibility-specific tests are out of scope unless explicitly required by this spec.

Canonical replacement is preferred over preservation, except where existing Microsoft-produced artifacts must remain readable as provider-owned historical detail.

Testing / Lane / Runtime Impact

  • Test purpose / classification: Unit, Feature, Browser
  • Validation lane(s): fast-feedback, confidence, browser
  • Why this classification and these lanes are sufficient: the pinned taxonomy inventory and descriptor normalizer are pure derivation and need unit proof; findings, evidence snapshots, stored reports, inventory metadata, and touched presenters need feature proof; one browser smoke is enough to prove the operator sees the new descriptor-first disclosure under the live Filament shell
  • New or expanded test families: focused artifact-source unit tests, artifact-contract feature tests, one guard test, and one browser smoke
  • Fixture / helper cost impact: moderate because proof needs workspace, managed environment, findings, reports, evidence snapshots, and inventory fixtures without widening shared defaults
  • Heavy-family visibility / justification: none beyond one narrow browser smoke for touched operator-facing read paths
  • Special surface test profile: standard-native-filament, shared-detail-family
  • Standard-native relief or required special coverage: most surfaces need ordinary feature coverage; the read-only review section and evidence summary contract need shared-detail-family assertions to keep disclosure ordering stable
  • Reviewer handoff: verify the exact pinned inventories across artifacts, confirm touched surfaces show canonical descriptor first and provider detail second, confirm no new table or backfill appears, and rely on the proof commands below rather than broad suite guesses
  • Budget / baseline / trend impact: contained feature-local increase only
  • Escalation needed: reject-or-split if implementation adds a detector catalog, package runtime, provider framework, historical backfill, or adjacent copy or RBAC scope
  • Active feature PR close-out entry: Guardrail
  • Planned validation commands:
    • export PATH="/bin:/usr/bin:/usr/local/bin:$PATH" && REPO_ROOT="$(git rev-parse --show-toplevel)" && (cd "$REPO_ROOT/apps/platform" && ./vendor/bin/sail artisan test --compact tests/Unit/Artifacts/ArtifactSourceTaxonomyCatalogTest.php tests/Unit/Inventory/InventoryCanonicalTypeDescriptorTest.php)
    • export PATH="/bin:/usr/bin:/usr/local/bin:$PATH" && REPO_ROOT="$(git rev-parse --show-toplevel)" && (cd "$REPO_ROOT/apps/platform" && ./vendor/bin/sail artisan test --compact tests/Feature/Artifacts/FindingArtifactSourceTaxonomyTest.php tests/Feature/Artifacts/EvidenceSnapshotSourceTaxonomyTest.php tests/Feature/Artifacts/StoredReportSourceTaxonomyTest.php tests/Feature/Artifacts/InventoryArtifactTypeTaxonomyTest.php tests/Feature/Filament/Artifacts/ArtifactSourceTaxonomySurfaceTest.php tests/Feature/Guards/ArtifactSourceProviderTruthGuardTest.php)
    • export PATH="/bin:/usr/bin:/usr/local/bin:$PATH" && REPO_ROOT="$(git rev-parse --show-toplevel)" && (cd "$REPO_ROOT/apps/platform" && ./vendor/bin/sail artisan test --compact tests/Browser/Spec284ArtifactSourceTaxonomySmokeTest.php)
    • export PATH="/bin:/usr/bin:/usr/local/bin:$PATH" && REPO_ROOT="$(git rev-parse --show-toplevel)" && (cd "$REPO_ROOT/apps/platform" && ./vendor/bin/sail bin pint --dirty --format agent)

User Scenarios & Testing

User Story 1 - Interpret findings, evidence, and reports with one source descriptor (Priority: P1)

As an operator, I want findings, evidence snapshots, and stored reports to expose the same artifact source summary so I can understand what produced the current signal without decoding Microsoft-only type names first.

Why this priority: this is the core reason for 284. If findings, evidence, and reports still describe the same lineage differently, the taxonomy does not solve the real product problem.

Independent Test: create or load one finding, one evidence snapshot, and one stored report for the same managed environment and confirm they each expose the canonical source family, target, detector summary, and control summary before any provider-native detail.

Acceptance Scenarios:

  1. Given a drift finding still carries policy_type in evidence_jsonb, When the operator opens the finding or evidence summary, Then the surface shows the canonical source descriptor first and keeps the Microsoft policy type as provider detail.
  2. Given a stored permission-posture or Entra-admin-roles report exists, When the operator opens the report, Then the surface shows the shared source family and report meaning first and nests the raw report_type and provider payload below that summary.

User Story 2 - Read inventory items without treating policy_type as universal platform truth (Priority: P1)

As an operator, I want inventory items to distinguish the platform's canonical type from the provider's object type and display type so I can inspect inventory without assuming Microsoft naming is the only valid domain model.

Why this priority: the candidate explicitly calls out inventory metadata. If inventory keeps using policy_type as top-level truth, later package-output and reporting work will keep inheriting that false universal.

Independent Test: open one inventory item with an existing Microsoft-backed policy type and confirm the page exposes canonical_type, provider_object_type, and provider_display_type as separate concepts.

Acceptance Scenarios:

  1. Given an inventory item was captured from a Microsoft object type such as deviceCompliancePolicy, When the operator opens the item, Then the page shows the canonical platform type separately from the raw provider object type.
  2. Given the inventory item has a user-facing label, When the operator scans the list or detail view, Then the provider display type is readable without replacing the canonical type as the platform's primary metadata.

User Story 3 - Keep evidence, reviews, and reporting surfaces descriptor-first (Priority: P2)

As an operator, I want evidence, review, and reporting surfaces to disclose canonical artifact source summaries first and provider detail second so review decisions stay readable and diagnostic depth remains available.

Why this priority: changing the underlying model without changing the first-decision summary would still leave the UI teaching the old artifact truth.

Independent Test: open the evidence snapshot resource, a tenant review with supporting sections, and a stored report, then confirm each touched summary leads with the same canonical descriptor fields and keeps raw provider detail in secondary disclosure.

Acceptance Scenarios:

  1. Given a tenant review section summarizes evidence from findings and reports, When the operator opens the review detail, Then the section shows the same source family and control summary used by the underlying artifacts instead of inventing a third summary label.
  2. Given an evidence snapshot item or stored report has raw provider payload available, When the operator opens the detail page, Then canonical descriptor fields stay in the summary region and raw provider payload remains diagnostics-only.

User Story 4 - Reuse source-family semantics in downstream shared consumers without adding package runtime (Priority: P3)

As a maintainer, I want touched support or AI source-family consumers and future package-output work to reuse the same source-family semantics so later packaging or summarization features do not need a second artifact taxonomy.

Why this priority: later package-output work is explicitly an acceptance target for 284, but 284 itself must stop before inventing package runtime.

Independent Test: inspect the shared descriptor contract, touched support or AI source-family consumers, and the logical contract package slot, then confirm they use the same source-family nouns and leave package_run_id optional and unused in the current release.

Acceptance Scenarios:

  1. Given a touched support or AI summary declares a source_family, When it references artifact-source semantics after 284, Then it uses the same source-family vocabulary as the new artifact descriptor.
  2. Given the ArtifactSourceDescriptor includes optional package_run_id, When current-release artifacts are rendered, Then the field stays null or absent and does not imply that package runtime already exists.

Edge Cases

  • A historical finding has source = null and only finding_type plus evidence_jsonb from an older write path.
  • A drift finding still carries only Microsoft policy_type or raw detector detail, but the canonical type mapping is missing or incomplete.
  • A stored report already has provider_key = microsoft in payload while report_type remains a Microsoft-shaped top-level discriminator.
  • An evidence source summary aggregates many records and therefore has no single source_record_id, so the shared descriptor must still point to the right source_target_kind and optional identifier.
  • An inventory item has no friendly provider display label, so the canonical type and provider object type must still remain distinct without inventing fake display copy.
  • provider_connection_id is not available for a historical artifact even though the provider key and managed environment are known.
  • A touched support or AI consumer already uses source_family semantics that would conflict with the new artifact family names if left unchanged.

Requirements

Constitution alignment (required): This slice changes artifact typing, artifact-source derivation, read-only summary disclosure, and canonical-control binding inputs across findings, evidence, stored reports, inventory, and review summaries. It does not introduce a new Graph contract path, a new long-running workflow, or a new persisted artifact ledger.

Constitution alignment (PROP-001 / ABSTR-001 / PROV-001 / BLOAT-001): One shared descriptor and one inventory type split are justified because the repo already has multiple live artifact families and conflicting interpretations of the same Microsoft-produced truth. No provider framework, no detector registry, no control-catalog expansion, and no new table are in scope.

Constitution alignment (XCUT-001 / UI-FIL-001 / DECIDE-001): The feature must reuse the existing findings, evidence, stored-report, inventory, and tenant-review surfaces. It may refine their summary ordering and view models, but it must not create a new dashboard, a second evidence viewer, or local semantic color or status systems.

Constitution alignment (RBAC-UX): Workspace and managed-environment boundaries remain unchanged. Existing view capabilities remain authoritative, and provider-neutral artifact typing must not widen who can see findings, evidence, reports, inventory, or reviews.

Constitution alignment (TEST-GOV-001): Proof stays bounded to focused unit, feature, guard, and one narrow browser smoke. The descriptor inventory, descriptor fields, and proof commands must stay pinned identically across the package.

Functional Requirements

  • FR-001: The system MUST introduce one shared artifact-source descriptor for findings, evidence snapshots, stored reports, inventory metadata, and touched review or summary consumers.
  • FR-002: The shared artifact-source descriptor MUST standardize these fields: workspace_id, tenant_id, managed_environment_id, source_family, source_kind, provider_key, provider_connection_id, source_target_kind, source_target_identifier, detector_key, control_key, and optional package_run_id.
  • FR-003: The initial source_family inventory for 284 v1 MUST be exactly finding, stored_report, evidence_snapshot, inventory, and operation_run.
  • FR-004: The initial source_kind inventory for 284 v1 MUST be exactly model_summary, stored_report, operation_rollup, and inventory_projection.
  • FR-005: The initial source_target_kind inventory for 284 v1 MUST be exactly managed_environment, governed_subject, provider_connection, and operation_run.
  • FR-006: 284 v1 MUST NOT introduce a global detector catalog or a broader control-catalog expansion; detector_key remains a standardized field and naming rule, not a new registry of every detector in the platform.
  • FR-007: Findings MUST derive the shared descriptor from existing finding_type, source, and evidence_jsonb fields without requiring historical backfill.
  • FR-008: EvidenceSourceProvider and EvidenceSnapshotService MUST carry or derive the shared descriptor consistently so EvidenceSnapshotItem does not rely on source_record_type alone as its top-level artifact identity.
  • FR-009: Stored reports MUST align report_type with shared source-family semantics while keeping report_type itself as provider-owned detail where needed.
  • FR-010: Inventory metadata MUST expose canonical_type, provider_object_type, and provider_display_type as separate concepts and MUST stop treating raw policy_type as the only platform-wide artifact type.
  • FR-011: Touched canonical-control consumers MUST resolve or disclose control_key through the shared descriptor path instead of rebuilding platform truth from page-local Microsoft type checks.
  • FR-012: Touched findings, evidence, stored-report, and tenant-review presenters MUST show canonical descriptor fields and control_key before provider-native detail. Inventory presenters MUST show the shared source descriptor and the canonical/provider type split before raw provider metadata.
  • FR-013: Existing Microsoft artifacts MUST remain valid and interpretable as provider_key = microsoft sources after 284 lands.
  • FR-014: 284 MUST NOT require historical backfill; legacy rows may be normalized on read or through additive future writes only.
  • FR-015: package_run_id MAY exist as a nullable field in the shared descriptor contract, but 284 MUST NOT create package runtime, package-run persistence, or package-output surfaces.
  • FR-016: Touched support or AI source-family consumers MUST use the same source-family nouns as the shared descriptor if they are updated in this slice.
  • FR-017: The implementation MUST NOT introduce a new artifact table, provider framework, compliance engine, detector registry, full control-catalog expansion, RBAC rewrite, copy-neutralization pass, or no-legacy enforcement pack.
  • FR-018: The descriptor inventory and source-type split MUST stay pinned identically across spec.md, plan.md, research.md, data-model.md, quickstart.md, tasks.md, the logical contract, and the readiness checklist. The canonical proof commands MUST stay pinned identically across spec.md, plan.md, quickstart.md, tasks.md, and the readiness checklist.
  • FR-019: Before runtime implementation begins, SCOPE-001 ownership compliance for touched tenant-owned artifact tables MUST be satisfied or explicitly excepted; 284 MUST NOT silently waive that prerequisite.

Authorization and Safety Requirements

  • AR-001: Workspace membership MUST remain the first access boundary for touched findings, evidence, reports, inventory, and review surfaces.
  • AR-002: Managed-environment entitlement MUST remain the second access boundary for those surfaces.
  • AR-003: Non-members or cross-workspace or cross-environment access attempts MUST continue to resolve as 404, while in-scope actors missing resource capabilities still resolve as 403.
  • AR-004: 284 introduces no new destructive action. Any touched destructive or high-impact action on findings or adjacent resources MUST remain confirmation-protected and server-authorized under the current action contract.
  • AR-005: Navigation-only related links on touched read-only artifact surfaces MUST remain clearly navigation-only and must not be re-expressed as mutations during this slice.
  • AR-006: Provider-neutral artifact typing MUST NOT bypass or weaken the current resource policies and capability checks.

Non-Functional Requirements

  • NFR-001: Filament remains v5 on Livewire v4.
  • NFR-002: Provider registration remains in apps/platform/bootstrap/providers.php; nothing moves to bootstrap/app.php.
  • NFR-003: Asset strategy remains unchanged. No new panel or shared asset registration is expected from 284.
  • NFR-004: FindingResource and InventoryItemResource keep valid View pages for any existing or future global-search posture. EvidenceSnapshotResource, StoredReportResource, and TenantReviewResource remain non-globally-searchable while keeping View pages.
  • NFR-005: The feature must remain reviewable as one bounded artifact-source slice and MUST NOT silently absorb work reserved for Specs 285 through 287.
  • NFR-006: Default-visible summary fields on touched operator-facing surfaces must stay Filament-native and avoid page-local card, badge, or semantic color systems.

UI Action Matrix

Surface Location Header Actions Inspect Affordance (List or Table) Row Actions (max 2 visible) Bulk Actions (grouped) Empty-State CTA(s) View Header Actions Create or Edit Save+Cancel Audit log? Notes / Exemptions
Findings resource FindingResource preserve existing header actions clickable row to View preserve existing contextual actions and grouping preserve existing grouped bulk actions only preserve current empty-state behavior preserve existing detail-header actions preserve existing edit or workflow forms where applicable preserve current mutation audit behavior 284 changes descriptor and summary semantics only
Evidence snapshot resource EvidenceSnapshotResource preserve existing read-only actions clickable row to View preserve current safe related links only none preserve current empty-state behavior preserve existing read-only header actions N/A no new audit surface descriptor-first disclosure only
Inventory item resource InventoryItemResource preserve current no-header-action posture clickable row to View preserve current row behavior none preserve current no-CTA posture preserve existing read-only detail actions N/A no new audit surface inventory type split only
Stored report resource StoredReportResource preserve existing read-only actions clickable row to View preserve current safe actions only none preserve current empty-state behavior preserve existing read-only header actions N/A no new audit surface source-family and summary semantics only
Tenant review detail sections TenantReviewResource and TenantReviewSectionFactory preserve existing header and section actions existing section links remain inspect affordances preserve current safe contextual links none N/A preserve existing review-header actions preserve current review flows preserve current review audit behavior section summary ordering only

All other touched support or AI consumers must keep their existing action contracts and only adopt the shared source-family vocabulary where 284 touches them.

Key Entities

  • Artifact Source Descriptor: one shared contract describing source family, source kind, provider, source target, optional target identifier, detector key, control key, and optional package-run reference for an artifact or summary.
  • Inventory Type Descriptor: the bounded inventory metadata split separating canonical_type, provider_object_type, and provider_display_type while preserving legacy policy_type as provider-owned detail.
  • Artifact Provider Detail: provider-owned raw fields such as finding_type, report_type, provider object type, Graph-facing detector detail, or legacy policy_type retained as nested evidence rather than top-level platform truth.
  • Artifact Source View Model: the derived presenter contract used by findings, evidence, reports, inventory, and tenant-review sections to disclose canonical descriptor fields first and provider detail second.

Success Criteria

Measurable Outcomes

  • SC-001: 100% of touched findings, evidence snapshots, stored reports, inventory items, and tenant-review artifact summaries expose the shared source descriptor before provider-native detail.
  • SC-002: 100% of touched inventory item summaries expose canonical_type, provider_object_type, and provider_display_type as separate fields.
  • SC-003: 100% of touched artifact summaries that already resolve a canonical control continue to expose control_key consistently through the shared descriptor path.
  • SC-004: The implementation introduces no new artifact table, no historical backfill requirement, and no package runtime while keeping existing Microsoft-produced artifacts readable as Microsoft provider sources.