v0.3.67 80dd4c6

before_start.go RawHistoryFolder

1package extensions
2
3import (
4	"context"
5	"encoding/json"
6	"fmt"
7
8	"github.com/patriceckhart/zot/packages/agent/extproto"
9)
10
11// MaxSystemPromptResponseSize limits the encoded system_prompt value. The
12// transport additionally limits each complete response frame to 4 MiB.
13const MaxSystemPromptResponseSize = 1024 * 1024
14
15// InterceptBeforeAgentStart chains exact prompt replacements in load order.
16// Failures are advisory, never permission decisions.
17func (m *Manager) InterceptBeforeAgentStart(ctx context.Context, ev extproto.EventInterceptFromHost) string {
18	current := ""
19	if ev.SystemPrompt != nil {
20		current = *ev.SystemPrompt
21	}
22	ev.Event = "before_agent_start"
23	ev.CWD = m.cwd
24	if ev.Provider == "" {
25		ev.Provider = m.provider
26	}
27	m.mu.RLock()
28	subs := append([]*Extension(nil), m.extOrder...)
29	m.mu.RUnlock()
30	for _, ext := range subs {
31		if ctx.Err() != nil {
32			break
33		}
34		ext.mu.Lock()
35		_, subscribed := ext.interceptSubs[ev.Event]
36		ext.mu.Unlock()
37		if !subscribed {
38			continue
39		}
40		ev.SystemPrompt = &current
41		callCtx, cancel := context.WithTimeout(ctx, interceptTimeout)
42		r := m.askIntercept(callCtx, ext, ev)
43		cancel()
44		failure := r.failure
45		if failure == "" && r.Block && len(r.SystemPrompt) == 0 {
46			failure = "extension returned a blocking response; startup hooks cannot block"
47		}
48		if failure == "" && len(r.SystemPrompt) > 0 {
49			var replacement string
50			switch {
51			case len(r.SystemPrompt) > MaxSystemPromptResponseSize:
52				failure = "system_prompt exceeds 1 MiB encoded limit"
53			case r.SystemPrompt[0] != '"' || json.Unmarshal(r.SystemPrompt, &replacement) != nil:
54				failure = "system_prompt must be a string"
55			default:
56				current = replacement
57			}
58		}
59		if failure != "" {
60			message := "before_agent_start: " + failure + "; keeping current system prompt"
61			fmt.Fprintln(ext.logFile, "[zot] "+message)
62			ext.recordDiagnostic(message)
63			if m.hooks != nil {
64				m.hooks.Notify(ext.Manifest.Name, "warn", message)
65			}
66		}
67	}
68	return current
69}

Keyboard shortcuts

Single-key shortcuts are on. ctrl k and esc work whatever this says.

ctrl k :
go to a section, branch, tag, file or repository
?
this list
j k
move the row cursor down / up
enter
open the row under the cursor; on Files, a directory opens or closes in place
↑ ↓ ← → home end
in the file tree (focus on a row): previous / next row, close / open a directory or go to its parent / first entry, first / last row. They never open a file
l h
on Files: open a directory or a file / close a directory or go up to its parent, then to the parent page. Elsewhere: into the side panel (on a merge request, its files) / back to the content; there j k move between its controls
g g G
first / last row
/
filter the list; on Files, find a file anywhere in the repository (esc clears, enter opens the best match)
b
switch branch or tag
g s g f g c g b g m g i g r g a
tabs: summary, files, commits, branches & tags, merge requests, issues, releases, actions (when available)
g h
home
w
wide mode: use the whole width of the screen, or not (remembered)
y
copy a permalink pinned to the commit
d u x
diff: split / unified / collapse or expand all
e E
diff: the whole file in view / every file, with the lines the hunks hide
n
merge request: next note in the diff
esc
close a dialog, leave a field

Branches 1

Tags 476

↑↓ moveenter openesc close