Files
codex/codex-rs/ext/mcp/src/lib_tests.rs
T
Anthony Tafoya cf0ed4c600 Acquire and cache opt-in executor capability inventories via V2 (#53736)
## What changed

- Add the disabled-by-default `executor_capability_discovery_v2` feature to acquire `capabilities/discoverV2` inventories from supporting remote executors using each selected environment's working directory and sandbox.
- Share snapshots with MCP and world-state contributors and skill providers without activating discovered plugins or publishing discovered skills to the model.
- Cache inventories by environment instance, executor session, working directory, and sandbox. Coalesce concurrent requests, refresh the cache at turn start, retry transient failures, and refresh MCP projections after recovery.
- Resolve the system skills root in the executor and pass it explicitly to capability location discovery.

## Testing

Add coverage for feature gating, unsupported executors, inert inventories, cache reuse and eviction, turn refreshes, failure recovery, executor replacement, and system skill locations.

GitOrigin-RevId: 1bdca28fa7f17622b27e2713ab3dcc0c13426889
2026-10-13 18:15:50 +00:00

57 lines
1.8 KiB
Rust

use super::*;
use codex_config::McpServerTransportConfig;
use codex_core::config::ConfigBuilder;
use codex_extension_api::ExtensionData;
use codex_extension_api::ExtensionDataInit;
use pretty_assertions::assert_eq;
#[tokio::test]
async fn hosted_plugin_runtime_forwards_thread_originator() -> Result<(), Box<dyn std::error::Error>>
{
let codex_home = tempfile::tempdir()?;
let config = ConfigBuilder::default()
.codex_home(codex_home.path().to_path_buf())
.fallback_cwd(Some(codex_home.path().to_path_buf()))
.cli_overrides(vec![
("features.apps".to_string(), true.into()),
("chatgpt_base_url".to_string(), "https://chatgpt.com".into()),
])
.build()
.await?;
let thread_init = ExtensionDataInit::new();
let thread_store = ExtensionData::new("thread");
let contributions = HostedPluginRuntimeExtension
.contribute(McpServerContributionContext::for_step(
&config,
&thread_init,
&thread_store,
"codex_work_desktop",
/*ready_selected_capability_roots*/ &[],
/*executor_capability_discovery*/ None,
/*executor_capability_discovery_v2*/ None,
))
.await;
let [
McpServerContribution::HostedApps {
config: server,
protocol_mode: None,
},
] = contributions.as_slice()
else {
panic!("hosted plugin runtime should contribute one server");
};
let McpServerTransportConfig::StreamableHttp { http_headers, .. } = &server.transport else {
panic!("hosted plugin runtime should use streamable HTTP");
};
assert_eq!(
http_headers
.as_ref()
.and_then(|headers| headers.get("originator")),
Some(&"codex_work_desktop".to_string())
);
Ok(())
}