Skip to content

Commit 5e0aff9

Browse files
committed
fix(conversation): send fewer carriage returns after a user message
1 parent 1f26946 commit 5e0aff9

File tree

4 files changed

+30
-5
lines changed

4 files changed

+30
-5
lines changed

.vscode/settings.json

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,7 @@
11
{
22
"editor.formatOnSave": true,
3-
"editor.defaultFormatter": "esbenp.prettier-vscode"
3+
"editor.defaultFormatter": "esbenp.prettier-vscode",
4+
"[go]": {
5+
"editor.defaultFormatter": "golang.go"
6+
}
47
}

lib/screentracker/conversation.go

Lines changed: 17 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@ type screenSnapshot struct {
2121
type AgentIO interface {
2222
Write(data []byte) (int, error)
2323
ReadScreen() string
24+
Cursor() (int, int)
2425
}
2526

2627
type ConversationConfig struct {
@@ -289,16 +290,28 @@ func (c *Conversation) writeMessageWithConfirmation(ctx context.Context, message
289290

290291
// wait for the screen to change after the carriage return is written
291292
screenBeforeCarriageReturn := c.cfg.AgentIO.ReadScreen()
293+
cursorBeforeCarriageReturnX, cursorBeforeCarriageReturnY := c.cfg.AgentIO.Cursor()
294+
lastCarriageReturnTime := time.Time{}
292295
if err := util.WaitFor(ctx, util.WaitTimeout{
293296
Timeout: 15 * time.Second,
294297
MinInterval: 25 * time.Millisecond,
295298
}, func() (bool, error) {
296-
if _, err := c.cfg.AgentIO.Write([]byte("\r")); err != nil {
297-
return false, xerrors.Errorf("failed to write carriage return: %w", err)
299+
// we don't want to spam additional carriage returns because the agent may process them
300+
// (aider does this), but we do want to retry sending one if nothing's
301+
// happening for a while
302+
if time.Since(lastCarriageReturnTime) >= 3*time.Second {
303+
lastCarriageReturnTime = time.Now()
304+
if _, err := c.cfg.AgentIO.Write([]byte("\r")); err != nil {
305+
return false, xerrors.Errorf("failed to write carriage return: %w", err)
306+
}
298307
}
299-
time.Sleep(25 * time.Millisecond)
308+
time.Sleep(1 * time.Millisecond)
300309
screen := c.cfg.AgentIO.ReadScreen()
301-
return screen != screenBeforeCarriageReturn, nil
310+
cursorX, cursorY := c.cfg.AgentIO.Cursor()
311+
312+
return screen != screenBeforeCarriageReturn ||
313+
cursorX != cursorBeforeCarriageReturnX ||
314+
cursorY != cursorBeforeCarriageReturnY, nil
302315
}); err != nil {
303316
return xerrors.Errorf("failed to wait for processing to start: %w", err)
304317
}

lib/screentracker/conversation_test.go

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,10 @@ func (a *testAgent) ReadScreen() string {
3131
return a.screen
3232
}
3333

34+
func (a *testAgent) Cursor() (int, int) {
35+
return 0, 0
36+
}
37+
3438
func (a *testAgent) Write(data []byte) (int, error) {
3539
return 0, nil
3640
}

lib/termexec/termexec.go

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -70,6 +70,11 @@ func (p *Process) ReadScreen() string {
7070
return p.xp.State.String()
7171
}
7272

73+
// Cursor returns the current cursor position.
74+
func (p *Process) Cursor() (int, int) {
75+
return p.xp.State.Cursor()
76+
}
77+
7378
// Write sends input to the process via the pseudo terminal.
7479
func (p *Process) Write(data []byte) (int, error) {
7580
return p.xp.TerminalInPipe().Write(data)

0 commit comments

Comments
 (0)