# FAQ (/docs/faq)



## What is `@pleach/core`? [#what-is-pleachcore]

A TypeScript-first agent runtime substrate published under the
`@pleach/*` scope on npm. It treats every LLM call inside an
agent as classifiable, auditable, and replayable — sessions,
checkpointing, reactive channels, family-locked model routing,
and an append-only per-call audit ledger.

The contract is language-agnostic by design. The TypeScript
distribution is the reference implementation, in production today.
A Go implementation has been built against the same contract and
round-trips a shared corpus of recorded turns — proof the wire
shapes aren't TypeScript-flavored. The Go implementation isn't
published as a SKU yet; an official `@pleach` Go runtime is the
next planned published implementation.

## How is this different from the Vercel AI SDK? [#how-is-this-different-from-the-vercel-ai-sdk]

Pleach wraps the AI SDK; it doesn't replace it. `AiSdkProvider`
keeps the AI SDK as your provider layer, and the runtime adds
what sits around it: sessions, family-locked routing, the
four-stage lattice, the audit ledger, replay determinism, and
checkpointing.

If your app is "chat with tools and stream the response," reach
for the AI SDK. If you need per-call audit, per-turn cost
attribution, replay determinism, or family-locked routing,
`@pleach/core` is doing structural work the AI SDK isn't built
for. The concrete shape difference: an AI SDK `streamText` call
returns a stream of text deltas and tool events with no shared
identity tuple; an `executeMessage` call yields the same surface
shape but every call beneath it lands as a row keyed on
`(sessionId, turnId, stageId, seqWithinTurn)` — that's the join
key the AI SDK doesn't ship.

See [Comparison](/docs/comparison) and [Migrating from the AI SDK](/docs/migrating-from-ai-sdk).

## How does this compare to Claude Code, Goose, OpenHands, AutoGen, CrewAI? [#how-does-this-compare-to-claude-code-goose-openhands-autogen-crewai]

Different category. Those are *agent harnesses* — complete
running products you launch and use. `@pleach/core` is the
*substrate* one layer below: the primitives a harness is built
on. If you're the end user, install a harness. If you're
shipping a customer-facing agent product where each tenant
needs their own session, audit trail, and invoice, the harness's
session log isn't the row shape you need.

