Releases: fgn/go-langfuse
Release list
v0.4.0
Deterministic whole-trace sampling for isolated mode, with correlated application-level sampling and score coordination. All additions are backward compatible; the default configuration keeps exporting everything.
Added
Config.SampleRate(LANGFUSE_SAMPLE_RATE,[0, 1], nil keeps everything) selects the fraction of traces exported in isolated mode, decided once per trace by a deterministic threshold on the trace ID that matches OpenTelemetry'sTraceIDRatioBasedbit-for-bit.Client.WithSampleRateoverrides the fraction per context path, so one process can export different kinds of traces at different rates. The decision is inherited by every SDK observation in the trace, including across foreign middle spans and later rate changes.TraceSampledAtexposes the same deterministic predicate for correlated application-level sampling: decisions at a smaller fraction are guaranteed subsets of those at a larger one, so work gated at a small fraction runs only on traces kept for export. Strict(bool, error)contract — out-of-range fractions and malformed trace IDs error instead of guessing.Observation.Sampledreports the decision (a sampling decision, not a delivery guarantee).
Changed
- Sampled-out observations keep their trace and span IDs and become cheap no-ops:
UpdateandRecordErrorreturn before serialization,Mask, orError()calls. - A score recorded directly on a sampled-out, SDK-originated context path targeting that trace is suppressed with a once-per-client diagnostic, so sampled-out traces do not accumulate orphaned scores. Session-only, out-of-context, foreign-origin, and all borrowed-mode scores are delivered unchanged.
- Borrowed mode is unaffected: the application's sampler remains authoritative and the new controls are ignored there with a diagnostic.
- A start that misses processor admission or observes the shutdown transition immediately after span start now returns the no-op observation instead of a live handle whose export path is already torn down.
This release also includes the 0.3.0 changelog entries (prompt management reads with client-side caching and fallbacks, Observation.EndAt, score backdating and score configs, and score delivery through the JSON ingestion endpoint), which were recorded earlier but never tagged.
v0.2.0
Scores are now delivered asynchronously with bounded retry, keeping the public API surface identical to v0.1.
Breaking
RecordScorenow validates synchronously and delivers asynchronously with bounded backoff retry instead of performing one blocking request. Returned errors are validation and lifecycle errors only; transport failures are retried (network errors and HTTP 408/429/5xx, honoringRetry-After, with the same backoff defaults as observation export) and, once the retry budget is exhausted, dropped with a payload-free diagnostic instead of returning to the caller.
Changed
FlushandShutdowndrain the new bounded score queue (256 scores).Flushis a call-time barrier: scores recorded after it begins do not extend the wait.Config.BlockOnQueueFullnow also applies to the score queue; by default a full queue drops the score with a diagnostic, matching the span pipeline.- The SDK generates the idempotent upsert ID when
Score.IDis empty, so retried deliveries cannot create duplicate scores. - Score delivery never runs application-pluggable OpenTelemetry error handlers on pipeline goroutines, diagnostics are built from static text and numeric status codes only, and the scores HTTP client never follows redirects.
See CHANGELOG.md and docs/reference.md for the full behavior reference.
Note: the documented live-gate and production-dogfood release gates were waived by the maintainer for this release; the tag was created directly on the CI-green main commit.
v0.1.1
v0.1.0
Full Changelog: https://github.com/fgn/go-langfuse/commits/v0.1.0