- orchestrator: Tracer interface with spans for intent analysis, persona, subsession dispatch, context build, LLM streaming and each tool call; traces finish when the stream completes — the admin Trace waterfall finally receives data - background: Thinker generates real LLM thoughts (post-chat + silence triggers, recent history as context, empty/overlong outputs discarded); thoughts broadcast to web clients as 'thinking' WS messages; pipeline postChatHook triggers post-chat thinking after each round - memory: ApplyDecayAll + ListUserIDs with a 6h decay/purge cron in main (was implemented but never scheduled)
58 lines
1.5 KiB
Go
58 lines
1.5 KiB
Go
package main
|
|
|
|
import (
|
|
"time"
|
|
|
|
tracepkg "git.yeij.top/AskaEth/Cyrene_v2/services/ai-core/trace"
|
|
)
|
|
|
|
// traceAdapter adapts trace.Logger to api.TraceLogger.
|
|
type traceAdapter struct{ *tracepkg.Logger }
|
|
|
|
func (a *traceAdapter) Recent(n int) []map[string]any {
|
|
traces := a.Logger.Recent(n)
|
|
result := make([]map[string]any, len(traces))
|
|
for i, t := range traces {
|
|
spans := make([]map[string]any, len(t.Spans))
|
|
for j, s := range t.Spans {
|
|
children := make([]map[string]any, len(s.Children))
|
|
for k, c := range s.Children {
|
|
children[k] = spanToMap(c)
|
|
}
|
|
spans[j] = spanToMap(s)
|
|
if len(children) > 0 { spans[j]["children"] = children }
|
|
}
|
|
result[i] = map[string]any{
|
|
"id": t.ID,
|
|
"user_msg": t.UserMsg,
|
|
"start_time": t.StartTime.Format(time.RFC3339Nano),
|
|
"end_time": nil,
|
|
"status": t.Status,
|
|
"error": t.Error,
|
|
"spans": spans,
|
|
}
|
|
if !t.EndTime.IsZero() {
|
|
result[i]["end_time"] = t.EndTime.Format(time.RFC3339Nano)
|
|
}
|
|
}
|
|
return result
|
|
}
|
|
|
|
func (a *traceAdapter) Clear() { a.Logger.Clear() }
|
|
|
|
// pipelineTracer adapts trace.Logger to orchestrator.Tracer
|
|
// (StartTrace's return value is discarded at the call site).
|
|
type pipelineTracer struct{ *tracepkg.Logger }
|
|
|
|
func (p pipelineTracer) StartTrace(id, userMsg string) { p.Logger.StartTrace(id, userMsg) }
|
|
|
|
func spanToMap(s tracepkg.Span) map[string]any {
|
|
m := map[string]any{
|
|
"name": s.Name, "label": s.Label,
|
|
"start_ms": s.StartMs, "duration_ms": s.Duration,
|
|
"status": s.Status, "detail": s.Detail,
|
|
}
|
|
if s.Data != nil { m["data"] = s.Data }
|
|
return m
|
|
}
|