See [Comparison → Agent harnesses](/docs/comparison#agent-harnesses-a-different-category) for the capability matrix.

## Is this open source? What's the license? [#is-this-open-source-whats-the-license]

Yes — every shipping `@pleach/*` package ships under
**FSL-1.1-Apache-2.0** (Functional Source License with Apache 2.0
as the future license). FSL is source-available, usable in
production, free of charge during the FSL window; the only
restriction is on competing offerings. Each package auto-
transitions to permissive Apache 2.0 two years after first stable
publish.

`@pleach/trust-pack` alone remains a `0.0.1 · UNLICENSED`
placeholder; it'll ship FSL-1.1-Apache-2.0 when its first cut
lands.

## Does Pleach replace my Anthropic or OpenAI Enterprise contract? [#does-pleach-replace-my-anthropic-or-openai-enterprise-contract]

No — it composes underneath. SSO/SAML, ZDR, Workspaces or
Projects, the Admin / Usage API, dedicated capacity, prompt
caching, snapshot pinning all keep doing their job. Pleach adds
the three things the vendor contract doesn't cover: per-axis
rollup by `tenantId` inside one Workspace or Project (external
customers in a SaaS, or employees, teams, and cost centers when
used internally), a hash-chained `AuditableCall` row in your own
Postgres, and replay-deterministic regression across model
snapshots. No new vendor on the security questionnaire — npm
install plus a table. See
[Migrating from Anthropic Enterprise](/docs/migrating-from-anthropic-enterprise)
and [Migrating from OpenAI Enterprise](/docs/migrating-from-openai-enterprise).

## Who's behind this? [#whos-behind-this]

`@pleach/*` is the public FSL-1.1-Apache-2.0 source-available
ecosystem (auto-transitions to Apache 2.0 two years after first
stable publish). The
substrate was extracted from a production agent runtime and generalized; the
upstream deployment is one private consumer of many possible.
Contact for both general questions and security disclosures:
`getpleach@protonmail.com`.

## What can I build with this? [#what-can-i-build-with-this]

Anything that wants the structural guarantees:

* A multi-tenant AI product where finance needs per-customer
  invoicing.
* A regulated agent surface where a compliance team will ask
  "show me every decision this session made."
* A long-running agent with planning + tool loop + synthesis +
  safety review, where each step needs to be observable.
* An eval / regression-test loop replaying production failures.
* A product mid-migration between providers that can't break
  tool-call dialect mid-conversation.
* An offline-first browser app needing IndexedDB sync.
* Stuck-session debugging where you need to rewind and try
  a different path.

What you're probably *not* building if `@pleach/core` is overkill:

* A single-shot RAG bot (query → paragraph). Use the AI SDK.
* A static workflow with fixed branches. Use Temporal or Inngest.
* A chat UI with no tools and no audit needs. Use `streamText`.

See the README's "Who is this for?" table for the long version.

## Is this designed for AI agents to use? [#is-this-designed-for-ai-agents-to-use]

Yes — agents are first-class consumers, not bolted on. Every
`AuditableCall` row is a typed record; `turnId`, `toolName`,
`subagentDepth`, and `tokenUsage` are addressable from code the
same way they're addressable in SQL. `SpawnTreeState` rolls
nested-spawn cost back to the parent `turnId`, so an agent
reading its own trace sees recursion as a tree, not a flattened
log.

The runtime also lets an agent debug itself: the deterministic
fingerprint stream replays last week's failure against this
week's prompt byte-identically; per-channel `checkpoint()` /
`restore()` under `window.__HARNESS_DEVTOOLS__` rewinds from
before a bad decision instead of escalating to a human. This
site renders to `/llms.txt` and `/llms-full.txt` — an agent
ingesting Pleach reads the docs themselves, not a stripped
sitemap.

The reference distribution is TypeScript a developer can read.
The same surface — typed rows, deterministic fingerprints,
checkpoints — is what an agent reads from code. Agent-friendly
first; usable by devs because devs read the same surface.

`@pleach/core` itself is written largely by agents under that
surface. The four-stage lattice fails CI on out-of-lattice
edges; the audit ledger makes the agent-written code reviewable
in SQL. The runtime authored by agents is the same one
auditable by humans.

## Why does it require so many decisions up front? [#why-does-it-require-so-many-decisions-up-front]

It doesn't. With zero config, `new SessionRuntime()` wires
in-memory adapters and runs. You add a provider, a storage
adapter, plugins, and safety policies *when you need them*.
Every `SessionRuntimeConfig` field except the implicit defaults
is optional.

The reference docs surface the full config space because that's
their job; the actual happy-path setup is small. The [Getting
started](/docs/getting-started) page is six lines of code.

## Why the 4-stage lattice? Isn't it limiting? [#why-the-4-stage-lattice-isnt-it-limiting]

The lattice is what makes cost allocation, observability, and
time-travel *structural* instead of bolted on. Once stages are
declared, you can budget a turn's `synthesize` calls
independently from its `tool-loop` calls, slice the audit ledger
by stage, and rewind to the start of `synthesize` to re-run.
"Slice the audit ledger by stage" is a literal SQL move: every
row in `harness_auditable_calls` carries a non-null `stage_id`
drawn from the four lattice members, so `GROUP BY stage_id`
gives you a real partition. There's no second source of truth
for which stage a call belonged to.

If you don't need those properties, yes — the lattice is
overhead. The substrate is overkill for "I want a chat shell
with tools." See [Architecture](/docs/architecture) §1.

## Why exactly one `synthesize` call per turn? [#why-exactly-one-synthesize-call-per-turn]

Because the user sees the synthesis. If the runtime fires two
`synthesize` calls and shows one of them, the audit ledger and
the rendered UI disagree on what the model said. Structurally
capping at one means the rendered string and the audited string
are the same string.

Sequential plan-then-verify chains land via an upcoming
per-runtime synthesize policy; concurrent debate topologies
(many synthesizers per turn, agent-handoff networks) are v1.1+
work.

## Why family-locked routing? [#why-family-locked-routing]

Because tokenizer, prompt-cache key, tool-call dialect, and
refusal pattern differ across families (Anthropic vs OpenAI vs
Google). When a provider fails mid-conversation and the cascade
silently widens to a different family, the tool dialect changes
and tools that worked stop working. The lock makes the cascade
walk in-family rungs only; cross-family widening is explicit and
visible.

See [Model resolution matrix](/docs/model-resolution-matrix).

## Why a separate `AuditableCall` ledger from the event log? [#why-a-separate-auditablecall-ledger-from-the-event-log]

Two distinct concerns. The event log is the broader stream of
*observable events* (messages, tools, interrupts); the audit
ledger records *load-bearing decisions* (which model fired, why,
with what fingerprint, against which policy).

A regulator's "show me every decision this session made" question
has a one-row-per-call answer from the ledger that doesn't
require event-log archeology. See [Event log](/docs/event-log)
and [AuditableCall row](/docs/auditable-call-row).

## Can I use this without Supabase? [#can-i-use-this-without-supabase]

Yes. `MemoryAdapter` and `MemorySaver` cover testing and dev;
`IndexedDBAdapter` and `IndexedDBSaver` cover browser apps;
`SupabaseAdapter` and `SupabaseSaver` cover server production.

Custom adapters are one interface away. See the SQLite recipe in
[Recipes](/docs/recipes) for a complete custom-adapter example.

## Can I use this with my own LLM provider? [#can-i-use-this-with-my-own-llm-provider]

Yes. `AiSdkProvider` covers any AI SDK provider (Anthropic,
OpenAI, Google, Mistral, xAI, Groq, Bedrock, plus community
providers); `AnthropicSdkProvider` wraps Anthropic's SDK
directly; `AgentProvider` is the interface for everything else
(local Ollama, a custom gateway, your own SDK wrapper).

See [Providers](/docs/providers).

## Can I use this without React? [#can-i-use-this-without-react]

Yes. `@pleach/core/react` is one subpath; the rest of the
runtime is framework-agnostic. Server-rendered apps,
Svelte/Vue/Solid frontends, native mobile clients, and CLI
tools all consume the runtime through its async-iterator
stream and the HTTP+SSE wire contract.

See [API routes](/docs/api-routes) for the wire shapes any
language can implement.

## Does it work with Edge runtimes? [#does-it-work-with-edge-runtimes]

Yes. The substrate avoids Node-only APIs in its hot path —
`fingerprint`, `channels`, `audit`, `prompt-builder` are all
isomorphic. Supabase + Anthropic SDKs both run on edge runtimes;
the storage adapter uses Web Crypto explicitly. The
fingerprint module reaches `globalThis.crypto.subtle` rather
than Node's `node:crypto`, which is why a recorded turn under
Node and the same turn replayed under Cloudflare Workers produce
the same fingerprint stream — same hash function, same input
canonicalization, same byte output.

See [Deployment](/docs/deployment).

## Why FSL-1.1-Apache-2.0? [#why-fsl-11-apache-20]

Every shipping `@pleach/*` package publishes under FSL-1.1-
Apache-2.0 — the Functional Source License with Apache 2.0 as
the future license. Source-available, usable in production, free
of charge during the FSL window; the only restriction is on
competing offerings. Each package auto-transitions to permissive
Apache 2.0 two years after first stable publish. Pre-`0.1.0`
placeholder publishes (`0.0.1`) carried the FSL grant under the
same posture. See the [fair-source post-mortem](/blog/why-fair-source)
for the reasoning behind the license-posture history.

## Can I contribute? [#can-i-contribute]

Yes. The upstream source is at
[github.com/pleachhq/core](https://github.com/pleachhq/core).
Bug reports, feature requests, and PRs are welcome. The
upstream `CONTRIBUTING.md` documents the workflow.

For sibling SKUs that aren't published yet, the design is
tracked in upstream planning docs; opening an issue with your
use case helps prioritize the publish wave.

## Where do I report security issues? [#where-do-i-report-security-issues]

`getpleach@protonmail.com`. The upstream `SECURITY.md` documents
the disclosure policy — initial acknowledgement within two
business days, a fix-or-mitigation plan for confirmed reports,
and a CVE filed when a published `@pleach/*` package needs one.
No paid bug-bounty program today; reports get a real response,
not a payout.

## Is there a hosted version? [#is-there-a-hosted-version]

Not today; in development. `@pleach/gateway@0.1.0` ships
the self-hostable routing substrate — `GatewayClient` wraps
`@pleach/core`'s model-family substrate with per-tenant BYOK key
routing, family-strict cascade pivot, per-call cost emission
(`domain.gateway.cost.recorded`), and OTel `llm.invocation` span
emission. See [Gateway](/docs/gateway) for the surface.
`@pleach/observe@0.1.0` ships as a destination-flexible
brownfield SDK — buyers write `AuditableCall` rows to their own
Postgres, Supabase, OTel collector, or any custom destination;
the SDK layer stays free.

The hosted products on the roadmap are enterprise products:

* **Hosted Gateway** — multi-tenant routing, per-tenant cost
  caps, provider failover. Per-tenant subscription pricing with
  optional consolidated billing on dollars Pleach holds; **no
  markup on inference** (BYO-key buyers route through the gateway
  at provider list price).
* **Hosted Observe at enterprise scope** — SSO/SAML/SCIM,
  multi-seat dashboards, retention SLAs, SOC 2 wrapper,
  signed audit retention, per-tenant evidence pack export. The
  managed export bridge routes audit rows into the review surface
  your team already runs (Datadog, Splunk, Grafana, SIEM, or
  custom destination). **Compliance attestation is bundled
  inside Hosted Observe Enterprise, not sold as a separate SKU** —
  the agent-runtime-specific axes (`AuditableCall` row +
  `subagentDepth` + `tenantId`) are the wedge that makes it
  defensible alongside Vanta or Drata, but they don't carry a
  separate procurement line item.
* **Marketplace bundles** — AWS, Azure, GCP. Procurement-readable
  packaging of the hosted products on the buyer's preferred cloud
  contract surface.

Self-serve tiers for smaller teams are in development. Pricing
specifics land on `/pricing` before they ship.

None of these gate runtime features. The runtime stays
trust-protected: no telemetry phone-home, no remote license
check, no account required to run, and no retro-paywall on a
release that already shipped. FSL-1.1-Apache-2.0 is irrevocable
per release — `npm install @pleach/core@<version>` works forever,
and that version's two-year clock to Apache 2.0 keeps ticking
independently.

## How do I stay updated? [#how-do-i-stay-updated]

* The upstream `CHANGELOG.md` on every `@pleach/*` package.
* The `pleachhq/core` repo's releases page.
* Security: `getpleach@protonmail.com` for advisories.

There's no marketing list. The packages are the canonical
broadcast surface.

## Capabilities [#capabilities]

<Accordions type="single">
  <Accordion title="Is @pleach/compliance shipping today?" id="is-pleachcompliance-shipping-today">
    Yes — `@pleach/compliance` ships a four-scrubber bundle (`SSN-US`,
    `Luhn`, `US-DL`, `KeyedRegex`) plus two inherited CI audit gates
    (`audit:tenant-scoping`,
    `audit:harness-event-log-tenant-id-required`). Wider scope (gateway
    integration, additional scrubbers, evidence exports) is planned
    but out of scope for the 1.0 cut.

    See [Compliance](/docs/compliance).
  </Accordion>

  <Accordion title="Do I need to wire OpenTelemetry myself, or is it built in?" id="do-i-need-to-wire-opentelemetry-myself-or-is-it-built-in">
    The substrate emits four span types directly (`session.turn`,
    `llm.invocation`, `graph.stage`, `tool.execution`) — wiring them
    to a backend is one OTLP exporter call. The `runtime.spans` facet
    reads spans in-process without an exporter for tests and DevTools.

    See [OTel observability](/docs/otel-observability).
  </Accordion>

  <Accordion title="Is the in-memory cache safe for production?" id="is-the-in-memory-cache-safe-for-production">
    Yes — `memoryCacheBackend` is now the substrate default with a
    1000-entry / 64 MB cap. For multi-process or multi-region
    deployments where a single process's cache is too narrow, swap
    in a Redis-backed `CacheBackend` implementation. The contract is
    two methods (`get`, `set`) plus a `metricsSnapshot()`.

    See [Cache](/docs/cache).
  </Accordion>

  <Accordion title="Does the hash chain verify in real time?" id="does-the-hash-chain-verify-in-real-time">
    No — the chain is an after-the-fact tamper detector. Writer-side
    stamping is in soak behind the `c9PhaseBEnabled` flag;
    `@pleach/core/eventLog` ships `verifyChainForChat` + `generateProof`
    to walk the chain in code today. The recursive-CTE SQL pattern on
    the [Hash chain](/docs/hash-chain) page is the manual fallback.
    Real-time write integrity is a runtime-attestation problem and
    out of scope for the chain (see
    [Attestation](/docs/attestation)).
  </Accordion>

  <Accordion title="How do I add multi-tenancy without rewriting the runtime?" id="how-do-i-add-multi-tenancy-without-rewriting-the-runtime">
    Set `tenantId` (and optionally `subTenantId`) on
    `SessionRuntimeConfig`. The runtime stamps `tenant_id` on every
    event log row, every audit ledger row, every OTel span (as
    `pleach.tenant_id`), and any outbound HTTP that rides through
    `withTenantHeader`. RLS at the database layer is the enforcement;
    the facet provides the value.

    See [Tenant facet](/docs/tenant-facet).
  </Accordion>

  <Accordion title="What's the difference between scrubbers and safety policies?" id="whats-the-difference-between-scrubbers-and-safety-policies">
    Safety policies act on prompt inputs *before* the model sees
    them — they're a synthesis-time concern. Scrubbers act on
    event log writes *before* they hit storage — they're a
    persistence-time concern. A redaction that needs to influence
    what the model generates belongs in a safety policy; a redaction
    that needs to influence what gets persisted belongs in a
    scrubber.

    See [Safety](/docs/safety) and [Scrubbers](/docs/scrubbers).
  </Accordion>

  <Accordion title="My audit ledger rows show payload.kind: &#x22;tokenCost&#x22; — what changed?" id="audit-payload-kind-token-cost-what-changed">
    Five `AuditableCall` payload shapes were promoted from opaque
    JSON to discriminated unions: `InterruptDecisionRecord`,
    `TokenCostRecord`, `ToolSelectionTrace`, `PlanGenerationRecord`,
    `SynthesisQualityRecord`. Narrow via `payload.kind` to get
    per-arm field narrowing. The version log on the audit row tracks
    which bump introduced each shape.

    See [Typed records](/docs/typed-records).
  </Accordion>

  <Accordion title="Can I use @pleach/langchain in production?" id="can-i-use-pleachlangchain-in-production">
    It's published intentionally pre-1.0 — the surface will move
    before 1.0. Pin via `~0.x.y` (allow patch only). The adapter is
    appropriate for hosts running LangChain primitives alongside
    Pleach during a migration; for a one-time conversion off
    LangChain, see the migration guide.

    See [`@pleach/langchain`](/docs/langchain).
  </Accordion>

  <Accordion title="I see runtime.tenant and runtime.getTenantId() — which should I use?" id="runtime-tenant-vs-get-tenant-id">
    Reach for the facet (`runtime.tenant.getTenantId()`). Flat
    methods stay shipped with `@deprecated` JSDoc that points at the
    facet; removal happens at the next major. New consumer code uses
    facets; existing code with `@deprecated` warnings still works
    through the minor series.

    See [Facets](/docs/facets).
  </Accordion>
</Accordions>

## Where to go next [#where-to-go-next]

<Cards>
  <Card title="Getting started" href="/docs/getting-started" description="Six lines of code to a running runtime." />

  <Card title="Architecture" href="/docs/architecture" description="The six pieces of the substrate." />

  <Card title="Comparison" href="/docs/comparison" description="How `@pleach/core` compares to the AI SDK, LangChain, LlamaIndex, Mastra." />

  <Card title="Glossary" href="/docs/glossary" description="Canonical terms — Anchor-plan, CallClass, Family-lock, Seam, and the rest." />

  <Card title="Recipes" href="/docs/recipes" description="End-to-end patterns — custom adapters, multi-tenant wiring, scrubber configuration." />
</Cards>
