[codex] Add auth mode to plugin manager constructor (#27652)

## Context

Plugins can expose more than one way for Codex to use them: App
connectors for ChatGPT/SIWC-backed sessions and MCP servers for API key
login sessions. The broader goal is to make `PluginsManager` the place
that understands which plugin surfaces should be visible for the current
auth route, so callers do not each have to make that decision
themselves.

This PR is the small setup step for that work. It lets the plugin
manager be created with the current `AuthMode`, which gives the followup
auth routing PRs the information they need without relying on setter
injection.

## Stack

- PR1: #27652 seed plugin manager auth at construction.
- PR2: #27459 route plugin surfaces by auth mode.
- PR3: #27607 dedupe plugin MCP servers by App declaration name.
- PR4: #27602 preserve plugin Apps in connector listings.
- PR5: #27461 skip install-time plugin MCP OAuth for matching App
routes.

## Summary

- Let `PluginsManager::new_with_restriction_product` accept an initial
`AuthMode`.
- Keep `PluginsManager::new` behavior unchanged for ordinary callers.

## Validation

```bash
cargo test -p codex-core-plugins plugins_manager_tracks_auth_mode
cargo test -p codex-core list_tool_suggest_discoverable_plugins
git diff --check
```

---------

Co-authored-by: Xin Lin <xl@openai.com>
This commit is contained in:
felixxia-oai
2026-06-13 02:00:31 +01:00
committed by GitHub
Unverified
parent 044c1420a1
commit aef40ad91f
3 changed files with 19 additions and 9 deletions
+4 -3
View File
@@ -354,12 +354,13 @@ struct PluginLoadCacheKey {
impl PluginsManager {
pub fn new(codex_home: PathBuf) -> Self {
Self::new_with_restriction_product(codex_home, Some(Product::Codex))
Self::new_with_options(codex_home, Some(Product::Codex), /*auth_mode*/ None)
}
pub fn new_with_restriction_product(
pub fn new_with_options(
codex_home: PathBuf,
restriction_product: Option<Product>,
auth_mode: Option<AuthMode>,
) -> Self {
// Product restrictions are enforced at marketplace admission time for a given CODEX_HOME:
// listing, install, and curated refresh all consult this restriction context before new
@@ -386,7 +387,7 @@ impl PluginsManager {
GlobalRemoteCatalogCacheRefreshState::default(),
),
restriction_product,
auth_mode: RwLock::new(None),
auth_mode: RwLock::new(auth_mode),
analytics_events_client: RwLock::new(None),
}
}
+11 -2
View File
@@ -61,6 +61,13 @@ fn plugins_manager_tracks_auth_mode() {
assert_eq!(manager.auth_mode(), Some(AuthMode::ChatgptAuthTokens));
assert!(manager.set_auth_mode(/*auth_mode*/ None));
assert_eq!(manager.auth_mode(), None);
let manager_with_auth = PluginsManager::new_with_options(
tmp.path().join("auth"),
Some(Product::Codex),
Some(AuthMode::Chatgpt),
);
assert_eq!(manager_with_auth.auth_mode(), Some(AuthMode::Chatgpt));
}
fn write_plugin_with_version(
@@ -3038,9 +3045,10 @@ plugins = true
let mut config = load_config(tmp.path(), tmp.path()).await;
config.chatgpt_base_url = format!("{}/backend-api/", server.uri());
let manager = PluginsManager::new_with_restriction_product(
let manager = PluginsManager::new_with_options(
tmp.path().to_path_buf(),
Some(Product::Chatgpt),
/*auth_mode*/ None,
);
let featured_plugin_ids = manager
@@ -3074,9 +3082,10 @@ plugins = true
let mut config = load_config(tmp.path(), tmp.path()).await;
config.chatgpt_base_url = format!("{}/backend-api/", server.uri());
let manager = PluginsManager::new_with_restriction_product(
let manager = PluginsManager::new_with_options(
tmp.path().to_path_buf(),
/*restriction_product*/ None,
/*auth_mode*/ None,
);
let featured_plugin_ids = manager
+4 -4
View File
@@ -273,11 +273,11 @@ impl ThreadManager {
let codex_home = config.codex_home.clone();
let restriction_product = session_source.restriction_product();
let (thread_created_tx, _) = broadcast::channel(THREAD_CREATED_CHANNEL_CAPACITY);
let plugins_manager = Arc::new(PluginsManager::new_with_restriction_product(
let plugins_manager = Arc::new(PluginsManager::new_with_options(
codex_home.to_path_buf(),
restriction_product,
auth_manager.get_api_auth_mode(),
));
plugins_manager.set_auth_mode(auth_manager.get_api_auth_mode());
let mcp_manager = Arc::new(McpManager::new_with_extensions(
Arc::clone(&plugins_manager),
Arc::clone(&extensions),
@@ -368,11 +368,11 @@ impl ThreadManager {
};
let (thread_created_tx, _) = broadcast::channel(THREAD_CREATED_CHANNEL_CAPACITY);
let restriction_product = SessionSource::Exec.restriction_product();
let plugins_manager = Arc::new(PluginsManager::new_with_restriction_product(
let plugins_manager = Arc::new(PluginsManager::new_with_options(
codex_home.clone(),
restriction_product,
auth_manager.get_api_auth_mode(),
));
plugins_manager.set_auth_mode(auth_manager.get_api_auth_mode());
let mcp_manager = Arc::new(McpManager::new(Arc::clone(&plugins_manager)));
let skills_manager = Arc::new(SkillsManager::new_with_restriction_product(
skills_codex_home,