diff --git a/codex-rs/core/BUILD.bazel b/codex-rs/core/BUILD.bazel index b6d4e853e0..c3b822481c 100644 --- a/codex-rs/core/BUILD.bazel +++ b/codex-rs/core/BUILD.bazel @@ -2,15 +2,7 @@ load("//:defs.bzl", "codex_rust_crate") codex_rust_crate( name = "core", - compile_data = glob( - include = ["**"], - allow_empty = True, - exclude = [ - "**/* *", - "BUILD.bazel", - "Cargo.toml", - ], - ), + compile_data = glob(["assets/**"]), crate_name = "codex_core", extra_binaries = [ "//codex-rs/bwrap:bwrap", @@ -22,7 +14,7 @@ codex_rust_crate( "//codex-rs/windows-sandbox-rs:codex-command-runner", "//codex-rs/windows-sandbox-rs:codex-windows-sandbox-setup", ], - integration_compile_data_extra = ["src/guardian/node_repl_policy.md"], + integration_compile_data_extra = glob(["assets/**"]), integration_test_timeout = "long", run_tests_with_wine_exec = True, rustc_env = { @@ -34,6 +26,7 @@ codex_rust_crate( "config.schema.json", ] + glob([ "src/**/snapshots/**", + "tests/fixtures/**", ]) + [ # This is a bit of a hack, but empirically, some of our integration tests # are relying on the presence of this file as a repo root marker. When diff --git a/codex-rs/core/src/agent/agent_names.txt b/codex-rs/core/assets/agent/agent_names.txt similarity index 100% rename from codex-rs/core/src/agent/agent_names.txt rename to codex-rs/core/assets/agent/agent_names.txt diff --git a/codex-rs/core/src/agent/builtins/awaiter.toml b/codex-rs/core/assets/agent/builtins/awaiter.toml similarity index 100% rename from codex-rs/core/src/agent/builtins/awaiter.toml rename to codex-rs/core/assets/agent/builtins/awaiter.toml diff --git a/codex-rs/core/src/agent/builtins/explorer.toml b/codex-rs/core/assets/agent/builtins/explorer.toml similarity index 100% rename from codex-rs/core/src/agent/builtins/explorer.toml rename to codex-rs/core/assets/agent/builtins/explorer.toml diff --git a/codex-rs/core/src/consequential_tool_message_templates.json b/codex-rs/core/assets/consequential_tool_message_templates.json similarity index 100% rename from codex-rs/core/src/consequential_tool_message_templates.json rename to codex-rs/core/assets/consequential_tool_message_templates.json diff --git a/codex-rs/core/src/guardian/node_repl_policy.md b/codex-rs/core/assets/guardian/node_repl_policy.md similarity index 100% rename from codex-rs/core/src/guardian/node_repl_policy.md rename to codex-rs/core/assets/guardian/node_repl_policy.md diff --git a/codex-rs/core/src/guardian/policy.md b/codex-rs/core/assets/guardian/policy.md similarity index 100% rename from codex-rs/core/src/guardian/policy.md rename to codex-rs/core/assets/guardian/policy.md diff --git a/codex-rs/core/src/guardian/policy_template.md b/codex-rs/core/assets/guardian/policy_template.md similarity index 100% rename from codex-rs/core/src/guardian/policy_template.md rename to codex-rs/core/assets/guardian/policy_template.md diff --git a/codex-rs/core/templates/persistent_mode.md b/codex-rs/core/assets/persistent_mode.md similarity index 100% rename from codex-rs/core/templates/persistent_mode.md rename to codex-rs/core/assets/persistent_mode.md diff --git a/codex-rs/core/src/tools/handlers/apply_patch.lark b/codex-rs/core/assets/tools/apply_patch.lark similarity index 100% rename from codex-rs/core/src/tools/handlers/apply_patch.lark rename to codex-rs/core/assets/tools/apply_patch.lark diff --git a/codex-rs/core/src/agent/control/spawn.rs b/codex-rs/core/src/agent/control/spawn.rs index a7e460f517..ab82ac3550 100644 --- a/codex-rs/core/src/agent/control/spawn.rs +++ b/codex-rs/core/src/agent/control/spawn.rs @@ -19,7 +19,7 @@ use codex_protocol::intersect_effective_permission_profiles; use codex_protocol::protocol::EnvironmentConfigState; use codex_utils_path_uri::PathUri; -const AGENT_NAMES: &str = include_str!("../agent_names.txt"); +const AGENT_NAMES: &str = include_str!("../../../assets/agent/agent_names.txt"); struct SpawnAgentThreadInheritance { environments: Option, diff --git a/codex-rs/core/src/agent/role.rs b/codex-rs/core/src/agent/role.rs index 1eb771bd54..cb203776ed 100644 --- a/codex-rs/core/src/agent/role.rs +++ b/codex-rs/core/src/agent/role.rs @@ -405,8 +405,8 @@ Rules: /// Resolves a built-in role `config_file` path to embedded content. pub(super) fn config_file_contents(path: &Path) -> Option<&'static str> { - const EXPLORER: &str = include_str!("builtins/explorer.toml"); - const AWAITER: &str = include_str!("builtins/awaiter.toml"); + const EXPLORER: &str = include_str!("../../assets/agent/builtins/explorer.toml"); + const AWAITER: &str = include_str!("../../assets/agent/builtins/awaiter.toml"); match path.to_str()? { "explorer.toml" => Some(EXPLORER), "awaiter.toml" => Some(AWAITER), diff --git a/codex-rs/core/src/context/guardian_node_repl_policy.rs b/codex-rs/core/src/context/guardian_node_repl_policy.rs index 0353cf0826..7e465b6758 100644 --- a/codex-rs/core/src/context/guardian_node_repl_policy.rs +++ b/codex-rs/core/src/context/guardian_node_repl_policy.rs @@ -22,6 +22,6 @@ impl ContextualUserFragment for GuardianNodeReplPolicy { } fn body(&self) -> String { - include_str!("../guardian/node_repl_policy.md").to_string() + include_str!("../../assets/guardian/node_repl_policy.md").to_string() } } diff --git a/codex-rs/core/src/context/world_state/persistent_mode.rs b/codex-rs/core/src/context/world_state/persistent_mode.rs index b2d5284cce..1257053415 100644 --- a/codex-rs/core/src/context/world_state/persistent_mode.rs +++ b/codex-rs/core/src/context/world_state/persistent_mode.rs @@ -10,7 +10,7 @@ use codex_protocol::openai_models::ReasoningEffort; use serde::Deserialize; use serde::Serialize; -const DEFAULT_INSTRUCTIONS: &str = include_str!("../../../templates/persistent_mode.md"); +const DEFAULT_INSTRUCTIONS: &str = include_str!("../../../assets/persistent_mode.md"); const REPLACEMENT_NOTICE: &str = "These persistent-mode instructions replace all previously provided persistent-mode instructions."; const REMOVAL_NOTICE: &str = "The previously provided persistent-mode instructions no longer apply."; diff --git a/codex-rs/core/src/guardian/prompt.rs b/codex-rs/core/src/guardian/prompt.rs index 66341b756f..3fc07a77b7 100644 --- a/codex-rs/core/src/guardian/prompt.rs +++ b/codex-rs/core/src/guardian/prompt.rs @@ -819,8 +819,9 @@ For anything else, use this JSON schema: }"# } -pub(crate) const BUNDLED_GUARDIAN_POLICY: &str = include_str!("policy.md"); -pub(crate) const BUNDLED_GUARDIAN_POLICY_TEMPLATE: &str = include_str!("policy_template.md"); +pub(crate) const BUNDLED_GUARDIAN_POLICY: &str = include_str!("../../assets/guardian/policy.md"); +pub(crate) const BUNDLED_GUARDIAN_POLICY_TEMPLATE: &str = + include_str!("../../assets/guardian/policy_template.md"); const TENANT_POLICY_CONFIG_PLACEHOLDER: &str = "{{ tenant_policy_config }}"; /// Guardian policy prompt. diff --git a/codex-rs/core/src/mcp_tool_approval_templates.rs b/codex-rs/core/src/mcp_tool_approval_templates.rs index 1c905b4f27..862768e704 100644 --- a/codex-rs/core/src/mcp_tool_approval_templates.rs +++ b/codex-rs/core/src/mcp_tool_approval_templates.rs @@ -70,7 +70,7 @@ pub(crate) fn render_mcp_tool_approval_template( fn load_consequential_tool_message_templates() -> Option> { let templates = match serde_json::from_str::( - include_str!("consequential_tool_message_templates.json"), + include_str!("../assets/consequential_tool_message_templates.json"), ) { Ok(templates) => templates, Err(err) => { diff --git a/codex-rs/core/src/session/tests.rs b/codex-rs/core/src/session/tests.rs index 1637cb5d9b..901a954dd9 100644 --- a/codex-rs/core/src/session/tests.rs +++ b/codex-rs/core/src/session/tests.rs @@ -1613,8 +1613,12 @@ async fn user_shell_commands_remain_login_shells_when_model_login_shells_are_dis #[tokio::test] async fn get_base_instructions_no_user_content() { + let prompt_path = codex_utils_cargo_bin::find_resource!( + "tests/fixtures/prompt_with_apply_patch_instructions.md" + ) + .expect("resolve prompt fixture path"); let prompt_with_apply_patch_instructions = - include_str!("../../prompt_with_apply_patch_instructions.md"); + std::fs::read_to_string(prompt_path).expect("read prompt fixture"); let models_response = bundled_models_response() .unwrap_or_else(|err| panic!("bundled models.json should parse: {err}")); let model_info_for_slug = |slug: &str, config: &Config| { diff --git a/codex-rs/core/src/tools/handlers/apply_patch_spec.rs b/codex-rs/core/src/tools/handlers/apply_patch_spec.rs index 39956d208f..9efd8f9d8d 100644 --- a/codex-rs/core/src/tools/handlers/apply_patch_spec.rs +++ b/codex-rs/core/src/tools/handlers/apply_patch_spec.rs @@ -2,7 +2,7 @@ use codex_tools::FreeformTool; use codex_tools::FreeformToolFormat; use codex_tools::ToolSpec; -const APPLY_PATCH_LARK_GRAMMAR: &str = include_str!("apply_patch.lark"); +const APPLY_PATCH_LARK_GRAMMAR: &str = include_str!("../../../assets/tools/apply_patch.lark"); /// Returns a custom tool that can be used to edit files. Well-suited for GPT-5 models /// https://platform.openai.com/docs/guides/function-calling#custom-tools diff --git a/codex-rs/core/prompt_with_apply_patch_instructions.md b/codex-rs/core/tests/fixtures/prompt_with_apply_patch_instructions.md similarity index 100% rename from codex-rs/core/prompt_with_apply_patch_instructions.md rename to codex-rs/core/tests/fixtures/prompt_with_apply_patch_instructions.md diff --git a/codex-rs/core/tests/suite/guardian_review.rs b/codex-rs/core/tests/suite/guardian_review.rs index f40ff66038..c21dec9161 100644 --- a/codex-rs/core/tests/suite/guardian_review.rs +++ b/codex-rs/core/tests/suite/guardian_review.rs @@ -753,7 +753,7 @@ async fn guardian_node_repl_policy_follows_production_approval_path( .collect::>(); assert_eq!(guardian_requests.len(), actions.len()); - let policy = include_str!("../../src/guardian/node_repl_policy.md"); + let policy = include_str!("../../assets/guardian/node_repl_policy.md"); let first_guardian_thread = guardian_requests[0].body_json()["client_metadata"]["thread_id"] .as_str() .expect("Guardian reviewer thread id") diff --git a/codex-rs/tui/BUILD.bazel b/codex-rs/tui/BUILD.bazel index 297a038ff9..21fb44ae92 100644 --- a/codex-rs/tui/BUILD.bazel +++ b/codex-rs/tui/BUILD.bazel @@ -2,18 +2,10 @@ load("//:defs.bzl", "MACOS_WEBRTC_RUSTC_LINK_FLAGS", "codex_rust_crate") codex_rust_crate( name = "tui", - compile_data = glob( - include = ["**"], - allow_empty = True, - exclude = [ - "**/* *", - "BUILD.bazel", - "Cargo.toml", - ], - ) + [ - "//codex-rs/collaboration-mode-templates:templates/default.md", - "//codex-rs/collaboration-mode-templates:templates/plan.md", - ], + compile_data = glob([ + "assets/**", + "frames/**", + ]), crate_name = "codex_tui", extra_binaries = [ "//codex-rs/cli:codex", @@ -23,6 +15,7 @@ codex_rust_crate( test_data_extra = glob([ "src/**/*.rs", "src/**/snapshots/**", + "tests/fixtures/**", ]), test_shard_counts = { "tui-unit-tests": 8, diff --git a/codex-rs/tui/src/inline_visualization/assets/visualize.css b/codex-rs/tui/assets/inline_visualization/visualize.css similarity index 100% rename from codex-rs/tui/src/inline_visualization/assets/visualize.css rename to codex-rs/tui/assets/inline_visualization/visualize.css diff --git a/codex-rs/tui/src/inline_visualization/assets/visualize.html b/codex-rs/tui/assets/inline_visualization/visualize.html similarity index 100% rename from codex-rs/tui/src/inline_visualization/assets/visualize.html rename to codex-rs/tui/assets/inline_visualization/visualize.html diff --git a/codex-rs/tui/prompt_for_init_command.md b/codex-rs/tui/assets/prompt_for_init_command.md similarity index 100% rename from codex-rs/tui/prompt_for_init_command.md rename to codex-rs/tui/assets/prompt_for_init_command.md diff --git a/codex-rs/tui/tooltips.txt b/codex-rs/tui/assets/tooltips.txt similarity index 100% rename from codex-rs/tui/tooltips.txt rename to codex-rs/tui/assets/tooltips.txt diff --git a/codex-rs/tui/src/chatwidget/slash_dispatch.rs b/codex-rs/tui/src/chatwidget/slash_dispatch.rs index 69229ba4dd..6925ef5a6e 100644 --- a/codex-rs/tui/src/chatwidget/slash_dispatch.rs +++ b/codex-rs/tui/src/chatwidget/slash_dispatch.rs @@ -258,7 +258,7 @@ impl ChatWidget { .send(AppEvent::OpenDesktopThread { thread_id }); } SlashCommand::Init => { - const INIT_PROMPT: &str = include_str!("../../prompt_for_init_command.md"); + const INIT_PROMPT: &str = include_str!("../../assets/prompt_for_init_command.md"); self.submit_user_message(INIT_PROMPT.to_string().into()); } SlashCommand::Compact => { diff --git a/codex-rs/tui/src/inline_visualization/viewer.rs b/codex-rs/tui/src/inline_visualization/viewer.rs index 0a7bd7709b..b94f809d63 100644 --- a/codex-rs/tui/src/inline_visualization/viewer.rs +++ b/codex-rs/tui/src/inline_visualization/viewer.rs @@ -10,8 +10,8 @@ const FRAGMENT_PLACEHOLDER: &str = ""; const VIEWER_DIRECTORY_NAME: &str = ".codex-viewers"; // Keep these assets in sync with the bundled visualize skill's browser renderer. -const VIEWER_STYLESHEET: &str = include_str!("assets/visualize.css"); -const VIEWER_RUNTIME: &str = include_str!("assets/visualize.html"); +const VIEWER_STYLESHEET: &str = include_str!("../../assets/inline_visualization/visualize.css"); +const VIEWER_RUNTIME: &str = include_str!("../../assets/inline_visualization/visualize.html"); const FRAME_CSP: &str = "default-src 'none'; script-src 'unsafe-inline' 'unsafe-eval' 'wasm-unsafe-eval' blob: data: https://cdnjs.cloudflare.com https://cdn.jsdelivr.net https://esm.sh https://fonts.bunny.net https://fonts.googleapis.com https://fonts.gstatic.com https://unpkg.com; style-src 'unsafe-inline' blob: data: https://cdnjs.cloudflare.com https://cdn.jsdelivr.net https://esm.sh https://fonts.bunny.net https://fonts.googleapis.com https://fonts.gstatic.com https://unpkg.com; img-src blob: data: https://cdnjs.cloudflare.com https://cdn.jsdelivr.net https://esm.sh https://fonts.bunny.net https://fonts.googleapis.com https://fonts.gstatic.com https://unpkg.com; font-src blob: data: https://cdnjs.cloudflare.com https://cdn.jsdelivr.net https://esm.sh https://fonts.bunny.net https://fonts.googleapis.com https://fonts.gstatic.com https://unpkg.com; media-src blob: data:; worker-src blob:; connect-src blob: data:; frame-src 'none'; object-src 'none'; base-uri 'none'; form-action 'none'"; const SHELL_STYLE: &str = ":root{color-scheme:light dark;background:light-dark(rgb(255 255 255), rgb(24 24 24))}html,body{margin:0}body{box-sizing:border-box;padding:1rem;background:inherit}iframe{display:block;width:100%;max-width:736px;height:calc(100vh - 2rem);margin:0 auto;border:0}"; diff --git a/codex-rs/tui/src/tooltips.rs b/codex-rs/tui/src/tooltips.rs index f659ae75dc..9ea7912ac2 100644 --- a/codex-rs/tui/src/tooltips.rs +++ b/codex-rs/tui/src/tooltips.rs @@ -20,7 +20,7 @@ const OTHER_TOOLTIP_NON_MAC: &str = "*New* Build faster with Codex."; const FREE_GO_TOOLTIP: &str = "*New* For a limited time, Codex is included in your plan for free – let’s build together."; -const RAW_TOOLTIPS: &str = include_str!("../tooltips.txt"); +const RAW_TOOLTIPS: &str = include_str!("../assets/tooltips.txt"); lazy_static! { static ref TOOLTIPS: Vec<&'static str> = RAW_TOOLTIPS diff --git a/defs.bzl b/defs.bzl index 490950d00a..48922cd696 100644 --- a/defs.bzl +++ b/defs.bzl @@ -458,10 +458,11 @@ def codex_rust_crate( integration_test_binaries = sanitized_binaries integration_test_cargo_env = cargo_env integration_test_cargo_env_runfiles = cargo_env_runfiles + integration_test_files = native.glob(["tests/**"], allow_empty = True) integration_test_data_extra = [ data for data in test_data_extra - if data not in cargo_env_runfiles + if data not in cargo_env_runfiles and data not in integration_test_files ] non_windows_sanitized_binaries = [] non_windows_cargo_env = {} @@ -545,8 +546,8 @@ def codex_rust_crate( crate_name = test_crate_name, crate_root = test, srcs = [test], - data = native.glob(["tests/**"], allow_empty = True) + integration_test_binaries + integration_test_data_extra, - compile_data = native.glob(["tests/**"], allow_empty = True) + integration_compile_data_extra, + data = integration_test_files + integration_test_binaries + integration_test_data_extra, + compile_data = integration_test_files + integration_compile_data_extra, deps = all_crate_deps(normal = True, normal_dev = True) + maybe_deps + deps_extra, # Bazel has emitted both `codex-rs//...` and # `../codex-rs//...` paths for `file!()`. Strip either @@ -585,8 +586,8 @@ def codex_rust_crate( crate_name = test_crate_name, crate_root = test, srcs = [test], - data = native.glob(["tests/**"], allow_empty = True) + integration_test_binaries + integration_test_data_extra, - compile_data = native.glob(["tests/**"], allow_empty = True) + integration_compile_data_extra, + data = integration_test_files + integration_test_binaries + integration_test_data_extra, + compile_data = integration_test_files + integration_compile_data_extra, deps = all_crate_deps(normal = True, normal_dev = True) + maybe_deps + deps_extra, # Bazel has emitted both `codex-rs//...` and # `../codex-rs//...` paths for `file!()`. Strip either @@ -660,8 +661,8 @@ def codex_rust_crate( crate_name = test_crate_name, crate_root = test, srcs = [test], - data = native.glob(["tests/**"], allow_empty = True) + integration_test_binaries + integration_test_data_extra, - compile_data = native.glob(["tests/**"], allow_empty = True) + integration_compile_data_extra, + data = integration_test_files + integration_test_binaries + integration_test_data_extra, + compile_data = integration_test_files + integration_compile_data_extra, deps = all_crate_deps(normal = True, normal_dev = True) + maybe_deps + deps_extra, rustc_flags = rustc_flags_extra + WINDOWS_RUSTC_LINK_FLAGS + [ "--remap-path-prefix=../codex-rs=",