English | 简体中文
A configurable Chromium browser for automation, compatibility testing, and reproducible browser-identity experiments.
Chromix combines source-level Chromium patches with Python and Node.js SDKs. Use familiar Playwright objects, keep a stable profile across sessions, and configure language, timezone, display, and other browser-visible properties from one launch configuration. A separate Node entry point supports Puppeteer.
Project website · Download browser · Feature guide (中文) · Flag reference · Build guide · Report an issue
Project website walkthrough: language switching, Python/Node/Docker examples and the feature FAQ. These are recordings of the Chromix website, separate from browser-engine or detection-test results.
Watch the WebM video · Mobile screenshot · Open the website
| Capability | What you can do | Details |
|---|---|---|
| Python + Node automation | Launch Chromix through Playwright; use Puppeteer from Node | Python, Node |
| Persistent profiles | Retain cookies/localStorage and reuse a fingerprint seed | Profile example |
| Browser identity | Configure UA, platform, locale, timezone, hardware and display properties | Public flags |
| Proxy-aware configuration | Use HTTP/HTTPS/SOCKS proxies and optionally derive locale/timezone through GeoIP | Proxy example |
| Rendering and media policies | Configure native GPU policy, fonts, audio and codec restrictions | Backend policies |
| Input helpers | Add mouse, typing and scrolling timing with humanize |
SDK feature details |
| Encrypted cookie transfer | Export/import cookies between explicitly selected active contexts | Cookie migration |
| Portable distribution | Use a release ZIP or a Linux amd64/arm64 container | Downloads, Docker |
A persona is the browser identity configuration used for a launch. Its reported values, actual browser behavior, and underlying device capabilities have separate verification requirements. Chromix tracks those boundaries in FINGERPRINT_STATUS.md; website-specific detection outcomes depend on more than browser configuration.
Choose a language below. The SDK resolves a locally configured executable first; otherwise it downloads and caches the browser selected by its configured release channel.
The SDK's
latestchannel is a pinned mapping, separate from GitHub's Latest release. For a specific release such asv154.0.8037.97, download its package and setCLOAKBROWSER_BINARY_PATH, or use the pinned Docker image. Updating an SDK does not replace an explicitly configured browser.
Requires Python 3.8+ according to the package metadata; your Playwright version must also support your Python version.
python -m pip install chromix playwrightOn Linux, install Playwright's system dependencies if needed:
python -m playwright install-deps chromiumfrom chromix import launch
browser = launch(headless=True)
try:
page = browser.new_page()
page.goto("https://example.com")
print(page.title())
finally:
browser.close()Use launch_async, launch_context or launch_persistent_context for other lifecycles. See the Python API guide. To use this checkout's SDK, install ./sdk/python in place of chromix.
Requires Node.js 18+ according to the package metadata; choose a compatible automation-driver version. The npm package is @xiaoxiaofeihh/chromix. The unscoped chromix name belongs to an unrelated project.
npm install @xiaoxiaofeihh/chromix playwright-coreSave as example.mjs, then run node example.mjs:
import { launch } from "@xiaoxiaofeihh/chromix";
const browser = await launch({ headless: true });
try {
const page = await browser.newPage();
await page.goto("https://example.com");
console.log(await page.title());
} finally {
await browser.close();
}npm install @xiaoxiaofeihh/chromix puppeteer-coreUse the separate driver entry point:
import { launch } from "@xiaoxiaofeihh/chromix/puppeteer";
const browser = await launch({ headless: true });
try {
const page = await browser.newPage();
await page.goto("https://example.com");
console.log(await page.title());
} finally {
await browser.close();
}Driver-specific options and context ownership are explained in the Node API guide. Python provides Playwright integration.
The published Docker release provides 154.0.8037.97 for both amd64 and arm64 under latest and 154.0.8037.97. Docker's amd64 platform selects the release's linux-x64 archive; arm64 selects linux-arm64.
docker pull ghcr.io/xiaozhou26/chromix:latest
docker run --rm ghcr.io/xiaozhou26/chromix:latest --versionlatest selects the matching architecture at 154.0.8037.97; the existing 154.0.8037.57 tag remains unchanged for both architectures. The image is a non-root browser CLI; SDKs and a remote browser service are separate. See Docker setup and commands for checksum verification, sandbox requirements and headless use. The image build reuses release binaries rather than compiling Chromium again.
Use one user-data directory per identity. The SDK stores a seed with the profile so subsequent launches reuse it.
from chromix import launch_persistent_context
context = launch_persistent_context(
"./profiles/demo",
headless=False,
locale="en-US",
timezone="America/New_York",
)
try:
page = context.new_page()
page.goto("https://example.com")
finally:
context.close()Node uses launchPersistentContext({ userDataDir: "./profiles/demo", ... }). Keep concurrent browser processes on separate profile directories. For reproducible nonpersistent tests, pass an explicit args=["--fingerprint=42"] (Python) or args: ["--fingerprint=42"] (Node).
import os
from chromix import launch
browser = launch(
proxy=os.environ["CHROMIX_PROXY"],
geoip=True,
locale="en-US",
headless=True,
)
try:
page = browser.new_page()
page.goto("https://example.com")
finally:
browser.close()Set CHROMIX_PROXY to your proxy URL, for example http://user:pass@proxy.example:8080. Explicit locale/timezone settings take precedence over GeoIP results. GeoIP makes a metadata request through the effective proxy.
Authenticated SOCKS5 TCP requires a matching patched Chromix binary. WebRTC address presentation and actual traffic routing are separate: changing a candidate IP does not create a UDP tunnel. Read the WebRTC/proxy contract before relying on a particular network route.
Add humanize=True in Python or humanize: true in Node to enable the SDK's input helpers. Python accepts extension_paths; Node uses extensionPaths. Consult the SDK guides for the supported operations, presets and driver-specific restrictions. Input helpers do not establish website-specific detection guarantees.
Download ZIPs and their checksum files from the same release. Windows x64 / ARM64 and Linux x64 / ARM64 downloads use v154.0.8037.97. Only macOS x64 / ARM64 downloads retain v154.0.8037.57 until their newer packages are published.
| Target | Archive | Manual launcher inside the extracted directory |
|---|---|---|
| Windows x64 | chromix-win-x64.zip |
chromix/chromix.cmd |
| Windows ARM64 | chromix-win-arm64.zip |
chromix/chromix.cmd |
| Linux x64 / Docker amd64 | chromix-linux-x64.zip |
chromix/chromix |
| Linux ARM64 | chromix-linux-arm64.zip |
chromix/chromix |
| macOS Intel | chromix-mac-x64.zip |
chromix/chromix |
| macOS Apple Silicon | chromix-mac-arm64.zip |
chromix/chromix |
Platforms build and publish independently. Windows ARM64 cross-compiles on windows-2022 and uses windows-11-arm for native verification. macOS bundles have no Developer ID distribution signature or notarization. Linux needs compatible system libraries and a working Chromium sandbox.
Checksum files may be platform-specific. For v154.0.8037.97, Linux x64 uses SHA256SUMS, while Linux ARM64 uses SHA256SUMS-linux-arm64. Windows x64 uses SHA256SUMS-win-x64; its ZIP is also listed in the same release's main SHA256SUMS. Windows ARM64 uses SHA256SUMS-win-arm64. Select the file containing your exact ZIP name; do not assume the generic manifest lists every platform.
Linux x64 example, after downloading both files:
set -eu
archive=chromix-linux-x64.zip
awk -v name="$archive" '$2 == name || $2 == "*" name { print; count++ } END { if (count != 1) exit 1 }' SHA256SUMS > SHA256SUMS.selected
sha256sum -c SHA256SUMS.selected
unzip "$archive" -d chromix-linux-x64
./chromix-linux-x64/chromix/chromix --versionFor Linux ARM64, change the archive/directory to chromix-linux-arm64 and the manifest to SHA256SUMS-linux-arm64. On macOS use shasum -a 256 -c and preserve framework symlinks and executable permissions. On Windows use PowerShell Get-FileHash -Algorithm SHA256 to compare against the matching manifest before Expand-Archive.
For Actions artifacts, first extract GitHub's outer ZIP, then verify the inner browser archive. Detailed candidate verification is in BUILDING.md.
Set CLOAKBROWSER_BINARY_PATH in the same terminal as your SDK script. Keep the full extracted bundle next to the executable.
# Windows: actual executable, rather than the .cmd launcher
$env:CLOAKBROWSER_BINARY_PATH = "D:\chromix-win-x64\chromix\chrome.exe"# Linux
export CLOAKBROWSER_BINARY_PATH="/absolute/path/chromix/chrome"
# macOS (use this assignment instead on a Mac)
export CLOAKBROWSER_BINARY_PATH="/absolute/path/chromix/Chromium.app/Contents/MacOS/Chromium"Then use the usual SDK launch functions. This environment variable works in both SDKs. Python launch(executable_path=...) conflicts with the wrapper's own argument. Node's ordinary Playwright launches also accept launchOptions: { executablePath: "/absolute/path/to/chrome" } to bypass download; the Puppeteer entry point additionally accepts top-level executablePath. Measured-device launches have separate restrictions; see the Node guide.
Python SDK 152.0.7977.82.post4 and Node SDK 0.1.4 are published. Both Windows architectures and both Linux architectures map stable / latest to v154.0.8037.97. The SDKs also support the Windows release archive's path separators. macOS retains stable v151.0.7922.173 and latest v152.0.7977.75. A local browser can be selected with CLOAKBROWSER_BINARY_PATH. Upgrade with python -m pip install --upgrade chromix or npm install @xiaoxiaofeihh/chromix@latest. SDK package versions remain separate from the browser version.
These are separate version sources:
| Version source | Current checkout | Meaning |
|---|---|---|
| Linux / Windows source pins | Chromium 154.0.8037.97 |
Version compiled by those platform workflows |
| macOS source pin | Chromium 154.0.8037.97 |
Build cache from upstream run 37654894671; existing published downloads remain unchanged until the new build is verified |
Container latest / 154.0.8037.97 |
amd64 / arm64 154.0.8037.97 |
Both architectures use the same release; the old .57 tag is retained |
SDK Linux x64 / ARM64 stable / latest |
v154.0.8037.97 |
Platform-specific automatic download target |
SDK Windows x64 stable / latest |
v154.0.8037.97 |
Published in Python 152.0.7977.82.post3 / Node 0.1.3 |
SDK Windows ARM64 stable / latest |
v154.0.8037.97 |
Published in Python 152.0.7977.82.post4 / Node 0.1.4 |
SDK macOS stable |
v151.0.7922.173 |
Existing mapping retained; check asset availability |
SDK macOS latest |
v152.0.7977.75 |
Existing mapping retained; check asset availability |
Source pins are authoritative in build/ungoogled-revisions.psd1; channel mappings are in the Python and Node downloaders. CLOAKBROWSER_VERSION accepts a configured major or an exact four-part release version; an explicit channel takes precedence. Exact versions fail if the requested platform asset is absent. A source feature requires a browser built with the corresponding patches; an SDK update alone cannot add it to an older executable. The Windows ARM64 .97 package reuses the natively reverified 216-patch build; it does not include the new noise changes in the current source.
- Identity settings: supported flags and defaults are listed in the flag reference. Screen size and page viewport are separate settings.
- GPU behavior: the default uses the shared native policy. Identity templates and measured device records have different admission requirements; see GPU backend and device pool.
- Experimental controls: runtime suppression and the remote Canvas bridge are opt-in. The bridge's unsafe mode changes renderer sandboxing; read the patch documentation before enabling it.
- Evidence: fingerprint acceptance describes checks against the exact built executable. Unit tests, source patches, browser startup and full runtime acceptance establish different facts.
For a verified local executable, run a focused smoke check:
python3 tools/fingerprint_smoke.py \
--browser /absolute/path/chromix/chrome \
--platform linux --locale en-US \
--output /tmp/chromix-fingerprint-smoke.jsonThis requires Python Playwright and uses local test pages. It does not download a browser.
| Symptom | First checks |
|---|---|
| SDK downloads an older browser or returns 404 | Check configured channels and release Assets; use CLOAKBROWSER_BINARY_PATH for the exact build you downloaded |
| A flag has no visible effect | Confirm the executable version and relevant source feature; distinguish profile settings from native device capabilities |
| Linux fails to start | Check system libraries, sandbox support, user permissions and shared memory in containers |
| Headed mode fails on a server | Use headless mode or configure a display server |
| Proxy/GeoIP fails | Check credentials, DNS, protocol and metadata reachability through that proxy; explicit locale/timezone can avoid a GeoIP dependency |
| Windows crashes on reload | Follow Windows crash diagnostics and record the exact executable/build |
| A GitHub build fails | Reuse the latest verified uploaded file-tree checkpoint; see BUILDING.md for exact run/stage/attempt/asset inputs |
When reporting an issue, include OS/architecture, browser version, SDK version, launch options with credentials removed, build/run link, and a minimal reproduction.
| Goal | Read |
|---|---|
| Choose a feature and configure it | Feature guide (中文) |
| Use Python / async contexts | Python SDK |
| Use Node / Playwright / Puppeteer | Node SDK |
| Run a Linux container | Docker |
| Look up native browser switches | Fingerprint flags |
| Understand rendering and media behavior | Backend policy, Canvas, GPU |
| Evaluate device templates and measured records | Device pool |
| Inspect verification status | Status, coverage, acceptance |
| Compare CloakBrowser-compatible APIs | Functionality comparison, implementation history |
| Build, resume, package or publish | BUILDING.md |
The repository pins Chromium, ungoogled core and platform overlays, then applies the Chromix stack from patches/series. See BUILDING.md for per-platform dependencies and staged GitHub Actions builds.
Windows needs Visual Studio C++ tools and Windows SDK 10.0.28000.0, including Debugging Tools, plus Python, Git, PowerShell 7 and 7-Zip. Linux and macOS require their respective Chromium toolchains. Build caches restore source and intermediate outputs; Ninja recompiles outputs affected by changed inputs.
pwsh build/windows/build.ps1 -WorkDir D:\chromix-build -Jobs 8
# Continue with the same work directory:
pwsh build/windows/build.ps1 -WorkDir D:\chromix-build -Resume -Jobs 8Useful development checks, with the appropriate development dependencies installed:
python3 tools/check_patches.py
python3 -m unittest discover -s tools/tests -v
npm --prefix sdk/node test
git diff --checkpatches/ Chromium source patches and version-specific overrides
build/ Platform preparation, staged compilation and packaging
docker/ Release-based Linux container
site/ GitHub Pages project website
sdk/ Python and Node automation wrappers
tools/ Build validation, diagnostics and regression tests
docs/ Feature guides, design notes and acceptance boundaries
assets/fonts/ Font assets and provenance
Chromix's original code, patch integration and SDKs use the BSD 3-Clause License. Chromium, third-party components and fonts retain their own terms; see font provenance. Referenced projects retain their own branding and licensing.

