Agent IDE — Codex fork for AI-native development environment
Find a file
LIHUA 397279d46e
Fix: Improve text encoding for shell output in VSCode preview (#6178) (#6182)
## 🐛 Problem

Users running commands with non-ASCII characters (like Russian text
"пример") in Windows/WSL environments experience garbled text in
VSCode's shell preview window, with Unicode replacement characters (�)
appearing instead of the actual text.

**Issue**: https://github.com/openai/codex/issues/6178

## 🔧 Root Cause

The issue was in `StreamOutput<Vec<u8>>::from_utf8_lossy()` method in
`codex-rs/core/src/exec.rs`, which used `String::from_utf8_lossy()` to
convert shell output bytes to strings. This function immediately
replaces any invalid UTF-8 byte sequences with replacement characters,
without attempting to decode using other common encodings.

In Windows/WSL environments, shell output often uses encodings like:

- Windows-1252 (common Windows encoding)
- Latin-1/ISO-8859-1 (extended ASCII)

## 🛠️ Solution

Replaced the simple `String::from_utf8_lossy()` call with intelligent
encoding detection via a new `bytes_to_string_smart()` function that
tries multiple encoding strategies:

1. **UTF-8** (fast path for valid UTF-8)
2. **Windows-1252** (handles Windows-specific characters in 0x80-0x9F
range)
3. **Latin-1** (fallback for extended ASCII)
4. **Lossy UTF-8** (final fallback, same as before)

## 📁 Changes

### New Files

- `codex-rs/core/src/text_encoding.rs` - Smart encoding detection module
- `codex-rs/core/tests/suite/text_encoding_fix.rs` - Integration tests

### Modified Files

- `codex-rs/core/src/lib.rs` - Added text_encoding module
- `codex-rs/core/src/exec.rs` - Updated StreamOutput::from_utf8_lossy()
- `codex-rs/core/tests/suite/mod.rs` - Registered new test module

##  Testing

- **5 unit tests** covering UTF-8, Windows-1252, Latin-1, and fallback
scenarios
- **2 integration tests** simulating the exact Issue #6178 scenario
- **Demonstrates improvement** over the previous
`String::from_utf8_lossy()` approach

All tests pass:

```bash
cargo test -p codex-core text_encoding
cargo test -p codex-core test_shell_output_encoding_issue_6178
```

## 🎯 Impact

-  **Eliminates garbled text** in VSCode shell preview for non-ASCII
content
-  **Supports Windows/WSL environments** with proper encoding detection
-  **Zero performance impact** for UTF-8 text (fast path)
-  **Backward compatible** - UTF-8 content works exactly as before
-  **Handles edge cases** with robust fallback mechanism

## 🧪 Test Scenarios

The fix has been tested with:

- Russian text ("пример")
- Windows-1252 quotation marks (""test")
- Latin-1 accented characters ("café")
- Mixed encoding content
- Invalid byte sequences (graceful fallback)

## 📋 Checklist

- [X] Addresses the reported issue
- [X] Includes comprehensive tests
- [X] Maintains backward compatibility
- [X] Follows project coding conventions
- [X] No breaking changes

---------

Co-authored-by: Josh McKinney <joshka@openai.com>
2025-11-20 11:04:11 -08:00
.devcontainer chore: install an extension for TOML syntax highlighting in the devcontainer (#1650) 2025-07-22 10:58:09 -07:00
.github Update defaults to gpt-5.1 (#6652) 2025-11-17 17:40:11 -08:00
.vscode Move rust analyzer target dir (#5328) 2025-10-18 17:31:46 -07:00
codex-cli detect Bun installs in CLI update banner (#5074) 2025-10-14 17:49:44 +00:00
codex-rs Fix: Improve text encoding for shell output in VSCode preview (#6178) (#6182) 2025-11-20 11:04:11 -08:00
docs Added feature switch to disable animations in TUI (#6870) 2025-11-20 10:40:08 -08:00
scripts fix: ToC so it doesn’t include itself or duplicate the end marker (#4388) 2025-11-05 14:52:51 -08:00
sdk/typescript feat(ts-sdk): allow overriding CLI environment (#6648) 2025-11-14 19:44:19 +00:00
.codespellignore feat: make it possible to toggle mouse mode in the Rust TUI (#971) 2025-05-16 16:16:50 -07:00
.codespellrc TypeScript SDK scaffold (#4455) 2025-09-29 13:27:13 -07:00
.gitignore nit: personal git ignore (#6787) 2025-11-17 17:45:52 +00:00
.npmrc chore: migrate to pnpm for improved monorepo management (#287) 2025-04-18 16:25:15 -07:00
.prettierignore [apply-patch] Clean up apply-patch tool definitions (#2539) 2025-08-21 20:07:41 -07:00
.prettierrc.toml Initial commit 2025-04-16 12:56:08 -04:00
AGENTS.md tests: replace mount_sse_once_match with mount_sse_once for SSE mocking (#6640) 2025-11-13 18:04:05 -08:00
CHANGELOG.md Documentation improvement: add missing period (#3754) 2025-10-30 13:01:33 -07:00
cliff.toml docs(changelog): update install command to @openai/codex@<version> (#2073) 2025-10-18 11:02:22 -07:00
flake.lock Fix nix build (#4048) 2025-10-17 12:19:08 -07:00
flake.nix Fix nix build (#4048) 2025-10-17 12:19:08 -07:00
LICENSE Initial commit 2025-04-16 12:56:08 -04:00
NOTICE resizable viewport (#1732) 2025-07-31 00:06:55 +00:00
package.json chore: subject docs/*.md to Prettier checks (#4645) 2025-10-03 11:35:48 -07:00
pnpm-lock.yaml [exec] Add MCP tool arguments and results (#5899) 2025-10-29 14:23:57 -07:00
pnpm-workspace.yaml TypeScript SDK scaffold (#4455) 2025-09-29 13:27:13 -07:00
PNPM.md fix: include pnpm lock file (#377) 2025-04-18 17:01:11 -07:00
README.md update execpolicy quickstart readme (#6952) 2025-11-19 16:57:27 -08:00

npm i -g @openai/codex
or brew install --cask codex

Codex CLI is a coding agent from OpenAI that runs locally on your computer.

If you want Codex in your code editor (VS Code, Cursor, Windsurf), install in your IDE
If you are looking for the cloud-based agent from OpenAI, Codex Web, go to chatgpt.com/codex

Codex CLI splash


Quickstart

Installing and running Codex CLI

Install globally with your preferred package manager. If you use npm:

npm install -g @openai/codex

Alternatively, if you use Homebrew:

brew install --cask codex

Then simply run codex to get started:

codex

If you're running into upgrade issues with Homebrew, see the FAQ entry on brew upgrade codex.

You can also go to the latest GitHub Release and download the appropriate binary for your platform.

Each GitHub Release contains many executables, but in practice, you likely want one of these:

  • macOS
    • Apple Silicon/arm64: codex-aarch64-apple-darwin.tar.gz
    • x86_64 (older Mac hardware): codex-x86_64-apple-darwin.tar.gz
  • Linux
    • x86_64: codex-x86_64-unknown-linux-musl.tar.gz
    • arm64: codex-aarch64-unknown-linux-musl.tar.gz

Each archive contains a single entry with the platform baked into the name (e.g., codex-x86_64-unknown-linux-musl), so you likely want to rename it to codex after extracting it.

Using Codex with your ChatGPT plan

Codex CLI login

Run codex and select Sign in with ChatGPT. We recommend signing into your ChatGPT account to use Codex as part of your Plus, Pro, Team, Edu, or Enterprise plan. Learn more about what's included in your ChatGPT plan.

You can also use Codex with an API key, but this requires additional setup. If you previously used an API key for usage-based billing, see the migration steps. If you're having trouble with login, please comment on this issue.

Model Context Protocol (MCP)

Codex can access MCP servers. To configure them, refer to the config docs.

Configuration

Codex CLI supports a rich set of configuration options, with preferences stored in ~/.codex/config.toml. For full configuration options, see Configuration.

Execpolicy Quickstart

Codex can enforce your own rules-based execution policy before it runs shell commands.

  1. Create a policy directory: mkdir -p ~/.codex/policy.
  2. Create one or more .codexpolicy files in that folder. Codex automatically loads every .codexpolicy file in there on startup.
  3. Write prefix_rule entries to describe the commands you want to allow, prompt, or block:
prefix_rule(
    pattern = ["git", ["push", "fetch"]],
    decision = "prompt",  # allow | prompt | forbidden
    match = [["git", "push", "origin", "main"]],  # examples that must match
    not_match = [["git", "status"]],              # examples that must not match
)
  • pattern is a list of shell tokens, evaluated from left to right; wrap tokens in a nested list to express alternatives (e.g., match both push and fetch).
  • decision sets the severity; Codex picks the strictest decision when multiple rules match (forbidden > prompt > allow).
  • match and not_match act as (optional) unit tests. Codex validates them when it loads your policy, so you get feedback if an example has unexpected behavior.

In this example rule, if Codex wants to run commands with the prefix git push or git fetch, it will first ask for user approval.

Use execpolicy2 CLI to preview decisions for policy files:

cargo run -p codex-execpolicy2 -- check --policy ~/.codex/policy/default.codexpolicy git push origin main

Pass multiple --policy flags to test how several files combine. See the codex-rs/execpolicy2 README for a more detailed walkthrough of the available syntax.


Docs & FAQ


License

This repository is licensed under the Apache-2.0 License.