e-naxosMAF COURSE / COURS
Français

MICROSOFT AGENT FRAMEWORK · 0.16.0-rc.1

Business journal and effect evidence

Distinguish intention, acknowledgement and committed effect; reopen the database to verify local evidence.

Objectives

Start with the effect to prove

“The request was recorded” is a claim to verify. A call trace and read acknowledgement do not prove a write. The business journal stores a minimal chronology of host events; RecordedDecisions stores the local ReviewRequested action. Evidence means linking the commit event to that row read back from storage.

Local evidence path
  1. Host GUID → RequestReceived → accepted workflow
  2. Intention → SQLite transaction
  3. RecordedDecisions + ActionCommitted → same commit
  4. New process → Read → HasAction

Choose events and meanings

Closed program vocabulary
MechanismScope
RequestReceived / IntentionRequest received / intended action; no proven write
AcknowledgedRead tool called; no business effect
ActionCommitted + ActionIdCreated by CommitReview with the business row
ExecutionSucceeded / Failed / CancelledScenario outcome; later failure does not undo an earlier commit

JournalEntry accepts only a host GUID, UTC timestamp, current TraceId, closed enum and optional ActionId. It contains no functional user, conversation, tool arguments/results or free exception text. The old script proposed more data; the renovated program chooses this minimal shape to avoid storing secrets as supposed evidence. It does not reveal internal model reasoning.

Guarantee atomicity in this database

public long CommitReview(Guid executionId)
{
    using var connection = Open();
    using var transaction = connection.BeginTransaction();
    using var command = connection.CreateCommand();
    command.Transaction = transaction;
    command.CommandText = "INSERT INTO RecordedDecisions(ExecutionId,Decision) VALUES($id,'ReviewRequested') ON CONFLICT DO NOTHING";
    command.Parameters.AddWithValue("$id", executionId.ToString("N"));
    bool created = command.ExecuteNonQuery() == 1;
    command.CommandText = "SELECT Id FROM RecordedDecisions WHERE ExecutionId=$id";
    long id = (long)command.ExecuteScalar()!;
    if (created) Insert(connection, transaction, executionId, JournalKind.ActionCommitted, id);
    transaction.Commit();
    return id;

shared/Maf.Observability/BusinessJournal.cs · L58–L71 · 9a895c94534c

Source code · Maf.Observability · Folder

CommitReview opens a transaction, inserts under unique ExecutionId, reads the identifier, creates ActionCommitted only for a new row, then commits. Repeating the same GUID returns the same action without a second event. Append forbids ActionCommitted: an intention or generated text cannot manufacture commit evidence through that API.

Correlation relates observations; atomicity binds two writes to the same transaction. They are different guarantees. This transaction covers no remote system. For human approval and durable resumption, return to Demo320; the journal replaces neither host permission nor binding to the approved proposal.

Read back after restart

public bool HasAction(Guid executionId, long actionId)
{
    using var connection = Open();
    using var command = connection.CreateCommand();
    command.CommandText = "SELECT COUNT(*) FROM RecordedDecisions WHERE ExecutionId=$id AND Id=$action";
    command.Parameters.AddWithValue("$id", executionId.ToString("N"));
    command.Parameters.AddWithValue("$action", actionId);
    return (long)command.ExecuteScalar()! == 1;

shared/Maf.Observability/BusinessJournal.cs · L103–L110 · 9a895c94534c

Source code · Maf.Observability · Folder

if (Value(args, "--read") is string read)
{
    var entries = journal.Read(Guid.Parse(read));
    Console.WriteLine(JsonSerializer.Serialize(entries));
    return entries.Count > 0 && entries.Where(e => e.Kind == JournalKind.ActionCommitted)
        .All(e => e.ActionId.HasValue && journal.HasAction(e.ExecutionId, e.ActionId.Value)) ? 0 : 1;

shared/Maf.Observability/ObservabilityDemo.cs · L24–L29 · 9a895c94534c

Source code · Maf.Observability · Folder

Retain Database and ExecutionId, end the process, then call --read with the same file. Read orders by Id and preserves the original TraceId. HasAction checks RecordedDecisions for that GUID and ActionId. Record the exit code and also inspect Kind: --read can succeed for a nonempty failed chronology without ActionCommitted because its commit check then has no rows. Exit 0 therefore does not mean “action performed”.

Retention and scope of evidence

At each new execution, code policy purges metadata older than 30 days; read-only inspection does not trigger that purge. --erase deletes an execution’s metadata without undoing its action. Business-row retention is separate. SQLite performs logical deletion; free pages, copies and backups may remain. Protect files and output through operating-system permissions.

The journal is mutable, unsigned and offers no append-only or tamper-evidence guarantee. The teaching database is separate from preserved historical EP008 databases. Reading back a TraceId does not revive an active span or a continuous distributed trace. No global exactly-once, remote effect or regulatory compliance is demonstrated.

Observe success and failure

Prerequisites

Continue reading

Previous

Next

lot012-observability-1 · 2026-10-24 · 9a895c94534cd5fc6f3da883e37e5f7856e588c1