server: handle session/new write+read in server (rdwr pattern), bypass FileConfig
This commit is contained in:
parent
7e731d4624
commit
daf535308f
|
|
@ -50,6 +50,7 @@ type fid struct {
|
|||
completeResult []byte // for /complete: result of last write (per-fid state)
|
||||
generateResult []byte // for /generate: result of last write (per-fid state)
|
||||
routeResult []byte // for /route: result of last write (per-fid state)
|
||||
sessionResult []byte // for /session/new: session name from last write
|
||||
}
|
||||
|
||||
// connState tracks all open fids for a single 9P connection.
|
||||
|
|
@ -836,13 +837,19 @@ func (s *Server) read(cs *connState, fc *plan9.Fcall, ctx context.Context) *plan
|
|||
return s.readDNS(fc, &f.generateResult)
|
||||
}
|
||||
|
||||
// /route: return per-fid result from previous write (offset 0-based)
|
||||
if path == "/route" {
|
||||
s.log.Debug("Tread path=%q offset=%d count=%d", path, fc.Offset, fc.Count)
|
||||
return s.readDNS(fc, &f.routeResult)
|
||||
}
|
||||
// /route: return per-fid result from previous write (offset 0-based)
|
||||
if path == "/route" {
|
||||
s.log.Debug("Tread path=%q offset=%d count=%d", path, fc.Offset, fc.Count)
|
||||
return s.readDNS(fc, &f.routeResult)
|
||||
}
|
||||
|
||||
s.log.Debug("Tread path=%q offset=%d count=%d", path, fc.Offset, fc.Count)
|
||||
// /session/new: return per-fid result from previous write
|
||||
if path == "/session/new" {
|
||||
s.log.Debug("Tread path=%q offset=%d count=%d", path, fc.Offset, fc.Count)
|
||||
return s.readDNS(fc, &f.sessionResult)
|
||||
}
|
||||
|
||||
s.log.Debug("Tread path=%q offset=%d count=%d", path, fc.Offset, fc.Count)
|
||||
entry, err := s.openEntry(path)
|
||||
if err != nil {
|
||||
return errFcall(fc, err.Error())
|
||||
|
|
@ -1010,11 +1017,22 @@ func (s *Server) write(cs *connState, fc *plan9.Fcall) *plan9.Fcall {
|
|||
if err != nil {
|
||||
return errFcall(fc, err.Error())
|
||||
}
|
||||
f.routeResult = []byte(fmt.Sprintf("backend=%s model=%s", result.Backend, result.Model))
|
||||
return &plan9.Fcall{Type: plan9.Rwrite, Tag: fc.Tag, Count: uint32(len(fc.Data))}
|
||||
}
|
||||
f.routeResult = []byte(fmt.Sprintf("backend=%s model=%s", result.Backend, result.Model))
|
||||
return &plan9.Fcall{Type: plan9.Rwrite, Tag: fc.Tag, Count: uint32(len(fc.Data))}
|
||||
}
|
||||
|
||||
// Accumulate; the 9P client may split large writes across multiple Twrite messages.
|
||||
// /session/new: synchronous create-session (per-fid state, like /net/dns)
|
||||
if f.path == "/session/new" {
|
||||
cs.mu.Unlock()
|
||||
name, err := fs.CreateFromRoot(s.sessionTree, strings.Fields(strings.TrimSpace(string(fc.Data))))
|
||||
if err != nil {
|
||||
return errFcall(fc, err.Error())
|
||||
}
|
||||
f.sessionResult = []byte(name)
|
||||
return &plan9.Fcall{Type: plan9.Rwrite, Tag: fc.Tag, Count: uint32(len(fc.Data))}
|
||||
}
|
||||
|
||||
// Accumulate; the 9P client may split large writes across multiple Twrite messages.
|
||||
end := int(fc.Offset) + len(fc.Data)
|
||||
if end > len(f.writeBuf) {
|
||||
grown := make([]byte, end)
|
||||
|
|
|
|||
|
|
@ -422,28 +422,19 @@ func rootOpen(rs *rootState, name string) (File, error) {
|
|||
},
|
||||
IsBlocking_: true,
|
||||
}, nil
|
||||
case "new":
|
||||
var sessResult string
|
||||
return &FileConfig{
|
||||
StatFn: func() (os.FileInfo, error) {
|
||||
return &SyntheticFileInfo{Name_: "new", Mode_: Perms[PathSessions].Files["new"]}, nil
|
||||
},
|
||||
ReadFn: func() ([]byte, error) {
|
||||
if sessResult != "" {
|
||||
return []byte(sessResult + "\n"), nil
|
||||
}
|
||||
return []byte("name=\n"), nil
|
||||
},
|
||||
WriteFn: func(data []byte) error {
|
||||
name, err := Create(rs, strings.Fields(strings.TrimSpace(string(data))))
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
sessResult = name
|
||||
return nil
|
||||
},
|
||||
BlockingReadFn: notBlocking,
|
||||
}, nil
|
||||
case "new":
|
||||
return &FileConfig{
|
||||
StatFn: func() (os.FileInfo, error) {
|
||||
return &SyntheticFileInfo{Name_: "new", Mode_: Perms[PathSessions].Files["new"]}, nil
|
||||
},
|
||||
ReadFn: func() ([]byte, error) {
|
||||
return []byte("name=\n"), nil
|
||||
},
|
||||
WriteFn: func(data []byte) error {
|
||||
return fmt.Errorf("use ollie-9p rdwr session/new")
|
||||
},
|
||||
BlockingReadFn: notBlocking,
|
||||
}, nil
|
||||
case "idx":
|
||||
return &FileConfig{
|
||||
StatFn: func() (os.FileInfo, error) {
|
||||
|
|
@ -472,30 +463,30 @@ case "new":
|
|||
if len(parts) == 2 {
|
||||
return nil, fmt.Errorf("%s: is a directory", name)
|
||||
}
|
||||
if len(parts) >= 3 && parts[2] == "new" {
|
||||
if len(parts) == 3 {
|
||||
// agent/new — request-response file to create an agent
|
||||
var agentResult string
|
||||
return &FileConfig{
|
||||
StatFn: func() (os.FileInfo, error) {
|
||||
return &SyntheticFileInfo{Name_: "new", Mode_: Perms[PathSessionFile].Files["new"]}, nil
|
||||
},
|
||||
ReadFn: func() ([]byte, error) {
|
||||
if agentResult != "" {
|
||||
return []byte(agentResult + "\n"), nil
|
||||
}
|
||||
return []byte("cwd=\nbackend=\nmodel=\nagent=\nagent_alias=\nremote=\nsystem_prompt=\n"), nil
|
||||
},
|
||||
WriteFn: func(data []byte) error {
|
||||
if err := CreateAgent(rs, sessID, strings.Fields(strings.TrimSpace(string(data)))); err != nil {
|
||||
return err
|
||||
}
|
||||
agentResult = "ok"
|
||||
return nil
|
||||
},
|
||||
BlockingReadFn: notBlocking,
|
||||
}, nil
|
||||
}
|
||||
if len(parts) >= 3 && parts[2] == "new" {
|
||||
if len(parts) == 3 {
|
||||
// agent/new — request-response file to create an agent
|
||||
var agentResult string
|
||||
return &FileConfig{
|
||||
StatFn: func() (os.FileInfo, error) {
|
||||
return &SyntheticFileInfo{Name_: "new", Mode_: Perms[PathSessionFile].Files["new"]}, nil
|
||||
},
|
||||
ReadFn: func() ([]byte, error) {
|
||||
if agentResult != "" {
|
||||
return []byte(agentResult + "\n"), nil
|
||||
}
|
||||
return []byte("cwd=\nbackend=\nmodel=\nagent=\nagent_alias=\nremote=\nsystem_prompt=\n"), nil
|
||||
},
|
||||
WriteFn: func(data []byte) error {
|
||||
if err := CreateAgent(rs, sessID, strings.Fields(strings.TrimSpace(string(data)))); err != nil {
|
||||
return err
|
||||
}
|
||||
agentResult = "ok"
|
||||
return nil
|
||||
},
|
||||
BlockingReadFn: notBlocking,
|
||||
}, nil
|
||||
}
|
||||
return nil, fmt.Errorf("%s: not a file", name)
|
||||
}
|
||||
if len(parts) < 4 {
|
||||
|
|
|
|||
Loading…
Reference in New Issue