1
>
/*---------------------------------------------------------------------------------------------
codexPromptResolver.ts
2
>
* Copyright (c) Microsoft Corporation. All rights reserved.
3
>
* Licensed under the MIT License. See License.txt in the project root for license information.
4
>
*--------------------------------------------------------------------------------------------*/
5
>
6
>
import * as crypto from 'crypto';
7
>
import * as fs from 'fs';
8
>
import * as os from 'os';
9
>
import { join } from '../../../../base/common/path.js';
10
>
import { URI } from '../../../../base/common/uri.js';
11
>
import { MessageAttachmentKind, type MessageAttachment, type MessageEmbeddedResourceAttachment } from '../../common/state/sessionState.js';
12
>
import type { UserInput } from './protocol/generated/v2/UserInput.js';
13
>
import type { TextElement } from './protocol/generated/v2/TextElement.js';
14
>
15
>
/**
16
>
* Translate the agent host's `(prompt, attachments)` shape into codex's
17
>
* `turn/start.input[]`.
18
>
*
19
>
* Phase 2 minimum:
20
>
* - The prompt text becomes a single `{ type: 'text' }` input item.
21
>
* - `Resource` attachments referencing local files are inlined into the
22
>
* text as `@<path>` mentions so codex's prompt template picks them up.
23
>
* - `Simple` attachments with a `modelRepresentation` get appended to the
24
>
* prompt text as a separate paragraph.
25
>
* - `EmbeddedResource` attachments with an `image/*` content type are
26
>
* written to a temp file and surfaced as `{ type: 'localImage' }`. The
27
>
* returned files are tracked in `cleanupPaths` so the caller can unlink
28
>
* them after the turn completes.
29
>
* - `EmbeddedResource` attachments carrying textual content (e.g. the live
30
>
* text of an unsaved / dirty editor or a code selection, which the client
31
>
* inlines as a `text/plain` embedded resource) are base64-decoded and
32
>
* inlined into the prompt as a labelled fenced block so codex sees the
33
>
* exact in-memory content — a path mention would read the stale on-disk
34
>
* file (or nothing at all for untitled buffers). Non-textual, non-image
35
>
* embedded resources (e.g. `application/pdf`) are still dropped.
36
>
*
37
>
* Skill / app mentions are deferred to a later phase.
38
>
*/
39
>
export interface IResolvedCodexInput {
40
>
readonly input: ReadonlyArray<UserInput>;
41
>
/** Temporary files created during resolution. Caller MUST unlink. */
42
>
readonly cleanupPaths: readonly string[];
43
>
}
44
>
45
>
const EMPTY_TEXT_ELEMENTS: TextElement[] = [];
46
>
47
>
export function resolveCodexInput(
48
prompt: string,
49
attachments: readonly MessageAttachment[] | undefined,