import { clearBootstrapSnapshot } from "../../agents/bootstrap-cache.js" ;
import { clearAllCliSessions } from "../../agents/cli-session.js" ;
import { resetConfiguredBindingTargetInPlace } from "../../channels/plugins/binding-targets.js" ;
import { updateSessionStoreEntry } from "../../config/sessions/store.js" ;
import { logVerbose } from "../../globals.js" ;
import { isAcpSessionKey } from "../../routing/session-key.js" ;
import { resolveBoundAcpThreadSessionKey } from "./commands-acp/targets.js" ;
import { emitResetCommandHooks, type ResetCommandAction } from "./commands-reset-hooks.js" ;
import { parseSoftResetCommand } from "./commands-reset-mode.js" ;
import type { CommandHandlerResult, HandleCommandsParams } from "./commands-types.js" ;
import { isResetAuthorizedForContext } from "./reset-authorization.js" ;
function applyAcpResetTailContext(ctx: HandleCommandsParams["ctx" ], resetTail: string): void {
const mutableCtx = ctx as Record<string, unknown>;
mutableCtx.Body = resetTail;
mutableCtx.RawBody = resetTail;
mutableCtx.CommandBody = resetTail;
mutableCtx.BodyForCommands = resetTail;
mutableCtx.BodyForAgent = resetTail;
mutableCtx.BodyStripped = resetTail;
mutableCtx.AcpDispatchTailAfterReset = true ;
}
function isResetAuthorized(params: HandleCommandsParams): boolean {
return isResetAuthorizedForContext({
ctx: params.ctx,
cfg: params.cfg,
commandAuthorized: params.command.isAuthorizedSender || params.ctx.CommandAuthorized === true ,
});
}
export async function maybeHandleResetCommand(
params: HandleCommandsParams,
): Promise<CommandHandlerResult | null > {
const softReset = parseSoftResetCommand(params.command.commandBodyNormalized);
if (softReset.matched) {
if (!isResetAuthorized(params)) {
logVerbose(
`Ignoring /reset soft from unauthorized sender: ${params.command.senderId || "<unknown>" }`,
);
return { shouldContinue: false };
}
const boundAcpSessionKey = resolveBoundAcpThreadSessionKey(params);
const boundAcpKey =
boundAcpSessionKey && isAcpSessionKey(boundAcpSessionKey)
? boundAcpSessionKey.trim()
: undefined;
if (boundAcpKey) {
return {
shouldContinue: false ,
reply: { text: "Usage: /reset soft is not available for ACP-bound sessions yet." },
};
}
const targetSessionEntry = params.sessionStore?.[params.sessionKey] ?? params.sessionEntry;
const previousSessionEntry =
params.previousSessionEntry ?? (targetSessionEntry ? { ...targetSessionEntry } : undefined);
if (targetSessionEntry) {
clearAllCliSessions(targetSessionEntry);
if (params.sessionEntry && params.sessionEntry !== targetSessionEntry) {
clearAllCliSessions(params.sessionEntry);
params.sessionEntry.updatedAt = Date.now();
}
if (params.sessionKey) {
clearBootstrapSnapshot(params.sessionKey);
}
targetSessionEntry.updatedAt = Date.now();
if (params.sessionStore && params.sessionKey) {
params.sessionStore[params.sessionKey] = targetSessionEntry;
}
if (params.storePath && params.sessionKey) {
await updateSessionStoreEntry({
storePath: params.storePath,
sessionKey: params.sessionKey,
update: async (entry) => {
const next = { ...entry };
clearAllCliSessions(next);
return {
cliSessionBindings: next.cliSessionBindings,
cliSessionIds: next.cliSessionIds,
claudeCliSessionId: next.claudeCliSessionId,
updatedAt: Date.now(),
};
},
});
}
}
await emitResetCommandHooks({
action: "reset" ,
ctx: params.ctx,
cfg: params.cfg,
command: params.command,
sessionKey: params.sessionKey,
sessionEntry: targetSessionEntry,
previousSessionEntry,
workspaceDir: params.workspaceDir,
});
params.command.softResetTriggered = true ;
params.command.softResetTail = softReset.tail;
return null ;
}
const resetMatch = params.command.commandBodyNormalized.match(/^\/(new |reset)(?:\s|$)/);
if (!resetMatch) {
return null ;
}
if (!isResetAuthorized(params)) {
logVerbose(
`Ignoring /reset from unauthorized sender: ${params.command.senderId || "<unknown>" }`,
);
return { shouldContinue: false };
}
const commandAction: ResetCommandAction = resetMatch[1 ] === "reset" ? "reset" : "new" ;
const resetTail = params.command.commandBodyNormalized.slice(resetMatch[0 ].length).trimStart();
const boundAcpSessionKey = resolveBoundAcpThreadSessionKey(params);
const boundAcpKey =
boundAcpSessionKey && isAcpSessionKey(boundAcpSessionKey)
? boundAcpSessionKey.trim()
: undefined;
if (boundAcpKey) {
const resetResult = await resetConfiguredBindingTargetInPlace({
cfg: params.cfg,
sessionKey: boundAcpKey,
reason: commandAction,
commandSource: `${params.command.surface}:${params.ctx.CommandSource ?? "text" }`,
});
if (!resetResult.ok) {
logVerbose(`acp reset failed for ${boundAcpKey}: ${resetResult.error ?? "unknown error" }`);
}
if (resetResult.ok) {
params.command.resetHookTriggered = true ;
if (resetTail) {
applyAcpResetTailContext(params.ctx, resetTail);
if (params.rootCtx && params.rootCtx !== params.ctx) {
applyAcpResetTailContext(params.rootCtx, resetTail);
}
return { shouldContinue: false };
}
return {
shouldContinue: false ,
reply: { text: "✅ ACP session reset in place." },
};
}
return {
shouldContinue: false ,
reply: { text: "⚠️ ACP session reset failed. Check /acp status and try again." },
};
}
const targetSessionEntry = params.sessionStore?.[params.sessionKey] ?? params.sessionEntry;
await emitResetCommandHooks({
action: commandAction,
ctx: params.ctx,
cfg: params.cfg,
command: params.command,
sessionKey: params.sessionKey,
sessionEntry: targetSessionEntry,
previousSessionEntry: params.previousSessionEntry,
workspaceDir: params.workspaceDir,
});
return null ;
}
Messung V0.5 in Prozent C=98 H=95 G=96
¤ Dauer der Verarbeitung: 0.14 Sekunden
(vorverarbeitet am 2026-06-10)
¤
*© Formatika GbR, Deutschland