persistChatContextSummary is called from the chat loop's compaction callback. activeAPIKeyID is stamped onto the summary user message. When empty, it falls back to the delegated key in ctx.
( ctx context.Context, chatID uuid.UUID, modelConfigID uuid.UUID, activeAPIKeyID string, toolCallID string, result chatloop.CompactionResult, )
| 8464 | // callback. activeAPIKeyID is stamped onto the summary user message. When |
| 8465 | // empty, it falls back to the delegated key in ctx. |
| 8466 | func (p *Server) persistChatContextSummary( |
| 8467 | ctx context.Context, |
| 8468 | chatID uuid.UUID, |
| 8469 | modelConfigID uuid.UUID, |
| 8470 | activeAPIKeyID string, |
| 8471 | toolCallID string, |
| 8472 | result chatloop.CompactionResult, |
| 8473 | ) error { |
| 8474 | if strings.TrimSpace(result.SystemSummary) == "" || |
| 8475 | strings.TrimSpace(result.SummaryReport) == "" { |
| 8476 | return nil |
| 8477 | } |
| 8478 | |
| 8479 | systemContent, err := chatprompt.MarshalParts([]codersdk.ChatMessagePart{ |
| 8480 | codersdk.ChatMessageText(result.SystemSummary), |
| 8481 | }) |
| 8482 | if err != nil { |
| 8483 | return xerrors.Errorf("encode system summary: %w", err) |
| 8484 | } |
| 8485 | |
| 8486 | args, err := json.Marshal(map[string]any{ |
| 8487 | "source": "automatic", |
| 8488 | "threshold_percent": result.ThresholdPercent, |
| 8489 | }) |
| 8490 | if err != nil { |
| 8491 | return xerrors.Errorf("encode summary tool args: %w", err) |
| 8492 | } |
| 8493 | |
| 8494 | assistantContent, err := chatprompt.MarshalParts([]codersdk.ChatMessagePart{ |
| 8495 | codersdk.ChatMessageToolCall(toolCallID, "chat_summarized", args), |
| 8496 | }) |
| 8497 | if err != nil { |
| 8498 | return xerrors.Errorf("encode summary tool call: %w", err) |
| 8499 | } |
| 8500 | |
| 8501 | summaryResult, err := json.Marshal(map[string]any{ |
| 8502 | "summary": result.SummaryReport, |
| 8503 | "source": "automatic", |
| 8504 | "threshold_percent": result.ThresholdPercent, |
| 8505 | "usage_percent": result.UsagePercent, |
| 8506 | "context_tokens": result.ContextTokens, |
| 8507 | "context_limit_tokens": result.ContextLimit, |
| 8508 | }) |
| 8509 | if err != nil { |
| 8510 | return xerrors.Errorf("encode summary result payload: %w", err) |
| 8511 | } |
| 8512 | toolResult, err := chatprompt.MarshalParts([]codersdk.ChatMessagePart{ |
| 8513 | codersdk.ChatMessageToolResult(toolCallID, "chat_summarized", summaryResult, false, false), |
| 8514 | }) |
| 8515 | if err != nil { |
| 8516 | return xerrors.Errorf("encode summary tool result: %w", err) |
| 8517 | } |
| 8518 | |
| 8519 | summaryAPIKeyID := activeAPIKeyID |
| 8520 | if summaryAPIKeyID == "" { |
| 8521 | summaryAPIKeyID, _ = aibridge.DelegatedAPIKeyIDFromContext(ctx) |
| 8522 | } |
| 8523 |