Skip to content
Merged
Show file tree
Hide file tree
Changes from 7 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,9 @@ You can use AgentAPI:

Run an HTTP server that lets you control an agent. If you'd like to start an agent with additional arguments, pass the full agent command after the `--` flag.

> [!NOTE]
> When using Codex, make sure to explicitly specify the agent type (for example, `agentapi server -- codex`) after the `--` flag when starting the server.

```bash
agentapi server -- claude --allowedTools "Bash(git*) Edit Replace"
```
Expand Down
3 changes: 3 additions & 0 deletions cmd/server/server.go
Original file line number Diff line number Diff line change
Expand Up @@ -78,6 +78,9 @@ func runServer(ctx context.Context, logger *slog.Logger, argsToPass []string) er
}
if termHeight < 10 {
return xerrors.Errorf("term height must be at least 10")
} else if agentType == AgentTypeCodex && termHeight > 930 {
logger.Warn(fmt.Sprintf("Term height is set to %d which may cause issues with Codex. Setting it to 930 instead.", termHeight))
termHeight = 930 // codex has a bug where the TUI distorts the screen if the height is too large, see: https://github.com/openai/codex/issues/1608
}

var process *termexec.Process
Expand Down
38 changes: 38 additions & 0 deletions lib/msgfmt/message_box.go
Original file line number Diff line number Diff line change
Expand Up @@ -51,3 +51,41 @@ func removeMessageBox(msg string) string {

return strings.Join(lines, "\n")
}

func removeCodexMessageBox(msg string) string {
lines := strings.Split(msg, "\n")
messageBoxEndIdx := -1
messageBoxStartIdx := -1

for i := len(lines) - 1; i >= 0; i-- {
if messageBoxEndIdx == -1 {
if strings.Contains(lines[i], "╰────────") && strings.Contains(lines[i], "───────╯") {
messageBoxEndIdx = i
}
} else {
// We reached the start of the message box (we don't want to show this line), also exit the loop
if strings.Contains(lines[i], "╭") && strings.Contains(lines[i], "───────╮") {
// We only want this to be i + 1 in case the top of the box is visible
messageBoxStartIdx = i
break
}

// We are in between the start and end of the message box, so remove the │ from the start and end of the line, let the trimEmptyLines handle the rest
if strings.HasPrefix(lines[i], "│") {
lines[i] = strings.TrimPrefix(lines[i], "│")
}
if strings.HasSuffix(lines[i], "│") {
lines[i] = strings.TrimSuffix(lines[i], "│")
lines[i] = strings.TrimRight(lines[i], " \t")
}
}
}

// If we didn't find messageBoxEndIdx, set it to the end of the lines
if messageBoxEndIdx == -1 {
messageBoxEndIdx = len(lines)
}

return strings.Join(lines[messageBoxStartIdx+1:messageBoxEndIdx], "\n")

}
10 changes: 9 additions & 1 deletion lib/msgfmt/msgfmt.go
Original file line number Diff line number Diff line change
Expand Up @@ -216,6 +216,14 @@ func formatGenericMessage(message string, userInput string) string {
return message
}

func formatCodexMessage(message string, userInput string) string {
message = RemoveUserInput(message, userInput)
message = removeMessageBox(message)
message = removeCodexMessageBox(message)
message = trimEmptyLines(message)
return message
}

func FormatAgentMessage(agentType AgentType, message string, userInput string) string {
switch agentType {
case AgentTypeClaude:
Expand All @@ -225,7 +233,7 @@ func FormatAgentMessage(agentType AgentType, message string, userInput string) s
case AgentTypeAider:
return formatGenericMessage(message, userInput)
case AgentTypeCodex:
return formatGenericMessage(message, userInput)
return formatCodexMessage(message, userInput)
case AgentTypeGemini:
return formatGenericMessage(message, userInput)
case AgentTypeCustom:
Expand Down
25 changes: 8 additions & 17 deletions lib/msgfmt/testdata/format/codex/confirmation_box/expected.txt
Original file line number Diff line number Diff line change
@@ -1,19 +1,10 @@
thinking for 9s
Shell Command
~/Documents/work/agentapi$ git rev-parse --show-toplevel

command
Allow command?

$ git rev-parse --show-toplevel

╭──────────────────────────────────────────────────────────────────────────────────────────────────────────╮
│Shell Command │
│ │
│$ git rev-parse --show-toplevel │
│ │
│Allow command? │
│ │
│ ❯ Yes (y) │
│ Yes, always approve this exact command for this session (a) │
│ Edit or give feedback (e) │
│ No, and keep going (n) │
│ No, and stop for now (esc) │
╰──────────────────────────────────────────────────────────────────────────────────────────────────────────╯
▶ Yes (y)
Yes, always approve this exact command for this session (a)
Edit or give feedback (e)
No, and keep going (n)
No, and stop for now (esc)
50 changes: 28 additions & 22 deletions lib/msgfmt/testdata/format/codex/confirmation_box/msg.txt
Original file line number Diff line number Diff line change
@@ -1,22 +1,28 @@
user
what repository are you in?

thinking for 9s

command

$ git rev-parse --show-toplevel

╭──────────────────────────────────────────────────────────────────────────────────────────────────────────╮
│Shell Command │
│ │
│$ git rev-parse --show-toplevel │
│ │
│Allow command? │
│ │
│ ❯ Yes (y) │
│ Yes, always approve this exact command for this session (a) │
│ Edit or give feedback (e) │
│ No, and keep going (n) │
│ No, and stop for now (esc) │
╰──────────────────────────────────────────────────────────────────────────────────────────────────────────╯
╭Messages (tab to focus)──────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────╮
│OpenAI Codex v0.10.0 (research preview) │
│ │
│codex session 790ba389-ab4d-47be-bb16-9cc7f36bcf2b │
│workdir: /Users/jkmr/Documents/work/agentapi │
│model: codex-mini-latest │
│provider: openai │
│approval: untrusted │
│sandbox: read-only │
│reasoning effort: medium │
│reasoning summaries: auto │
│ │
│user │
│what repository are you in? │
│ │
╰─────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────╯
╭Review───────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────╮
│Shell Command │
│~/Documents/work/agentapi$ git rev-parse --show-toplevel │
│ │
│Allow command? │
│ │
│ ▶ Yes (y) │
│ Yes, always approve this exact command for this session (a) │
│ Edit or give feedback (e) │
│ No, and keep going (n) │
│ No, and stop for now (esc) │
╰─────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────╯
20 changes: 9 additions & 11 deletions lib/msgfmt/testdata/format/codex/first_message/expected.txt
Original file line number Diff line number Diff line change
@@ -1,12 +1,10 @@
╭──────────────────────────────────────────────────────────────╮
│ ● OpenAI Codex (research preview) v0.1.2504161551 │
╰──────────────────────────────────────────────────────────────╯
╭──────────────────────────────────────────────────────────────╮
│ localhost session: c4bf4c89c3fb483c935bdff223394646 │
│ ↳ workdir: ~/dev/agentapi │
│ ↳ model: o4-mini │
│ ↳ approval: suggest │
╰──────────────────────────────────────────────────────────────╯
OpenAI Codex v0.10.0 (research preview)

system
Warning: model "o4-mini" is not in the list of available models returned by OpenAI.
codex session 56576d81-529d-42f3-843b-78d870054a75
workdir: /Users/jkmr/Documents/work/agentapi
model: codex-mini-latest
provider: openai
approval: untrusted
sandbox: read-only
reasoning effort: medium
reasoning summaries: auto
Loading