[codex] Consolidate shared prompts in codex-prompts (#25151)

## Why

`codex_core` is consistently a bottleneck for incremental builds during
iteration. The simplest fix is to make the crate smaller.

## Summary

`codex-core` owns several reusable prompt renderers and static prompt
assets, which makes the crate harder to split apart.

Rename `codex-review-prompts` to `codex-prompts` and move shared review,
goal, permissions, compaction, realtime, hierarchical AGENTS.md, and
`apply_patch` prompts into it. Move prompt-only tests and update
consumers and `CODEOWNERS`.

## Validation

- `just test -p codex-prompts -p codex-apply-patch`
- `just test -p codex-core prompt_caching`
- Bazel builds for the affected crates
This commit is contained in:
Adam Perry @ OpenAI
2026-06-01 11:45:07 -07:00
committed by GitHub
Unverified
parent 88c7a4ff07
commit ba2b67f9cd
55 changed files with 814 additions and 740 deletions
+3 -51
View File
@@ -1,6 +1,7 @@
use std::borrow::Cow;
use std::sync::Arc;
use codex_prompts::render_review_exit_interrupted;
use codex_prompts::render_review_exit_success;
use codex_protocol::config_types::WebSearchMode;
use codex_protocol::items::TurnItem;
use codex_protocol::models::ContentItem;
@@ -13,7 +14,6 @@ use codex_protocol::protocol::ExitedReviewModeEvent;
use codex_protocol::protocol::ItemCompletedEvent;
use codex_protocol::protocol::ReviewOutputEvent;
use codex_protocol::protocol::SubAgentSource;
use codex_utils_template::Template;
use tokio_util::sync::CancellationToken;
use crate::codex_delegate::run_codex_thread_one_shot;
@@ -26,18 +26,10 @@ use crate::session::turn_context::TurnContext;
use crate::state::TaskKind;
use codex_features::Feature;
use codex_protocol::user_input::UserInput;
use std::sync::LazyLock;
use super::SessionTask;
use super::SessionTaskContext;
static REVIEW_EXIT_SUCCESS_TEMPLATE: LazyLock<Template> = LazyLock::new(|| {
let normalized =
normalize_review_template_line_endings(crate::client_common::REVIEW_EXIT_SUCCESS_TMPL);
Template::parse(normalized.as_ref())
.unwrap_or_else(|err| panic!("review exit success template must parse: {err}"))
});
#[derive(Clone, Copy)]
pub(crate) struct ReviewTask;
@@ -240,10 +232,7 @@ pub(crate) async fn exit_review_mode(
let assistant_message = render_review_output_text(&out);
(rendered, assistant_message)
} else {
let rendered = normalize_review_template_line_endings(
crate::client_common::REVIEW_EXIT_INTERRUPTED_TMPL,
)
.into_owned();
let rendered = render_review_exit_interrupted();
let assistant_message =
"Review was interrupted. Please re-run /review and wait for it to complete."
.to_string();
@@ -287,40 +276,3 @@ pub(crate) async fn exit_review_mode(
// file creation + git metadata collection cannot delay client-facing items.
session.ensure_rollout_materialized().await;
}
fn render_review_exit_success(results: &str) -> String {
REVIEW_EXIT_SUCCESS_TEMPLATE
.render([("results", results)])
.unwrap_or_else(|err| panic!("review exit success template must render: {err}"))
}
fn normalize_review_template_line_endings(template: &str) -> Cow<'_, str> {
if template.contains('\r') {
Cow::Owned(template.replace("\r\n", "\n").replace('\r', "\n"))
} else {
Cow::Borrowed(template)
}
}
#[cfg(test)]
mod tests {
use super::normalize_review_template_line_endings;
use super::render_review_exit_success;
use pretty_assertions::assert_eq;
#[test]
fn render_review_exit_success_replaces_results_placeholder() {
assert_eq!(
render_review_exit_success("Finding A\nFinding B"),
"<user_action>\n <context>User initiated a review task. Here's the full review output from reviewer model. User may select one or more comments to resolve.</context>\n <action>review</action>\n <results>\n Finding A\nFinding B\n </results>\n </user_action>\n"
);
}
#[test]
fn normalize_review_template_line_endings_rewrites_crlf() {
assert_eq!(
normalize_review_template_line_endings("<user_action>\r\n <results>\r\n None.\r\n"),
"<user_action>\n <results>\n None.\n"
);
}
}