dbus: add Complete and missing session methods; readme: add -nodbus flag

This commit is contained in:
Levi Neely 2026-07-18 22:36:24 +02:00
parent 8e4c1accaa
commit da611d3ef2
3 changed files with 110 additions and 0 deletions

View File

@ -90,6 +90,7 @@ The server listens on a Unix socket in the Plan 9 namespace (`$NAMESPACE/ollie`)
| `-yolo` | Skip the landrun sandbox for all `execute_code` execution. |
| `-tcp <addr>` | Also listen on a TCP address (e.g. `:564`). |
| `-mount <path>` | Override the FUSE mount path. |
| `-nodbus` | Disable the embedded D-Bus adapter (implied by `-tcp`). |
```sh
olliesrv start -strict # tools only, sandboxed

100
dbus.go
View File

@ -543,6 +543,97 @@ func (a *DBusAdapter) Route(task, backendName string) (string, *dbus.Error) {
return fmt.Sprintf("backend=%s model=%s", result.Backend, result.Model), nil
}
func (a *DBusAdapter) Complete(cwd, filePath, prefix, suffix, extraContext string) (string, *dbus.Error) {
result, err := a.mgr.Complete(cwd, filePath, prefix, suffix, extraContext)
if err != nil {
return "", dbus.MakeFailedError(err)
}
return result, nil
}
func (a *DBusAdapter) GetEnv(sessionID string) (string, *dbus.Error) {
sess := a.mgr.Session(sessionID)
if sess == nil {
return "", nil
}
var sb strings.Builder
fmt.Fprintf(&sb, "OLLIE_SESSION_ID=%s\n", sess.RunnableID())
for _, e := range os.Environ() {
if strings.HasPrefix(e, "OLLIE_") && !strings.HasPrefix(e, "OLLIE_SESSION_ID=") {
sb.WriteString(e)
sb.WriteByte('\n')
}
}
return sb.String(), nil
}
func (a *DBusAdapter) GetPlan(sessionID string) (string, *dbus.Error) {
sess := a.mgr.Session(sessionID)
if sess == nil {
return "", nil
}
sess.Mu().RLock()
plan := string(sess.Plan())
sess.Mu().RUnlock()
return plan, nil
}
func (a *DBusAdapter) SetPlan(sessionID, plan string) (bool, *dbus.Error) {
sess := a.mgr.Session(sessionID)
if sess == nil {
return false, nil
}
sess.Mu().Lock()
sess.SetPlan([]byte(plan))
sess.Mu().Unlock()
return true, nil
}
func (a *DBusAdapter) GetSystemPrompt(sessionID string) (string, *dbus.Error) {
sess := a.mgr.Session(sessionID)
if sess == nil {
return "", nil
}
return sess.Core.SystemPrompt(), nil
}
func (a *DBusAdapter) GetContextSize(sessionID string) (string, *dbus.Error) {
sess := a.mgr.Session(sessionID)
if sess == nil {
return "", nil
}
return sess.Core.CtxSz(), nil
}
func (a *DBusAdapter) GetPreviousPrompt(sessionID string) (string, *dbus.Error) {
sess := a.mgr.Session(sessionID)
if sess == nil {
return "", nil
}
sess.Mu().RLock()
p := string(sess.PrevPrompt())
sess.Mu().RUnlock()
return p, nil
}
func (a *DBusAdapter) Compact(sessionID string) (bool, *dbus.Error) {
sess := a.mgr.Session(sessionID)
if sess == nil {
return false, nil
}
sess.Core.Submit(sess.Ctx, "/compact")
return true, nil
}
func (a *DBusAdapter) ClearContext(sessionID string) (bool, *dbus.Error) {
sess := a.mgr.Session(sessionID)
if sess == nil {
return false, nil
}
sess.Core.Submit(sess.Ctx, "/clear")
return true, nil
}
// --- Notifications ---
func (a *DBusAdapter) sendNotification(title, body string) {
@ -590,6 +681,15 @@ var introspectXML = `<node>
<method name="DismissDetached"><arg direction="in" type="s" name="sessionID"/><arg direction="in" type="i" name="pid"/><arg direction="out" type="b"/></method>
<method name="Generate"><arg direction="in" type="s" name="prompt"/><arg direction="in" type="s" name="system"/><arg direction="in" type="s" name="backend"/><arg direction="in" type="s" name="model"/><arg direction="out" type="s"/></method>
<method name="Route"><arg direction="in" type="s" name="task"/><arg direction="in" type="s" name="backend"/><arg direction="out" type="s"/></method>
<method name="Complete"><arg direction="in" type="s" name="cwd"/><arg direction="in" type="s" name="file"/><arg direction="in" type="s" name="prefix"/><arg direction="in" type="s" name="suffix"/><arg direction="in" type="s" name="context"/><arg direction="out" type="s"/></method>
<method name="GetEnv"><arg direction="in" type="s" name="sessionID"/><arg direction="out" type="s"/></method>
<method name="GetPlan"><arg direction="in" type="s" name="sessionID"/><arg direction="out" type="s"/></method>
<method name="SetPlan"><arg direction="in" type="s" name="sessionID"/><arg direction="in" type="s" name="plan"/><arg direction="out" type="b"/></method>
<method name="GetSystemPrompt"><arg direction="in" type="s" name="sessionID"/><arg direction="out" type="s"/></method>
<method name="GetContextSize"><arg direction="in" type="s" name="sessionID"/><arg direction="out" type="s"/></method>
<method name="GetPreviousPrompt"><arg direction="in" type="s" name="sessionID"/><arg direction="out" type="s"/></method>
<method name="Compact"><arg direction="in" type="s" name="sessionID"/><arg direction="out" type="b"/></method>
<method name="ClearContext"><arg direction="in" type="s" name="sessionID"/><arg direction="out" type="b"/></method>
<signal name="SessionCreated"><arg type="s" name="sessionID"/></signal>
<signal name="SessionKilled"><arg type="s" name="sessionID"/></signal>
<signal name="SessionRenamed"><arg type="s" name="oldID"/><arg type="s" name="newID"/></signal>

View File

@ -164,6 +164,15 @@ func (sess *Session) Mu() *sync.RWMutex { return &sess.mu }
// Log returns the raw chat log bytes. Caller must hold Mu().RLock().
func (sess *Session) Log() []byte { return sess.log }
// Plan returns the plan bytes. Caller must hold Mu().RLock().
func (sess *Session) Plan() []byte { return sess.plan }
// SetPlan sets the plan. Caller must hold Mu().Lock().
func (sess *Session) SetPlan(p []byte) { sess.plan = p }
// PrevPrompt returns the last submitted prompt. Caller must hold Mu().RLock().
func (sess *Session) PrevPrompt() []byte { return sess.prevPrompt }
var sessionStoreOrder = []string{"new", "idx", "ls", "kill", "sh", "b", "bfg", "bbg", "cleanup"}