mirror of
https://github.com/openclaw/openclaw.git
synced 2026-08-20 01:21:41 -06:00
45dd558d92
* fix(codex): preserve thread ownership across session lifecycles * test(codex): keep canonical context-engine session fixtures * fix(codex): fence replacement thread rollback by ownership * fix(codex): fence thread handoffs by physical client ownership * fix(codex): derive conversation privacy from its source session * fix(codex): claim active native subagents at their lifecycle owner * fix(codex): preserve conversation ownership when detach fails * fix(codex): fence stale native child close notifications * fix(codex): preserve active child ownership during rollback * test(codex): keep lifecycle fixtures aligned with public contracts * fix(codex): preserve rollback failure causes across ownership recovery * fix(codex): retain aggregate rollback causes through lint analysis * fix(codex): release native children when idle retention fails
107 lines
3.7 KiB
TypeScript
107 lines
3.7 KiB
TypeScript
import { resolveAgentDir, resolveSessionAgentIds } from "openclaw/plugin-sdk/agent-runtime";
|
|
import type { PluginCommandContext } from "openclaw/plugin-sdk/plugin-entry";
|
|
import { resolveCodexAppServerAuthProfileIdForAgent } from "./app-server/auth-bridge.js";
|
|
import { resolveCodexBindingAppServerConnection } from "./app-server/binding-connection.js";
|
|
import {
|
|
sessionBindingIdentity,
|
|
type CodexAppServerBindingIdentity,
|
|
} from "./app-server/session-binding.js";
|
|
import type { CodexCommandDeps } from "./command-handler-deps.js";
|
|
import type { CodexControlRequestOptions } from "./command-rpc.js";
|
|
import { readCodexConversationBindingData } from "./conversation-binding-data.js";
|
|
|
|
type CodexConversationControlTarget = {
|
|
identity: CodexAppServerBindingIdentity;
|
|
agentId: string;
|
|
agentDir: string;
|
|
requestedAuthProfileId?: string;
|
|
};
|
|
|
|
export async function resolveControlTarget(
|
|
ctx: PluginCommandContext,
|
|
): Promise<CodexConversationControlTarget | undefined> {
|
|
const binding = await ctx.getCurrentConversationBinding();
|
|
const data = readCodexConversationBindingData(binding);
|
|
const scope = resolveCodexConversationControlScope(ctx);
|
|
if (data?.kind === "codex-app-server-session") {
|
|
return {
|
|
identity: conversationBindingIdentity(data.bindingId),
|
|
agentId: data.agentId ?? scope.agentId,
|
|
agentDir: data.agentDir ?? scope.agentDir,
|
|
requestedAuthProfileId: data.start?.authProfileId,
|
|
};
|
|
}
|
|
return ctx.sessionId
|
|
? {
|
|
identity: sessionBindingIdentity({
|
|
sessionId: ctx.sessionId,
|
|
sessionKey: ctx.sessionKey,
|
|
agentId: scope.agentId,
|
|
config: ctx.config,
|
|
}),
|
|
agentId: scope.agentId,
|
|
agentDir: scope.agentDir,
|
|
}
|
|
: undefined;
|
|
}
|
|
|
|
type CommandAppServerScope = Pick<
|
|
CodexControlRequestOptions,
|
|
"authProfileId" | "sessionId" | "sessionKey" | "startOptions"
|
|
> & { agentId: string; agentDir: string };
|
|
|
|
export async function resolveCommandAppServerScope(
|
|
deps: CodexCommandDeps,
|
|
ctx: PluginCommandContext,
|
|
pluginConfig: unknown,
|
|
): Promise<CommandAppServerScope> {
|
|
const target = await resolveControlTarget(ctx);
|
|
const fallback = resolveCodexConversationControlScope(ctx);
|
|
const agentDir = target?.agentDir ?? fallback.agentDir;
|
|
const binding = target ? await deps.bindingStore.read(target.identity) : undefined;
|
|
const authProfileId =
|
|
binding?.connectionScope === "supervision"
|
|
? undefined
|
|
: resolveCodexAppServerAuthProfileIdForAgent({
|
|
authProfileId: binding?.authProfileId ?? target?.requestedAuthProfileId,
|
|
agentDir,
|
|
config: ctx.config,
|
|
});
|
|
const connection = resolveCodexBindingAppServerConnection({
|
|
binding,
|
|
authProfileId,
|
|
pluginConfig,
|
|
});
|
|
return {
|
|
agentId: target?.agentId ?? fallback.agentId,
|
|
agentDir,
|
|
...(connection.clientAuthProfileId !== undefined
|
|
? { authProfileId: connection.clientAuthProfileId }
|
|
: {}),
|
|
...(connection.usesSupervisionConnection ? { startOptions: connection.appServer.start } : {}),
|
|
...(ctx.sessionKey ? { sessionKey: ctx.sessionKey } : {}),
|
|
...(ctx.sessionId ? { sessionId: ctx.sessionId } : {}),
|
|
};
|
|
}
|
|
|
|
export function conversationBindingIdentity(
|
|
bindingId: string,
|
|
): Extract<CodexAppServerBindingIdentity, { kind: "conversation" }> {
|
|
return { kind: "conversation", bindingId };
|
|
}
|
|
|
|
export function resolveCodexConversationControlScope(ctx: PluginCommandContext): {
|
|
agentId: string;
|
|
agentDir: string;
|
|
} {
|
|
const { sessionAgentId } = resolveSessionAgentIds({
|
|
sessionKey: ctx.sessionKey,
|
|
agentId: ctx.agentId,
|
|
config: ctx.config,
|
|
});
|
|
return {
|
|
agentId: sessionAgentId,
|
|
agentDir: resolveAgentDir(ctx.config, sessionAgentId),
|
|
};
|
|
}
|