[codex] Add experimental Codex app instances#5
Merged
Conversation
Summary: - Encode app-instance bundle identifiers from the raw profile name so valid names with dots, underscores, hyphens, or case differences do not collapse to the same macOS bundle identifier. - Rebuild existing app clones when required bundle metadata is missing, malformed, stale, or still using the previous non-unique identifier. - Update the fake macOS launch harness so workspace document files stay separate from argv, matching the real open command more closely. Rationale: - Parallel Desktop instances depend on macOS seeing each cloned bundle as a distinct app. Non-unique identifiers can make distinct profiles fight over the same LaunchServices identity. - Users should not need to know when an old or damaged clone needs --rebuild; the command can detect bad metadata and repair it. - Tests should model the production launch boundary instead of passing document paths through argv and giving false confidence. Tests: - bash test/codex-profile-test.sh - shellcheck bin/codex-profile test/codex-profile-test.sh - make test - git diff --check Co-authored-by: Codex <codex@openai.com>
Summary: - Add a polished README demo asset showing two profile-scoped Codex Desktop instances side by side. - Refresh README positioning around isolated CODEX_HOME profiles and the experimental parallel Desktop workflow. - Include media assets in the npm package file list so README images are packaged with the published artifact. Rationale: - The new app-instance feature needs a clearer visual story than command examples alone: two profiles, one Mac, no token swapping. - The README should sell the feature while staying explicit that this is Codex state isolation, not full OS credential isolation. - Existing README-relative media should not be omitted from npm package contents. Tests: - make test - make lint - npm pack --dry-run --json - git diff --check Co-authored-by: Codex <codex@openai.com>
Summary: - Tighten the README demo section around the parallel Desktop hero image. - Add launch-mode and isolation-boundary tables for app-instance. - Mirror the experimental Desktop security boundary in SECURITY.md. Rationale: - Make the PR easier to review by explaining why app and app-instance stay separate and what each command guarantees. - Keep the branding polished without overstating OS-level isolation. Tests: - git diff --check - make lint - npm pack --dry-run --json - make test Co-authored-by: Codex <codex@openai.com>
Summary: - Add a README section explaining the real school/personal account workflow that motivated codex-profile. - Note the changelog entry for the origin-story documentation. Rationale: - Make the project motivation concrete without encouraging token copying or overselling the isolation boundary. - Explain why separate Codex homes and parallel Desktop profiles matter for accounts with different limits and connector access. Tests: - git diff --check - make lint - npm pack --dry-run --json - make test Co-authored-by: Codex <codex@openai.com>
There was a problem hiding this comment.
Pull request overview
Adds an experimental multi-instance launch mode for Codex Desktop (app-instance) to support running multiple profile-isolated Desktop windows in parallel on macOS, alongside documentation, packaging, and test coverage updates.
Changes:
- Introduces
codex-profile app-instance <profile>to create/reuse a per-profile clonedCodex.app, patch bundle metadata, and launch with isolated Electron user data + instance logs. - Extends
logswith--instanceto read the newdesktop-instance.log. - Updates README/SECURITY/CHANGELOG and npm packaging (ships
media/), plus adds Bash test coverage for the new flow and completions/help output.
Reviewed changes
Copilot reviewed 5 out of 7 changed files in this pull request and generated 1 comment.
Show a summary per file
| File | Description |
|---|---|
bin/codex-profile |
Adds app-instance, clone/metadata helpers, logs --instance, and completion updates. |
test/codex-profile-test.sh |
Adds fake macOS tooling + new tests covering parallel instance launches, clone rebuild logic, and logs/completions output. |
README.md |
Documents the new experimental parallel Desktop workflow, isolation boundaries, and includes media assets. |
SECURITY.md |
Clarifies that app-instance is profile-level Desktop isolation, not OS-level isolation. |
CHANGELOG.md |
Notes the new command/features, tests, and related fixes. |
package.json |
Updates description and includes media/ in the published files list. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
Summary: - Merge current main into the app-instance PR branch. - Resolve the test runner conflict by keeping main\s forced-quit app test and the branch app-instance tests. Rationale: - Clear the PR merge conflict while preserving regression coverage from both branches. - Keep the branch aligned with main\s updated Desktop app quit behavior. Tests: - git diff --check - make lint - npm pack --dry-run --json - make test Co-authored-by: Codex <codex@openai.com>
Summary: - Teach the fake plutil helper to extract arbitrary plist keys, not only CFBundleName. - Add coverage proving compatible existing app-instance clones are reused instead of being rebuilt. Rationale: - Match the macOS plutil behavior used by app-instance metadata validation. - Prevent tests from masking bundle identifier or display name validation bugs. Tests: - git diff --check - make lint - npm pack --dry-run --json - make test Co-authored-by: Codex <codex@openai.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
app-instancecommand for launching profile-specific Codex Desktop app clones without quitting existing Codex windows.CODEX_HOME, Electron--user-data-dir, app-instance logs, and patched/re-signed app bundle metadata when macOS tooling is available.CFBundleNamefor Electron helper lookup and launch clones throughopen -n -a <clone> <workspace> --args ...so workspace folders are opened as documents instead of being treated as Electron app paths.logs <profile> --instance, completions/help/docs, changelog notes, npm media packaging, and Bash test coverage.Launch Flow
The normal Desktop command stays conservative:
codex-profile app dev ~/Dev/project-aThat flow treats Codex Desktop as one active profile at a time. It switches Desktop to the selected profile by quitting the currently running Codex app/app-server, then relaunching the canonical
/Applications/Codex.appwithCODEX_HOMEpointed at the selected profile home.The experimental multi-instance path is explicit:
For each profile,
app-instancecreates or reuses a cloned app bundle under~/Library/Application Support/codex-profile/app-instances/<profile>/, patches only the clone identity needed by macOS, keepsCFBundleName=Codexso Electron can still findCodex Helper.app, launches the workspace throughopen -n -a <clone> <workspace>, and passes profile-local Electron state with--user-data-dir=<profile-home>/electron-user-data.README / Branding
codex-profile appversuscodex-profile app-instancetable so the expected launch flow is obvious from the Quick Start.media/inpackage.jsonso README-relative images ship with the npm package.Review Hardening
client.a,client_a,client-a, andClient-Ado not collapse to the same macOS identity.open -a <app> <workspace> --args ...more accurately by treating workspace folders as document files, not argv passed to the executable.app-instanceprovides profile-level Desktop process isolation, not OS-level isolation.Why a Separate Command
appandapp-instanceare intentionally different promises:appis the predictable account-switching path: one Desktop process, one selectedCODEX_HOME, no app bundle cloning.app-instanceis the experimental power-user path: profile-specific cloned bundles, separate Electron user data, and multiple Desktop processes at once.Making
codex-profile app devorcodex-profile app defaultimplicitly spawn multiple Desktop instances would surprise existing users who expectappto switch the active Desktop profile. It would also mix the stable account-switching flow with the experimental clone flow, where app-server behavior, Electron helper lookup, macOS bundle metadata, and workspace launch semantics all matter.Validation
bash test/codex-profile-test.shshellcheck bin/codex-profile test/codex-profile-test.shmake testmake lintnpm pack --dry-run --jsongit diff --checkmedia/codex-profile-parallel-instances.pngpersonalandworkapp instances simultaneously; both stayed running with distinct profile-local--user-data-dirpaths.