app-server: reject AWS-managed Bedrock logout

This commit is contained in:
celia-oai
2026-07-09 16:21:08 -07:00
parent 7391f65739
commit 63ac6b80a9
3 changed files with 19 additions and 22 deletions

View File

@@ -1930,7 +1930,7 @@ Codex supports these authentication modes. The current mode is surfaced in `acco
- `account/login/start` — begin login (`apiKey`, `chatgpt`, `chatgptDeviceCode`, `amazonBedrock`).
- `account/login/completed` (notify) — emitted when a login attempt finishes (success or error).
- `account/login/cancel` — cancel a pending managed ChatGPT login by `loginId`.
- `account/logout` — sign out; triggers `account/updated`.
- `account/logout` — sign out; triggers `account/updated` on success.
- `account/updated` (notify) — emitted whenever auth mode changes (`authMode`: `apikey`, `bedrockApiKey`, `chatgpt`, `personalAccessToken`, or `null`) and includes the current ChatGPT `planType` when available.
- `account/rateLimits/read` — fetch ChatGPT rate limits, an optional effective monthly credit limit, and the earned rate-limit resets currently available, including expiry details when provided by the backend. Rate-limit updates arrive via `account/rateLimits/updated` (notify); reset-credit data is snapshot-only.
- `account/rateLimitResetCredit/consume` — consume one earned reset using a caller-provided idempotency key, optionally selecting a reset-credit ID returned by `account/rateLimits/read`.
@@ -2060,7 +2060,7 @@ Codex stores the key and region as the primary Codex auth, replacing any previou
{ "method": "account/updated", "params": { "authMode": null, "planType": null } }
```
When Codex-managed Amazon Bedrock auth is stored, logout removes that credential and clears the user-level `model_provider` only when it is still `"amazon-bedrock"`. A concurrent user config change is preserved. For AWS-managed Bedrock auth, logout is a no-op because the AWS SDK credential chain is managed outside Codex.
When Codex-managed Amazon Bedrock auth is stored, logout removes that credential and clears the user-level `model_provider` only when it is still `"amazon-bedrock"`. A concurrent user config change is preserved. When Amazon Bedrock uses AWS-managed credentials, logout returns an error because the AWS SDK credential chain is managed outside Codex. Manage those credentials through AWS, or switch model providers before logging out Codex authentication.
### 7) Rate limits (ChatGPT)

View File

@@ -833,26 +833,23 @@ impl AccountRequestProcessor {
}
async fn logout_common(&self) -> std::result::Result<Option<AuthMode>, JSONRPCErrorError> {
// Cancel any active login attempt.
{
let mut guard = self.active_login.lock().await;
if let Some(active) = guard.take() {
drop(active);
}
}
let managed_bedrock_auth = matches!(
self.auth_manager.auth_cached(),
Some(CodexAuth::BedrockApiKey(_))
);
let config = self.load_latest_config().await;
if config.model_provider.is_amazon_bedrock() && !managed_bedrock_auth {
return Ok(self
.auth_manager
.auth_cached()
.as_ref()
.map(CodexAuth::api_auth_mode)
.map(auth_mode_to_api));
return Err(invalid_request(
"cannot log out while Amazon Bedrock is using AWS-managed credentials; manage those credentials through AWS or switch model providers before logging out Codex authentication",
));
}
// Cancel any active login attempt.
{
let mut guard = self.active_login.lock().await;
if let Some(active) = guard.take() {
drop(active);
}
}
match self.auth_manager.logout_with_revoke().await {

View File

@@ -1387,7 +1387,7 @@ async fn logout_managed_bedrock_restores_default_account() -> Result<()> {
}
#[tokio::test]
async fn logout_aws_managed_bedrock_preserves_openai_auth_and_config() -> Result<()> {
async fn logout_aws_managed_bedrock_errors_without_changing_auth_or_config() -> Result<()> {
let codex_home = TempDir::new()?;
create_config_toml(codex_home.path(), aws_managed_bedrock_config())?;
login_with_api_key(
@@ -1407,18 +1407,18 @@ async fn logout_aws_managed_bedrock_preserves_openai_auth_and_config() -> Result
.await?;
timeout(DEFAULT_READ_TIMEOUT, mcp.initialize()).await??;
let request_id = mcp.send_logout_account_request().await?;
let response = timeout(
let error = timeout(
DEFAULT_READ_TIMEOUT,
mcp.read_stream_until_response_message(RequestId::Integer(request_id)),
mcp.read_stream_until_error_message(RequestId::Integer(request_id)),
)
.await??;
assert_eq!(error.error.code, -32600);
assert_eq!(
to_response::<LogoutAccountResponse>(response)?,
LogoutAccountResponse {}
error.error.message,
"cannot log out while Amazon Bedrock is using AWS-managed credentials; manage those credentials through AWS or switch model providers before logging out Codex authentication"
);
assert_eq!(load_file_auth(codex_home.path())?, expected_auth);
assert_eq!(read_config_toml(codex_home.path())?, expected_config);
assert_account_updated(&mut mcp, Some(AuthMode::ApiKey)).await?;
Ok(())
}