SOTER

Logos Fact File Spec

Purpose

Define the Logos DSL syntax for .fact files: the language-level rules for writing fact blocks that record occurrences against a .model (Ontology) and project through a .view (Lens).

This specification covers the language layer. The underlying storage and protocol layer — canonical envelope fields, hash chains, and sequence numbers — is owned by Akasha; see AkashaLedgerTechnicalSpec.md.

Foundational axioms (Save-First, Immutability, Bitemporality) are defined in PhilosophyConstitution.md § 2.

Scope

  • The .fact file as an immutable, append-only event log — the third pillar of the SOTER system alongside .model (Ontology) and .view (Lens).
  • Syntax and attributes of the fact block (occurred_at, recorded_at, trigger, consume, produce, corrects, type).
  • Bitemporality as expressed at the Logos language level.
  • Correction and Reconciler mechanics (corrects, logical_compensation).
  • Linter error and warning codes for .fact files.

Non-Goals

Terminology

Term Meaning
fact A single entry in the append-only Ledger, describing an occurrence.
Observer Assigns recorded_at and maintains the FIFO write queue.
Ledger The append-only, inviolable store of facts.
Verifier Collides facts with the .model to check MES arithmetic.
Reconciler Generates a compensating fact when an arithmetic gap is detected.
Ontological Dissonance The state detected by the Verifier when reality and model diverge.
occurred_at Phenomenon time — declared by the source (subjective).
recorded_at Recording time — assigned by the Observer (objective).
trigger Reference to the Action (from .model, or a prior fact) that caused this fact.
consume / produce Resources (Objects) removed or created by the fact, with cost basis.
corrects Reference to an earlier, incorrect fact this fact supersedes.
Friction The metric recorded_at - occurred_at; informational delay.

Model or Contract

Ledger Pipeline

Source (Sensor / UI)
        ↓
   Observer            ← assigns recorded_at, FIFO queue
        ↓
    Ledger             ← Append-only (inviolable)
        ↓
   Verifier            ← collides facts with .model (MES arithmetic)
        ↓
  Reconciler           ← generates Ontological Dissonance if a gap is detected
        ↓
   Observer            ← closed cybernetic loop (fact returns to input)

Syntax of the fact Block

fact <ID>
    occurred_at: <ISO8601>
    recorded_at: <ISO8601>          # (optional — assigned by the Observer)
    trigger: <Action-UUID>
    consume:
        <Object-UUID>: { amount: <number>, cost_basis: <value> <currency> }
    produce:
        <Object-UUID>: { cost_basis: <value> <currency> }

Complete List of Attributes

Attribute Required Description
occurred_at Time declared by the source (subjective)
recorded_at Objective recording time in the Ledger (assigned by the Observer)
trigger UUID of the Action from .model that triggered the event
consume Consumed resources (Object) with quantities and cost basis
produce Produced resources with cost basis / market value
corrects ID of an earlier incorrect fact (immutable correction)
type logical_compensation — fact generated by the Reconciler

Rules

  • Immutability: Once written, a fact is inviolable. History is not rewritten — it is corrected by adding a new fact with corrects:.
  • Append-only FIFO: The write order is absolute. The Observer assigns the recorded_at timestamp at the moment of recording.
  • Description, not Prescription: Facts describe how things are, not how they should be. The Reconciler deals with physical consistency (arithmetics), not ethical evaluation.
  • f-001-style corrected facts remain in the Ledger for auditing purposes. Any state calculations ignore the corrected fact and only take the correcting fact into account.

Bitemporality

Dimension Attribute Character
Phenomenon Time occurred_at Subjective — declared by the source
Recording Time recorded_at Objective — assigned by the system
Friction recorded_at - occurred_at Key metric of informational delay

Examples

Corrections (Immutable Correction)

Errors are not deleted. You create a new fact with corrects::

fact f-002
    occurred_at: 2026-03-08T09:05:00
    corrects: f-001
    trigger: u-<action-UUID>
    consume:
        u-<object-UUID>: { amount: 10, cost_basis: 2000 PLN }
    produce:
        u-<object-UUID>: { cost_basis: 1800 PLN }

Ontological Dissonance (Reconciler)

When the Verifier detects an arithmetic gap (e.g., 200 PLN missing in the balance), the Reconciler automatically generates a compensating fact:

fact f-003
    type: logical_compensation
    recorded_at: 2026-03-08T09:05:01    # A millisecond after f-002
    trigger: f-002
    produce:
        u-bug-basket: { cost_basis: 200 PLN }

This fact is injected back into the Observer's input — closing the cybernetic loop.

Complete Example

soter v1

# --- FACTS ---

# 1. Adam reports 10h — error in amount
fact f-001
    occurred_at: 2026-03-08T09:00:00
    trigger: u-function-implementation
    consume:
        u-man-hour: { amount: 10, cost_basis: 1500 PLN }  # ERROR: should be 2000
    produce:
        u-code-feature: { cost_basis: 2000 PLN }

# 2. Adam corrects the report
fact f-002
    occurred_at: 2026-03-08T09:05:00
    corrects: f-001
    trigger: u-function-implementation
    consume:
        u-man-hour: { amount: 10, cost_basis: 2000 PLN }
    produce:
        u-code-feature: { cost_basis: 1800 PLN }  # 200 PLN "escapes"

# 3. RECONCILER: closes the balance
fact f-003
    type: logical_compensation
    recorded_at: 2026-03-08T09:05:01
    trigger: f-002
    produce:
        u-bug-basket: { cost_basis: 200 PLN }

Validation

Linter rules for .fact:

Error Code Condition
Missing occurred_at E-F01 Every fact must have a phenomenon time
Missing trigger E-F02 Every fact must point to an Action from .model
trigger points to non-existent UUID E-F03 Reference to an undefined Action
Balance gap without compensation W-F10 consume.cost_basis ≠ produce.cost_basis (no Reconciler fact)
corrects points to non-existent ID E-F04 Spectral correction reference

Compatibility

The fact block described here is the Logos-language authoring surface. When a fact is committed, it is mapped onto Akasha's canonical fact envelope (id, stream, sequence, previous_hash, hash, and related protocol fields) — see the Examples section of AkashaLedgerTechnicalSpec.md. The two field sets are related but not identical: this spec's trigger/consume/ produce express the SVO/MES semantics of an occurrence, while Akasha's envelope carries protocol-level bookkeeping (hash chain, receipts, signatures) that this spec does not define.

The details of technical requirements for the fact generator and cryptographic validation of the ledger (hashchain and Merkle checkpoints) can be found in FactSimulatorArchitectureSpec.md.

Open Questions

  • What is the precise, canonical mapping between this spec's fact block attributes (trigger, consume, produce) and Akasha's fact envelope fields (action, objects, payload)?
  • Should corrects support multiple prior fact IDs (as Akasha's terminology allows for corrects as a reference list), or remain single-valued at the Logos syntax level?

Related Documents

SOTER v1.12.0-beta