@@ -1174,6 +1174,12 @@ async function agentCommandInternal(
11741174 let stopReason : string | undefined ;
11751175 let resultStatus : "completed" | "cancelled" | undefined ;
11761176 let terminalOutcome : "blocked" | undefined ;
1177+ let acpSessionCwd = workspaceDir ;
1178+ let acpInternalTarget :
1179+ | Awaited < ReturnType < typeof prepareInternalSessionEffectsSession > >
1180+ | undefined ;
1181+ let acpUserTurnHandled : boolean ;
1182+ let acpTranscriptPersistenceBlocked = false ;
11771183 try {
11781184 const {
11791185 resolveAcpAgentPolicyError,
@@ -1197,6 +1203,86 @@ async function agentCommandInternal(
11971203 throw agentPolicyError ;
11981204 }
11991205
1206+ try {
1207+ const { resolveAcpSessionCwd } = await loadAcpSessionIdentifiersRuntime ( ) ;
1208+ acpSessionCwd = resolveAcpSessionCwd ( acpResolution . meta ) ?? workspaceDir ;
1209+ const internalSource = suppressVisibleSessionEffects
1210+ ? resolveInternalSessionEffectsSource ( {
1211+ agentId : sessionAgentId ,
1212+ sessionId,
1213+ sessionKey,
1214+ storePath,
1215+ } )
1216+ : undefined ;
1217+ acpInternalTarget = suppressVisibleSessionEffects
1218+ ? await prepareInternalSessionEffectsSession ( {
1219+ agentId : sessionAgentId ,
1220+ cwd : acpSessionCwd ,
1221+ runId,
1222+ source : internalSource ,
1223+ storePath,
1224+ } )
1225+ : undefined ;
1226+ trackInternalModelRunTarget ( acpInternalTarget ) ;
1227+ const transcriptMedia = opts . transcriptMedia ?? [ ] ;
1228+ const suppressUserTurnPersistence =
1229+ opts . suppressPromptPersistence === true ||
1230+ ( opts . transcriptMessage === "" && transcriptMedia . length === 0 ) ;
1231+ const userTurnTranscriptRecorder = createUserTurnTranscriptRecorder ( {
1232+ ...( ! suppressUserTurnPersistence && ( transcriptBody || transcriptMedia . length > 0 )
1233+ ? {
1234+ input : {
1235+ text : transcriptBody ,
1236+ ...( transcriptMedia . length > 0
1237+ ? {
1238+ media : transcriptMedia ,
1239+ mediaOnlyText : "[User sent media without caption]" ,
1240+ }
1241+ : { } ) ,
1242+ } ,
1243+ }
1244+ : { } ) ,
1245+ target : {
1246+ sessionId : acpInternalTarget ?. sessionId ?? sessionId ,
1247+ ...( ! acpInternalTarget ? { expectedSessionId : sessionId } : { } ) ,
1248+ agentId : acpInternalTarget ?. agentId ?? sessionAgentId ,
1249+ sessionKey : acpInternalTarget ?. sessionKey ?? sessionKey ,
1250+ sessionEntry : acpInternalTarget ?. sessionEntry ?? sessionEntry ,
1251+ sessionStore : suppressVisibleSessionEffects ? undefined : sessionStore ,
1252+ storePath : acpInternalTarget ?. storePath ?? storePath ,
1253+ threadId : opts . threadId ,
1254+ cwd : acpSessionCwd ,
1255+ config : cfg ,
1256+ } ,
1257+ beforeMessageWrite : runAgentHarnessBeforeMessageWriteHook ,
1258+ errorContext : "ACP user turn transcript" ,
1259+ } ) ;
1260+ if ( suppressUserTurnPersistence ) {
1261+ userTurnTranscriptRecorder . markBlocked ( ) ;
1262+ }
1263+ const persistedUserTurn = await userTurnTranscriptRecorder . persistApproved ( {
1264+ cwd : acpSessionCwd ,
1265+ } ) ;
1266+ if (
1267+ ! persistedUserTurn &&
1268+ ! userTurnTranscriptRecorder . hasPersisted ( ) &&
1269+ ( await userTurnTranscriptRecorder . resolveMessage ( ) )
1270+ ) {
1271+ userTurnTranscriptRecorder . markBlocked ( ) ;
1272+ }
1273+ acpUserTurnHandled =
1274+ userTurnTranscriptRecorder . hasPersisted ( ) || userTurnTranscriptRecorder . isBlocked ( ) ;
1275+ if ( ! acpInternalTarget && persistedUserTurn ?. sessionEntry ) {
1276+ sessionEntry = persistedUserTurn . sessionEntry ;
1277+ }
1278+ } catch ( error ) {
1279+ acpUserTurnHandled = false ;
1280+ acpTranscriptPersistenceBlocked = suppressVisibleSessionEffects && ! acpInternalTarget ;
1281+ log . warn (
1282+ `ACP pre-turn transcript persistence failed for ${ sessionKey } : ${ formatErrorMessage ( error ) } ` ,
1283+ ) ;
1284+ }
1285+
12001286 const acpImageAttachments = resolveInlineAgentImageAttachments ( opts . images ) ;
12011287 assertAgentRunLifecycleGenerationCurrent ( lifecycleGeneration ) ;
12021288 await acpManager . runTurn ( {
@@ -1278,57 +1364,43 @@ async function agentCommandInternal(
12781364
12791365 const finalTextRaw = visibleTextAccumulator . finalizeRaw ( ) ;
12801366 const finalText = visibleTextAccumulator . finalize ( ) ;
1281- try {
1282- const { resolveAcpSessionCwd } = await loadAcpSessionIdentifiersRuntime ( ) ;
1283- const internalSource = suppressVisibleSessionEffects
1284- ? resolveInternalSessionEffectsSource ( {
1285- agentId : sessionAgentId ,
1286- sessionId,
1287- sessionKey,
1288- storePath,
1289- } )
1290- : undefined ;
1291- const internalTarget = suppressVisibleSessionEffects
1292- ? await prepareInternalSessionEffectsSession ( {
1293- agentId : sessionAgentId ,
1294- cwd : resolveAcpSessionCwd ( acpResolution . meta ) ?? workspaceDir ,
1295- runId,
1296- source : internalSource ,
1297- storePath,
1298- } )
1299- : undefined ;
1300- trackInternalModelRunTarget ( internalTarget ) ;
1301- const transcriptSessionEntry = internalTarget ?. sessionEntry ?? sessionEntry ;
1302- const transcriptResult = await attemptExecutionRuntime . persistAcpTurnTranscript ( {
1303- body,
1304- transcriptBody,
1305- ...( opts . suppressPromptPersistence !== true && opts . transcriptMedia ?. length
1306- ? {
1307- userInput : {
1308- text : transcriptBody ,
1309- media : opts . transcriptMedia ,
1310- mediaOnlyText : "[User sent media without caption]" ,
1311- } ,
1312- }
1313- : { } ) ,
1314- finalText : finalTextRaw ,
1315- sessionId : internalTarget ?. sessionId ?? sessionId ,
1316- sessionKey : internalTarget ?. sessionKey ?? sessionKey ,
1317- sessionEntry : transcriptSessionEntry ,
1318- sessionStore : suppressVisibleSessionEffects ? undefined : sessionStore ,
1319- storePath : internalTarget ?. storePath ?? storePath ,
1320- sessionAgentId : internalTarget ?. agentId ?? sessionAgentId ,
1321- threadId : opts . threadId ,
1322- sessionCwd : resolveAcpSessionCwd ( acpResolution . meta ) ?? workspaceDir ,
1323- config : cfg ,
1324- } ) ;
1325- if ( ! internalTarget ) {
1326- sessionEntry = transcriptResult . sessionEntry ;
1367+ if ( ! acpTranscriptPersistenceBlocked ) {
1368+ try {
1369+ const transcriptSessionEntry = acpInternalTarget ?. sessionEntry ?? sessionEntry ;
1370+ const transcriptResult = await attemptExecutionRuntime . persistAcpTurnTranscript ( {
1371+ body,
1372+ transcriptBody,
1373+ ...( acpUserTurnHandled ? { skipUserTurn : true } : { } ) ,
1374+ ...( ! acpUserTurnHandled &&
1375+ opts . suppressPromptPersistence !== true &&
1376+ opts . transcriptMedia ?. length
1377+ ? {
1378+ userInput : {
1379+ text : transcriptBody ,
1380+ media : opts . transcriptMedia ,
1381+ mediaOnlyText : "[User sent media without caption]" ,
1382+ } ,
1383+ }
1384+ : { } ) ,
1385+ finalText : finalTextRaw ,
1386+ sessionId : acpInternalTarget ?. sessionId ?? sessionId ,
1387+ sessionKey : acpInternalTarget ?. sessionKey ?? sessionKey ,
1388+ sessionEntry : transcriptSessionEntry ,
1389+ sessionStore : suppressVisibleSessionEffects ? undefined : sessionStore ,
1390+ storePath : acpInternalTarget ?. storePath ?? storePath ,
1391+ sessionAgentId : acpInternalTarget ?. agentId ?? sessionAgentId ,
1392+ threadId : opts . threadId ,
1393+ sessionCwd : acpSessionCwd ,
1394+ config : cfg ,
1395+ } ) ;
1396+ if ( ! acpInternalTarget ) {
1397+ sessionEntry = transcriptResult . sessionEntry ;
1398+ }
1399+ } catch ( error ) {
1400+ log . warn (
1401+ `ACP transcript persistence failed for ${ sessionKey } : ${ formatErrorMessage ( error ) } ` ,
1402+ ) ;
13271403 }
1328- } catch ( error ) {
1329- log . warn (
1330- `ACP transcript persistence failed for ${ sessionKey } : ${ formatErrorMessage ( error ) } ` ,
1331- ) ;
13321404 }
13331405 const restartAbortReason = opts . abortSignal ?. reason ;
13341406 if ( isAgentRunRestartAbortReason ( restartAbortReason ) ) {
0 commit comments