- start.sh: never inject empty DISPLAY= into xvfb-run children
(was forcing Python headless and killing Turnstile)
- headed Chromium uses base flags only; headless-only flags
(disable-software-rasterizer/gpu) no longer applied under Xvfb
- Align closer to Git-creat7/grokRegister-cpa headed+extension path
Local probes showed resolve_browser_path=None on Windows, HeadlessChrome
hard-blocked by Cloudflare, and cookie text「接受所有 Cookie」unmatched.
Also add scripts/local_turnstile_probe.py for 3-step smoke checks.
readlink/realpath of /snap/bin/chromium becomes /usr/bin/snap, which is
not a browser and breaks DrissionPage launch. Keep the snap wrapper path,
reject snap host basenames, and prefer real deb chromium binaries.
Detect and prefer Chromium, auto-install when only Chrome is present,
and export BROWSER_PATH/BROWSER_PREFER into the register process so
Xvfb servers no longer fall back to google-chrome without extensions.
Google Chrome blocks --load-extension, so CF tokens stay empty under
Xvfb. Auto-select Chromium when the extension is present, install/
detect chromium in start.sh, and document browser_prefer overrides.
Enable Chromium on machines without DISPLAY: Python auto headless
with Xvfb hints, and start.sh installs/starts Xvfb (xvfb-run or
persistent :99) so registration can run headed under a virtual display.
Prefer Cloudflare Worker KV for verification codes with optional short IMAP
fallback disabled for private deploy; track config.json/.env for private repo.
Also add worker project, protocol mint backoff, and fail-fast Turnstile/mail
timeouts from batch runs.