Skip to content

Commit 081f254

Browse files
committed
Merge remote-tracking branch 'upstream/main' into chapeta/history-attachments
2 parents 07cb310 + 3196231 commit 081f254

35 files changed

Lines changed: 1024 additions & 61 deletions

.github/workflows/publish.yml

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -53,6 +53,7 @@ jobs:
5353
create-release:
5454
needs: publish-to-npm
5555
runs-on: ubuntu-latest
56+
environment: release
5657
permissions: {}
5758
steps:
5859
- name: Generate GitHub token
@@ -67,3 +68,28 @@ jobs:
6768
with:
6869
token: ${{ steps.generate-token.outputs.token }}
6970
generate_release_notes: true
71+
72+
trigger-registry-update:
73+
needs: create-release
74+
runs-on: ubuntu-latest
75+
environment: release
76+
permissions: {}
77+
steps:
78+
- name: Generate token scoped to the registry repo
79+
uses: actions/create-github-app-token@v3
80+
id: registry-token
81+
with:
82+
app-id: ${{ secrets.REGISTRY_UPDATER_APP_ID }}
83+
private-key: ${{ secrets.REGISTRY_UPDATER_APP_PRIVATE_KEY }}
84+
owner: ${{ github.repository_owner }}
85+
repositories: registry
86+
87+
- name: Dispatch registry version update
88+
env:
89+
GH_TOKEN: ${{ steps.registry-token.outputs.token }}
90+
run: |
91+
gh workflow run update-versions.yml \
92+
--repo ${{ github.repository_owner }}/registry \
93+
--ref main \
94+
-f apply=true \
95+
-f agents=codex-acp

