Core SDKHow-to guides

Configure SDK observability

Send SDK product events and sanitized failures through a host-owned PostHog client.

Initialize PostHog once in the host, then adapt that existing client:

import { createCapxulClient, postHogObservability } from "@capxul/sdk";

const observability = postHogObservability(posthog, {
  enabled: () => analyticsConsentGranted,
  engineeringEnabled: () => analyticsConsentGranted,
  capxulEnv: "production",
  context: () => ({
    application: "operations-console",
    release: appVersion,
    sessionId,
    organizationId,
    correlationId,
  }),
});

const created = await createCapxulClient({
  publishableKey,
  observability,
});

The module carries SDK product events and captures one sanitized record when a public operation returns a failed result or unexpectedly throws. Delivery is best-effort and cannot change the domain result.

Failures from an observed public Effect include the completed operation's trace_id and span_id. These IDs join the PostHog failure Event to its native Log and APM span. They preserve the person and correlation captured at call start. A host traceparent cannot supply the owning pair. Failures that have no owning span omit the fields.

Do not put email addresses, wallet addresses, URLs, JSON, tokens, or arbitrary messages in observation context. Unsafe values are dropped. The backend derives actor identity from authentication and verifies Organization/application hints.

Backend linkage is deliberately bounded. A configured backend may emit linked engineering events. This behavior does not prove universal backend exception delivery.

Omit observability when the host has no consented analytics destination. The SDK does not initialize PostHog, replay, page views, or global exception capture.

Engineering logs and traces do not add another application prop. The backend optionally supplies a validated PostHog ingest policy in the versioned bootstrap response; missing or invalid policy simply leaves engineering export disabled.

Use engineeringEnabled to apply the host's collection preference to these bootstrap-configured exporters as well. It accepts a boolean or callback. False or a thrown callback stops engineering collection for that client runtime and drops its queued batches. Re-enable by creating a new client. Omit the option to retain existing bootstrap behavior. The enabled option continues to control product events and failure capture.

client.system.health(nonce, { signal }) uses the same production runtime. Its SDK span continues the sanitized traceparent from host context and forwards its native parent context to the operator.diagnostics.health backend action. The action permits the existing bounded OTLP export. Local tests do not prove backend span arrival in PostHog.

For a CLI host that must exclude provider text and filesystem paths, also set engineeringPrivacy: "minimal" on postHogObservability. This optional policy projects every SDK engineering signal before export, including span exception events and log causes. It keeps closed operations and error codes, timings, environment, and validated invocation and native trace correlation. It removes free-form text, bodies, URLs, and source paths. Omission retains the existing credential-redacted diagnostics.

Browser failure capture

The optional failureCapture(event, properties, canonicalWords?) host callback replaces capture only for SDK failures. It runs inside best-effort delivery. Product and bootstrap events still use the existing client. Omit the callback to keep the current behavior.

canonicalWords is a frozen in-process snapshot from the private original CapxulError path. Direct adapter rows and decoded shape-only failures have no snapshot. Only error_message, $exception_message, $issue_description and the first exception value can carry canonical words. A distinct chain-revert description keeps its existing text policy. Details, cause, stack and URLs remain subject to the host privacy hook.

A browser host must supply the same synchronous capture closure to this callback and its before_send wrapper. Bind one pending snapshot to the native PostHog capture UUID, event and operation. Consume it before sanitization and restore only original strings that equal the snapshot. Clear it when capture returns or throws. Deferred, truncated and unmatched events use generic masking. Never serialize the snapshot or infer authority from event fields.

On this page