# StemeDB Usage Guide (Go)

> **Philosophy:** State as a Side Effect. Truth as a Consensus.
> **Package:** `github.com/orchard9/stemedb-go`

---

## SDK Quick Start

For most use cases, start with the **Go SDK** which provides a simple, type-safe API:

```bash
go get github.com/orchard9/stemedb-go/steme
```

```go
import "github.com/orchard9/stemedb-go/steme"

// Generate keypair
signer, _ := steme.GenerateSigner()

// Create client
client := steme.NewClient("http://localhost:18180", signer)

// Assert a fact
assertion := steme.NewAssertion("Tesla_Inc", "has_revenue").
    WithNumber(96.7).
    WithConfidence(0.95).
    WithSourceHash("...").
    Build()

hash, _ := client.Assert(ctx, assertion)

// Query with conflict resolution
params := steme.NewQuery().
    WithSubject("Tesla_Inc").
    WithPredicate("has_revenue").
    WithLens(steme.LensConsensus).
    Build()

result, _ := client.Query(ctx, params)
```

**Full SDK Documentation:** [docs/sdk/go-sdk.md](./docs/sdk/go-sdk.md)

---

## 1. The "Invisible" Integration (Job-Aware)

StemeDB is the "Flight Recorder" for your Agents. The Context carries the **Job ID**, binding every assertion to a persistent execution trace.

### Setup with Job Binding

```go
package main

import (
    "context"
    "github.com/orchard9/stemedb-go/steme"
)

func main() {
    // 1. Bind to a Persistent Job (The "Interaction Object")
    // This allows MCP/SSE clients to track progress in real-time.
    ctx := steme.BindJob(context.Background(), "job-uuid-123")
    
    // 2. Initialize Paradigm Context
    ctx = steme.NewContext(ctx, steme.Config{
        Project: "data-migration-v1",
        AgentID: "worker-01",
        // 3. Set Default Lens (Shared Reality)
        // Agents default to Consensus to ensure they "hallucinate together"
        DefaultLens: steme.LensConsensus,
    })
    
    // Updates status to "INDEXING" automatically via MCP
    steme.UpdateStatus(ctx, steme.StatusIndexing)
    
    // ... run app ...
}
```

---

## 2. Durable Execution (The Auto-Resume Pattern)

Stop writing checkpointing logic. Let the DB handle state continuity.

```go
type FileProcessor struct {
    steme.Task // Embed Steme tracking
}

func (p *FileProcessor) Process(ctx context.Context, files []string) {
    // PRE-FLIGHT CHECK: Lens::Constraints
    // Before doing ANY work, check for constraints on this domain.
    // This prevents the "Context Drift" problem where agents forget rules.
    constraints := steme.Query(ctx, steme.Query{
        Subject: "FileProcessing",
        Lens:    "Constraints", // Returns 'must_use', 'forbidden', etc.
    })
    
    if err := p.validateAgainst(constraints); err != nil {
        panic(err) // Fail fast if constraints violated
    }
    
    for _, file := range files {
        // 1. Check Reality: Is this done in the current Epoch?
        if steme.IsDone(ctx, file) {
            continue // Auto-skip (Durable Execution)
        }

        // 2. Visual Anchoring (Handling "Entropy of the Wild Web")
        // Anchors the assertion to a Perceptual Hash (pHash) of the source.
        snapshot := captureScreenshot(file)
        
        // 3. Assert with Proof AND Lifecycle
        steme.Assert(ctx, file, "status", "PROCESSED",
            steme.WithVisualProof(snapshot), // Stores pHash
            steme.WithConfidence(0.95),
            steme.WithLifecycle(steme.LifecycleApproved), // Explicitly mark as Done
        )
    }
}
```

---

## 3. Querying with Intent (The Agile Team Pattern)

Don't just ask "what is X?". Ask "what is the *approved* X?".

### Implementation Agent (Safety First)
```go
// The developer agent needs the definitive answer, not proposals.
algo := steme.Query(ctx, steme.Query{
    Subject:   "auth/jwt",
    Predicate: "signing_algorithm",
    Lens:      "Authority",
    Lifecycle: steme.LifecycleApproved, // Filters out RFCs/Proposals
})
// Returns "RS256" (Production Config)
```

### Research Agent (Broad Search)
```go
// The researcher wants to know about upcoming changes.
proposals := steme.Query(ctx, steme.Query{
    Subject:   "auth/jwt",
    Predicate: "signing_algorithm",
    Lens:      "Recency",
    Lifecycle: steme.LifecycleProposed, // Specific search for RFCs
})
// Returns "ES256" (The RFC)
```

---

## 4. The "Time Travel" Debugger (SRE Tool)

When an incident occurs, you must reproduce the exact state of the world at the time of failure.

```go
func DebugIncident(ctx context.Context) {
    // 1. Create a "Lens" to view the past
    // "Show me the state of the world as of yesterday 2 PM"
    // This allows the SRE to see exactly what the Agent saw.
    pastContext := steme.TimeTravel(ctx, "2023-10-24T14:00:00Z")

    // 2. Query exactly as if you were live
    status := steme.Get(pastContext, "Task-Auth", "status")
    
    // 3. Audit the decision trail
    trace := steme.GetAuditTrace(ctx, "deployment-agent-01")
    fmt.Printf("Agent queried %s and got result %s", trace.Query, trace.Result)
}
```

---

## 5. The "Paradigm Shift" (Bulk Invalidation)

Handling massive changes (e.g., deprecating an API version) is a single API call.

```go
func PivotToV2(ctx context.Context) {
    // Supersede the entire "V1" Epoch
    err := steme.SupersedeEpoch(ctx, steme.SupersedeReq{
        OldEpoch: "api-v1-semantics",
        NewEpoch: "api-v2-semantics",
        Type:     steme.SupersessionInvalidate, // "V1 was wrong"
        Reason:   "Security Vulnerability",
    })
}
```