Documentation
¶
Overview ¶
Package telemetry ports Pi's explicit-parent, callback-scoped telemetry to Go. The zero Context is inert; NewInMemory records span snapshots. It has no dependency on a JavaScript runtime or on the application.
Index ¶
- Constants
- func StartSpan[T any](c Context, options SpanOptions, callback func(*Span) (T, error)) (value T, err error)
- func StartSpanFrom[T any](c Context, read func() SpanOptions, callback func(*Span) (T, error)) (value T, err error)
- func StartTypedSpan[T any](starter SpanStarter, name string, attributes Attributes, ...) (value T, err error)
- func StringifyValue(value any) ([]byte, error)
- func WithContext(ctx context.Context, parent Context) context.Context
- type Array
- type AttributeDefinition
- type Attributes
- type Context
- type ContextCallbacks
- type ErrorDetails
- func (e *ErrorDetails) Error() string
- func (e ErrorDetails) MarshalJSON() ([]byte, error)
- func (e ErrorDetails) MessageValue() any
- func (e ErrorDetails) NameValue() any
- func (e *ErrorDetails) SetMessageValue(value any)
- func (e *ErrorDetails) SetNameValue(value any)
- func (e *ErrorDetails) UnmarshalJSON(data []byte) error
- type EventAttributeDefinition
- type EventDefinition
- type InMemory
- type JSONMethod
- type Object
- type ParentDefinition
- type Property
- type RecordedEvent
- type RecordedSpan
- type SchemaDefinition
- type Span
- func (s *Span) AddEvent(name string, attributes Attributes)
- func (s *Span) AddEventFrom(name string, read func() Attributes)
- func (s *Span) Context() Context
- func (s *Span) SetAttributes(attributes Attributes)
- func (s *Span) SetAttributesFrom(read func() Attributes)
- func (s *Span) SetStatus(status SpanStatus)
- func (s *Span) SetStatusFrom(read func() SpanStatus)
- func (s *Span) StartSpan(options SpanOptions, callback func(*Span) error) error
- func (s *Span) StartSpanFrom(read func() SpanOptions, callback func(*Span) error) error
- type SpanCallbacks
- type SpanDefinition
- type SpanOptions
- type SpanStarter
- type SpanStatus
- type SpanTiming
- type StartAttributeDefinition
- type StatusDefinition
Constants ¶
const Undefined = jsonjs.Undefined
Undefined represents JavaScript's undefined in attribute payloads. Unlike nil (null), it does not overwrite an existing attribute during SetAttributes. Nested snapshots retain the marker; JSON omits object fields carrying it and emits null for array elements, matching JSON.stringify.
Variables ¶
This section is empty.
Functions ¶
func StartSpan ¶
func StartSpan[T any](c Context, options SpanOptions, callback func(*Span) (T, error)) (value T, err error)
StartSpan preserves a typed callback result as well as its error. The method on Context is the equivalent for callbacks that only return an error.
func StartSpanFrom ¶
func StartSpanFrom[T any](c Context, read func() SpanOptions, callback func(*Span) (T, error)) (value T, err error)
StartSpanFrom preserves the typed callback value and error, as StartSpan does.
func StartTypedSpan ¶
func StartTypedSpan[T any](starter SpanStarter, name string, attributes Attributes, callback func(*Span, SpanStarter) (T, error)) (value T, err error)
StartTypedSpan preserves a generic result without boxing it into an interface.
func StringifyValue ¶
StringifyValue preserves JSON.stringify's undefined root as an empty result. Only explicit JSONMethod values stored as toJSON hooks can execute on export.
Types ¶
type AttributeDefinition ¶
type AttributeDefinition struct {
Type string `json:"type"`
Description string `json:"description"`
Sensitive *bool `json:"sensitive,omitempty"`
Cardinality string `json:"cardinality,omitempty"`
Values json.RawMessage `json:"values,omitempty"`
ElementValues json.RawMessage `json:"elementValues,omitempty"`
Examples json.RawMessage `json:"examples,omitempty"`
}
AttributeDefinition is the serializable schema metadata from Pi. Values, ElementValues and Examples retain the JSON shape of their selected Type: scalar examples are arrays, array examples are arrays of arrays. Metadata describes instrumentation; it never causes runtime validation or redaction.
type Attributes ¶
type Attributes = jsonjs.ObjectValue
Attributes records Pi's scalar and array attributes. Like Pi's runtime, it also accepts JSON-shaped objects, mixed arrays and nested values without imposing the TypeScript declaration as runtime validation. Attribute objects and outer arrays are copied; nested objects/arrays retain shared identity. NewAttributes and its Get/Lookup/Set/Delete/Entries methods retain property insertion order, with numeric index keys enumerated first. The zero value is empty. NewArray retains shared length and indexed mutations. Decoded arrays use *Array; direct array attributes are spread-copied, while nested arrays stay shared. A nil value represents null. Undefined omits an attribute, including during a merge; nested object fields omit Undefined and array elements export it as null. Function values remain in memory; JSON omits object fields and uses null for array elements without invoking the function. Numeric Go types share one category; []any may mix numeric widths. JSON uses binary64 numbers (including integer rounding), nonfinite values become null, and byte slices remain numeric arrays. In-memory snapshots keep Go types. JSON decoding creates binary64 values, retaining overflow and signed zero; a successful decode replaces the object, and a failed decode leaves it untouched. Decoded lone UTF-16 surrogates use WTF-8 bytes in strings and map keys. Attribute JSON export preserves them; ordinary Go rune iteration does not. Callers must synchronize access to shared input/snapshot maps and slices.
func NewAttributes ¶
func NewAttributes(properties ...Property) Attributes
type Context ¶
type Context struct {
// contains filtered or unexported fields
}
Context identifies an explicit parent. Copies share the same recording scope; there is no global recorder or implicit goroutine-local parent.
func FromContext ¶
func NewContext ¶
func NewContext(start func(SpanOptions, func(*Span) error) error) Context
NewContext binds a backend's synchronous callback-scoped span operation. The backend owns settlement, passivity, and explicit child parentage. A nil function gives the same no-op behavior as the zero Context.
func NewContextWithCallbacks ¶
func NewContextWithCallbacks(callbacks ContextCallbacks) Context
NewContextWithCallbacks binds a backend that supports deferred option reads. NewContext is the equivalent constructor for an eager-only backend.
func (Context) StartSpan ¶
func (c Context) StartSpan(options SpanOptions, callback func(*Span) error) (err error)
StartSpan invokes callback exactly once in the calling goroutine. Returning an error or panicking settles the span without changing the error/panic value. Child work that should belong to this span must start before callback returns.
func (Context) StartSpanFrom ¶
func (c Context) StartSpanFrom(read func() SpanOptions, callback func(*Span) error) error
StartSpanFrom reads options only when this context can admit a span. A read panic falls back to no-op telemetry, without allocating an ID or changing the callback's result. The callback still runs exactly once. Readers run without the recorder lock and may create other spans; those are admitted first. Concurrent parent settlement wins over a reader that has not yet returned.
type ContextCallbacks ¶
type ContextCallbacks struct {
StartSpan func(SpanOptions, func(*Span) error) error
StartSpanFrom func(func() SpanOptions, func(*Span) error) error
}
ContextCallbacks supplies eager and deferred span admission for a backend. Backends own settlement, read passivity and child parentage. A missing operation invokes the user's callback with a no-op span; an absent deferred operation also leaves its options reader uncalled.
type ErrorDetails ¶
type ErrorDetails struct {
Name string `json:"name"`
Message string `json:"message"`
// contains filtered or unexported fields
}
func (*ErrorDetails) Error ¶
func (e *ErrorDetails) Error() string
Error preserves an explicitly named failure when adapting serialized Pi errors. Ordinary Go errors continue to use the default name "Error".
func (ErrorDetails) MarshalJSON ¶
func (e ErrorDetails) MarshalJSON() ([]byte, error)
func (ErrorDetails) MessageValue ¶
func (e ErrorDetails) MessageValue() any
func (ErrorDetails) NameValue ¶
func (e ErrorDetails) NameValue() any
NameValue and MessageValue expose the actual JS-shaped fields, including Undefined for absent fields and shared *Object/*Array values. Name/Message remain convenient string projections for ordinary Go errors.
func (*ErrorDetails) SetMessageValue ¶
func (e *ErrorDetails) SetMessageValue(value any)
func (*ErrorDetails) SetNameValue ¶
func (e *ErrorDetails) SetNameValue(value any)
SetNameValue and SetMessageValue replace only this error's field. They also distinguish explicit empty strings, null and Undefined from an unchanged Go zero value. Nested edits through the returned object/array stay shared.
func (*ErrorDetails) UnmarshalJSON ¶
func (e *ErrorDetails) UnmarshalJSON(data []byte) error
type EventAttributeDefinition ¶
type EventAttributeDefinition = StartAttributeDefinition
type EventDefinition ¶
type EventDefinition struct {
Description string `json:"description"`
Attributes map[string]EventAttributeDefinition `json:"attributes"`
}
type InMemory ¶
type InMemory struct {
Context
}
InMemory owns one isolated recording scope. Spans are retained for its lifetime, just as in Pi's reference adapter.
func NewInMemory ¶
func NewInMemory() *InMemory
func (*InMemory) GetSpanTimings ¶
func (m *InMemory) GetSpanTimings() []SpanTiming
GetSpanTimings returns settled span timings in start order. Active and no-op spans have no completed timing. Durations use Go's monotonic clock and each snapshot is independent of future recording.
func (*InMemory) GetSpans ¶
func (m *InMemory) GetSpans() []RecordedSpan
GetSpans returns snapshots in start order, including active spans. Attribute maps and outer arrays are detached; nested objects/arrays remain shared, as with Pi's shallow copy. Callers must synchronize edits to shared payloads.
type JSONMethod ¶
type JSONMethod = jsonjs.JSONMethod
type ParentDefinition ¶
func (ParentDefinition) MarshalJSON ¶
func (p ParentDefinition) MarshalJSON() ([]byte, error)
An explicit empty spans list is distinct from an absent list in the union.
type Property ¶
Property, Object and Array share the native JSON value implementation used by agent arguments. No JavaScript runtime or interface hierarchy is involved.
type RecordedEvent ¶
type RecordedEvent struct {
Name string `json:"name"`
Attributes Attributes `json:"attributes"`
}
func (RecordedEvent) MarshalJSON ¶
func (e RecordedEvent) MarshalJSON() ([]byte, error)
func (*RecordedEvent) UnmarshalJSON ¶
func (e *RecordedEvent) UnmarshalJSON(raw []byte) error
type RecordedSpan ¶
type RecordedSpan struct {
ID int `json:"id"`
ParentID *int `json:"parentId"`
Name string `json:"name"`
Attributes Attributes `json:"attributes"`
Events []RecordedEvent `json:"events"`
Status SpanStatus `json:"status"`
Settled bool `json:"settled"`
EndSequence *int `json:"endSequence,omitempty"`
}
func (RecordedSpan) MarshalJSON ¶
func (s RecordedSpan) MarshalJSON() ([]byte, error)
func (*RecordedSpan) UnmarshalJSON ¶
func (s *RecordedSpan) UnmarshalJSON(raw []byte) error
type SchemaDefinition ¶
type SchemaDefinition struct {
Version float64 `json:"version"`
Spans map[string]SpanDefinition `json:"spans"`
}
func DefineSchema ¶
func DefineSchema(schema *SchemaDefinition) *SchemaDefinition
DefineSchema is Pi's identity helper. No cloning, normalization, validation, or schema access occurs; the same pointer is returned.
type Span ¶
type Span struct {
// contains filtered or unexported fields
}
Span is valid as a recording parent until its callback returns. Retaining it is safe: later mutations are inert, and later child callbacks still execute.
func NewSpan ¶
func NewSpan(children Context, callbacks SpanCallbacks) *Span
NewSpan constructs a backend span with its explicit child context. It does not add lifecycle behavior; that belongs to the backend's start function.
func (*Span) AddEvent ¶
func (s *Span) AddEvent(name string, attributes Attributes)
func (*Span) AddEventFrom ¶
func (s *Span) AddEventFrom(name string, read func() Attributes)
AddEventFrom reads attributes only while recording is active. A read panic suppresses the outer event; nested events already emitted by the reader stay in order. No recorder lock is held while invoking the reader. An event is ignored if its span settles before the reader returns.
func (*Span) SetAttributes ¶
func (s *Span) SetAttributes(attributes Attributes)
func (*Span) SetAttributesFrom ¶
func (s *Span) SetAttributesFrom(read func() Attributes)
SetAttributesFrom defers reading an incoming attribute set until recording is active. Like Pi's property reads, a panic discards the outer update while retaining any reentrant mutations the reader already made. A successful read merges into the attributes captured before reading, so reentrant attribute updates are overwritten by that outer merge. Events and status are unaffected. Readers run without the recorder lock; concurrent settlement wins.
func (*Span) SetStatus ¶
func (s *Span) SetStatus(status SpanStatus)
func (*Span) SetStatusFrom ¶
func (s *Span) SetStatusFrom(read func() SpanStatus)
SetStatusFrom reads a status only when recording is active. It is the Go equivalent of Pi reading a status object with user-defined getters. A reader panic is passive: no outer status/explicit-status change is applied, while the reader's own reentrant mutations remain. Readers run without the recorder lock, so they may record events, set a nested status or inspect snapshots. Concurrent settlement wins over a reader that has not yet returned. Callback backends implement admission through SpanCallbacks.SetStatusFrom.
func (*Span) StartSpan ¶
func (s *Span) StartSpan(options SpanOptions, callback func(*Span) error) error
func (*Span) StartSpanFrom ¶
func (s *Span) StartSpanFrom(read func() SpanOptions, callback func(*Span) error) error
StartSpanFrom creates a child using deferred options and explicit parentage.
type SpanCallbacks ¶
type SpanCallbacks struct {
AddEvent func(string, Attributes)
SetAttributes func(Attributes)
SetStatus func(SpanStatus)
// Deferred reads own admission, including skipping reads after settlement
// and suppressing read failures. Nil retains the supplied context's default
// behavior (inert for an opaque backend).
SetStatusFrom func(func() SpanStatus)
SetAttributesFrom func(func() Attributes)
AddEventFrom func(string, func() Attributes)
}
SpanCallbacks are the mutation operations supplied by a telemetry backend. Provided callbacks override native recorder operations; opaque contexts leave missing operations inert. Backends must ignore mutations after settlement and suppress recording failures without changing the user's callback result.
type SpanDefinition ¶
type SpanDefinition struct {
Description string `json:"description"`
Parents ParentDefinition `json:"parents"`
StartAttributes map[string]StartAttributeDefinition `json:"startAttributes"`
EndAttributes map[string]AttributeDefinition `json:"endAttributes"`
Events map[string]EventDefinition `json:"events,omitempty"`
Status StatusDefinition `json:"status"`
}
func (SpanDefinition) MarshalJSON ¶
func (s SpanDefinition) MarshalJSON() ([]byte, error)
type SpanOptions ¶
type SpanOptions struct {
Name string `json:"name"`
Attributes Attributes `json:"attributes,omitzero"`
}
func (SpanOptions) MarshalJSON ¶
func (o SpanOptions) MarshalJSON() ([]byte, error)
func (*SpanOptions) UnmarshalJSON ¶
func (o *SpanOptions) UnmarshalJSON(raw []byte) error
type SpanStarter ¶
type SpanStarter struct {
// contains filtered or unexported fields
}
SpanStarter binds one explicit parent context. Schema values are deliberately unread, as in createTypedSpanStarter. Go does not infer literal attribute types from schema values; use application-owned typed wrappers when needed. It must not introduce runtime validation absent from Pi's implementation.
func CreateTypedSpanStarter ¶
func CreateTypedSpanStarter(parent Context, _ ...*SchemaDefinition) SpanStarter
func (SpanStarter) StartSpan ¶
func (s SpanStarter) StartSpan(name string, attributes Attributes, callback func(*Span, SpanStarter) error) error
StartSpan supplies a child starter bound to the newly admitted span. Saving that starter does not extend the span's lifetime; late children remain no-op.
type SpanStatus ¶
type SpanStatus struct {
Status string `json:"status"`
Error *ErrorDetails `json:"error,omitempty"`
// contains filtered or unexported fields
}
func (SpanStatus) MarshalJSON ¶
func (s SpanStatus) MarshalJSON() ([]byte, error)
func (*SpanStatus) UnmarshalJSON ¶
func (s *SpanStatus) UnmarshalJSON(data []byte) error
UnmarshalJSON projects serialized status inputs using Pi's property reads. Non-object primitives have no status/error properties; null is unreadable and SetStatus ignores it. Truthy errors copy only their name/message properties.
type SpanTiming ¶
type SpanTiming struct {
SpanID int `json:"span_id"`
StartedAt time.Time `json:"started_at"`
Duration time.Duration `json:"duration_ns"`
}
SpanTiming is a detached timing for a settled span. It is kept separately from RecordedSpan so Pi-compatible records retain their original JSON shape.
type StartAttributeDefinition ¶
type StartAttributeDefinition struct {
AttributeDefinition
Required bool `json:"required"`
}
type StatusDefinition ¶
Source Files
¶
Directories
¶
| Path | Synopsis |
|---|---|
|
Package export delivers completed telemetry scopes to host-owned sinks.
|
Package export delivers completed telemetry scopes to host-owned sinks. |
|
Package llm defines the export format for model-call telemetry.
|
Package llm defines the export format for model-call telemetry. |
|
Package telemetrytest provides runner-independent conformance cases for Go telemetry adapters, ported from Pi's telemetry/testing entry point.
|
Package telemetrytest provides runner-independent conformance cases for Go telemetry adapters, ported from Pi's telemetry/testing entry point. |