README.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@ Use [OpenAI Codex](https://github.com/openai/codex) from [Agent Client Protocol]
1212
- Model, reasoning effort, fast mode, approval, and sandbox mode configuration.
1313
- Text prompts, embedded context, images, resource links, and additional workspace directories.
1414
- Shell command, file change, permission request, MCP tool call, terminal output, reasoning, plan, web search, image generation, image view, token usage, and review events.
15+
- Subagent launches as standard ACP tool calls, with Codex thread identity and activity details in namespaced `_meta.codex.subagent` metadata.
1516
- Client-provided MCP servers over command-based stdio config and HTTP transport.
1617
- Slash commands: `/status`, `/mcp`, `/skills`, `/review`, `/review-branch`, `/review-commit`, `/compact`, and `/logout`, as well as configured skills.
1718

package-lock.json

Lines changed: 2 additions & 2 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33
"publishConfig": {
44
"access": "public"
55
},
6-
"version": "1.1.3",
6+
"version": "1.1.4",
77
"description": "",
88
"main": "dist/index.js",
99
"bin": {

src/AcpExtensions.ts

Lines changed: 14 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ import type {
77
} from "@agentclientprotocol/sdk";
88

99
export const LEGACY_SET_SESSION_MODEL_METHOD = "session/set_model";
10+
export const GOAL_CONTROL_METHOD = "_codex/session/goal_control";
1011

1112
export type LegacySessionModel = {
1213
modelId: string;
@@ -42,11 +43,13 @@ export type ExtMethodRequest =
4243
AuthenticationStatusRequest
4344
| AuthenticationLogoutRequest
4445
| LegacySetSessionModelExtRequest
46+
| GoalControlExtRequest
4547

4648
export function isExtMethodRequest(request: { method: string, params: Record<string, unknown> }): request is ExtMethodRequest {
4749
return request.method === "authentication/status"
4850
|| request.method === "authentication/logout"
49-
|| request.method === LEGACY_SET_SESSION_MODEL_METHOD;
51+
|| request.method === LEGACY_SET_SESSION_MODEL_METHOD
52+
|| request.method === GOAL_CONTROL_METHOD;
5053
}
5154

5255
export type AuthenticationStatusRequest = { method: "authentication/status", params: {} }
@@ -60,6 +63,16 @@ export type LegacySetSessionModelExtRequest = {
6063
params: LegacySetSessionModelRequest;
6164
}
6265

66+
export type GoalControlRequest = {
67+
sessionId: SessionId;
68+
action: "pause" | "clear";
69+
}
70+
71+
export type GoalControlExtRequest = {
72+
method: typeof GOAL_CONTROL_METHOD;
73+
params: GoalControlRequest;
74+
}
75+
6376
export async function legacySetSessionModel(
6477
connection: Pick<ClientContext, "request">,
6578
params: LegacySetSessionModelRequest,

src/CodexAcpClient.ts

Lines changed: 35 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -33,13 +33,16 @@ import type {
3333
SkillsListResponse,
3434
SandboxPolicy,
3535
Thread,
36+
ThreadGoal,
3637
ThreadGoalStatus,
3738
ThreadSourceKind,
3839
TurnCompletedNotification,
3940
UserInput,
4041
} from "./app-server/v2";
4142
import packageJson from "../package.json";
4243
import type {AuthenticationStatusResponse} from "./AcpExtensions";
44+
import {createCodexCollaborationMode} from "./CollaborationModeConfig";
45+
import type {ModeKind} from "./app-server/ModeKind";
4346

4447
/**
4548
* Well-known provider id for the client-configurable custom LLM gateway.
@@ -84,7 +87,10 @@ export class CodexAcpClient {
8487

8588
async initialize(request: acp.InitializeRequest): Promise<void> {
8689
await this.codexClient.initialize({
87-
capabilities: null,
90+
capabilities: {
91+
experimentalApi: true,
92+
requestAttestation: false,
93+
},
8894
clientInfo: {
8995
name: request.clientInfo?.name ?? this.defaultClientInfo.name,
9096
version: request.clientInfo?.version ?? this.defaultClientInfo.version,
@@ -330,6 +336,7 @@ export class CodexAcpClient {
330336
sessionId: request.sessionId,
331337
currentModelId: currentModelId,
332338
models: codexModels,
339+
collaborationMode: this.getCollaborationMode(response.thread.id),
333340
modelProvider: response.modelProvider,
334341
currentServiceTier: response.serviceTier as ServiceTier ?? null,
335342
additionalDirectories,
@@ -357,6 +364,7 @@ export class CodexAcpClient {
357364
sessionId: request.sessionId,
358365
currentModelId: currentModelId,
359366
models: codexModels,
367+
collaborationMode: this.getCollaborationMode(response.thread.id),
360368
modelProvider: response.modelProvider,
361369
currentServiceTier: response.serviceTier as ServiceTier ?? null,
362370
thread: historyResponse.thread,
@@ -383,6 +391,7 @@ export class CodexAcpClient {
383391
sessionId: response.thread.id,
384392
currentModelId: currentModelId,
385393
models: codexModels,
394+
collaborationMode: this.getCollaborationMode(response.thread.id),
386395
modelProvider: response.modelProvider,
387396
currentServiceTier: response.serviceTier as ServiceTier ?? null,
388397
additionalDirectories,
@@ -417,6 +426,11 @@ export class CodexAcpClient {
417426
await this.codexClient.runCompact({threadId: sessionId});
418427
}
419428

429+
async getGoal(sessionId: string): Promise<ThreadGoal | null> {
430+
const response = await this.codexClient.threadGoalGet({threadId: sessionId});
431+
return response?.goal ?? null;
432+
}
433+
420434
async setGoal(
421435
sessionId: string,
422436
objective: string,
@@ -429,11 +443,18 @@ export class CodexAcpClient {
429443
}, onTurnStarted);
430444
}
431445

432-
async setGoalStatus(sessionId: string, status: ThreadGoalStatus): Promise<void> {
446+
async setGoalStatus(sessionId: string, status: ThreadGoalStatus): Promise<ThreadGoal> {
447+
let updatedGoal: ThreadGoal | null = null;
433448
await this.codexClient.runGoalSet({
434449
threadId: sessionId,
435450
status,
451+
}, undefined, undefined, (goal) => {
452+
updatedGoal = goal;
436453
});
454+
if (updatedGoal === null) {
455+
throw new Error(`Goal update for session ${sessionId} returned no goal`);
456+
}
457+
return updatedGoal;
437458
}
438459

439460
async resumeGoal(
@@ -679,6 +700,17 @@ export class CodexAcpClient {
679700
}, onTurnStarted);
680701
}
681702

703+
async setCollaborationMode(sessionId: string, mode: ModeKind, currentModelId: string): Promise<void> {
704+
await this.codexClient.threadSettingsUpdate({
705+
threadId: sessionId,
706+
collaborationMode: createCodexCollaborationMode(mode, currentModelId),
707+
});
708+
}
709+
710+
private getCollaborationMode(sessionId: string): ModeKind {
711+
return this.codexClient.getThreadSettings(sessionId)?.collaborationMode.mode ?? "default";
712+
}
713+
682714
resolveTurnInterrupted(params: { threadId: string, turnId: string }): void {
683715
this.codexClient.resolveTurnInterrupted(params.threadId, params.turnId);
684716
}
@@ -845,6 +877,7 @@ export type SessionMetadata = {
845877
sessionId: string,
846878
currentModelId: string,
847879
models: Model[],
880+
collaborationMode: ModeKind,
848881
modelProvider?: string | null,
849882
currentServiceTier?: ServiceTier | null,
850883
additionalDirectories: string[],

0 commit comments

Comments
 (0)