Skip to content

fix(scripts): scrub CI / CONTINUOUS_INTEGRATION env vars in dev mode to keep ink interactive - #26838

Closed
pmenic wants to merge 2 commits into
google-gemini:mainfrom
pmenic:fix/issue-22452-ci-var-scrub-dev
Closed

pmenic wants to merge 2 commits into
google-gemini:mainfrom
pmenic:fix/issue-22452-ci-var-scrub-dev

Conversation

@pmenic

@pmenic pmenic commented May 10, 2026 •

Copy link
Copy Markdown
Contributor

Summary

npm run start hangs silently after the banner whenever the developer's shell has CI=true or CONTINUOUS_INTEGRATION=true. is-in-ci — loaded transitively by ink inside the spawned child — reads those env vars and makes ink disable interactive rendering.

The bundled path closes this via an esbuild alias that replaces is-in-ci with a constant false (#4822). That alias is never applied in the unbundled dev flow, so the silent-hang regression still bites contributors. See #22452 for the report.

This change strips the offending vars from the env passed to the dev child in scripts/start.js and prints a one-line stderr warning listing what was removed, plus a short note that the variables are not propagated to shell-tool subprocesses in dev (pointing developers who need them to the bundled build).

Scope is intentionally limited to scripts/start.js, so the bundled and production paths are untouched.

Scope of the filter

The filter targets exactly the two variables is-in-ci@2.0.0 actually consults:

// node_modules/ink/node_modules/is-in-ci/index.js
const check = (key) =>
  key in env && env[key] !== '0' && env[key] !== 'false';
const isInCi = check('CI') || check('CONTINUOUS_INTEGRATION');

Issue #22452 claimed any CI_*-prefixed variable also triggered the hang, but the is-in-ci source above shows that is not the case at the version pinned here. The filter therefore intentionally does not touch CI_TOKEN, CI_BUILD_ID, or any other CI_* developer-set token — those continue to propagate to the CLI process and to shell-tool subprocesses, matching the bundled-build behavior.

The filter also mirrors is-in-ci's truthiness rule (skip 0, false, or unset), so a developer who explicitly sets CI=0 to mark "not in CI" still sees no-op behavior here.

Why this approach

Two alternatives considered and rejected:

  • Runtime module shim of is-in-ci to mirror the bundled alias: requires a --import preloader or ESM loader hook for the dev flow, more moving parts, and still requires changing the spawn invocation.
  • Scrub inside packages/cli/index.ts at process startup: would also run in the bundled binary, duplicating the alias work and printing the warning in production for users who never see a hang.

Scrubbing only in the dev launcher is the smallest change that covers the bug, leaves production semantics untouched, and is naturally gated by the dev-mode entry point.

Test plan

Verified manually on Windows (the change is platform-neutral; pure env filtering in Node):

  • CI=true CI_TOKEN=x node scripts/start.js --version → warning lists only CI; CI_TOKEN preserved
  • CI=0 node scripts/start.js --version → no warning (matches is-in-ci falsy rule)
  • CONTINUOUS_INTEGRATION=1 node scripts/start.js --version → warning lists CONTINUOUS_INTEGRATION
  • No CI / CONTINUOUS_INTEGRATION set → no warning printed
  • node -c scripts/start.js — syntax OK
  • npx eslint scripts/start.js --max-warnings 0 — clean
  • pre-commit hook (prettier + eslint --fix) passes

Note: I did not add an automated test because scripts/start.js is a small integration-flavored launcher and exercising it end-to-end would require driving a real interactive Node child. Happy to extract the filter into a tiny pure helper with a unit test if reviewers prefer.

Fixes #22452

pmenic added 2 commits May 11, 2026 00:04
`scripts/start.js` is the entry point for `npm run start`. When the
developer's shell has `CI`, `CONTINUOUS_INTEGRATION`, or any `CI_*`
variable set (commonly `CI_TOKEN`, `CI_BUILD_ID`, etc.), `is-in-ci` —
loaded transitively by `ink` inside the spawned child — reports CI mode
and `ink` disables interactive rendering, leaving the CLI hanging
silently after the banner.

The bundled path already handles this via an esbuild alias that
replaces `is-in-ci` with a constant `false` (google-gemini#4822). That alias is
never applied in the unbundled `npm run start` flow, so the same
silent-hang regression still bites contributors with a `CI_TOKEN` in
their environment.

This change strips the offending vars from the env passed to the dev
child and prints a single stderr line listing what was removed, plus a
one-line note that the variables are not propagated to shell-tool
subprocesses in dev — pointing developers who need them to the bundled
build. Scope is limited to `scripts/start.js`, so the bundled and
production paths are untouched.

Verified manually:
- with `CI_TOKEN=x CI_BUILD_ID=y npm run start --version`, both vars
  are listed in the warning and stripped before spawn
- with no CI_* vars set, no warning is printed

Fixes google-gemini#22452
Reviewer pointed out that `is-in-ci@2.0.0` (the version pinned in this
repo's `ink` dependency) only checks `CI` and `CONTINUOUS_INTEGRATION`
— it does NOT look at any `CI_*`-prefixed variable, contrary to what
issue google-gemini#22452 stated. Source of truth:

  // node_modules/ink/node_modules/is-in-ci/index.js
  const check = (key) =>
    key in env && env[key] !== '0' && env[key] !== 'false';
  const isInCi = check('CI') || check('CONTINUOUS_INTEGRATION');

The previous patch over-filtered and would clear legitimate developer
env vars like `CI_TOKEN` / `CI_BUILD_ID` from the CLI process and from
shell-tool subprocesses without that being needed to keep `ink`
interactive.

This commit:
- Narrows the filter to exactly `CI` and `CONTINUOUS_INTEGRATION`
- Mirrors `is-in-ci`'s truthiness rule (skip `0` / `false` / unset),
  so `CI=0` no-ops just like upstream
- Updates the comment and stderr warning to say "CI-detection" instead
  of "CI-related", and explicitly notes that `CI_*` vars are preserved
@pmenic pmenic changed the title fix(scripts): scrub CI_* env vars in dev mode to keep ink interactive fix(scripts): scrub CI / CONTINUOUS_INTEGRATION env vars in dev mode to keep ink interactive May 10, 2026
@gemini-cli gemini-cli Bot added area/core Issues related to User Interface, OS Support, Core Functionality help wanted We will accept PRs from all issues marked as "help wanted". Thanks for your support! labels May 10, 2026
@pmenic
pmenic marked this pull request as ready for review May 10, 2026 22:32
@pmenic
pmenic requested a review from a team as a code owner May 10, 2026 22:32
@gemini-code-assist

Copy link
Copy Markdown
Contributor

Summary of Changes

Hello, I'm Gemini Code Assist1! I'm currently reviewing this pull request and will post my feedback shortly. In the meantime, here's a summary to help you and other reviewers quickly get up to speed!

This pull request addresses a regression where the development environment would hang silently when 'CI' or 'CONTINUOUS_INTEGRATION' environment variables were present. By filtering these specific variables in the development launcher, the CLI ensures that the 'ink' library maintains interactive rendering capabilities during local development, matching the behavior of the production bundled build.

Highlights

  • CI Environment Variable Filtering: Added logic to scripts/start.js to detect and remove 'CI' and 'CONTINUOUS_INTEGRATION' environment variables before spawning the development child process.
  • Interactive Rendering Fix: Prevents the 'ink' library from incorrectly detecting a CI environment, which previously caused the development server to hang silently.
  • Developer Feedback: Implemented a stderr warning that notifies developers when these variables are stripped, while explicitly preserving other 'CI_*' variables like tokens.
Using Gemini Code Assist

The full guide for Gemini Code Assist can be found on our documentation page, here are some quick tips.

Invoking Gemini

You can request assistance from Gemini at any point by creating a comment using either /gemini <command> or @gemini-code-assist <command>. Below is a summary of the supported commands on the current page.

Feature Command Description
Code Review /gemini review Performs a code review for the current pull request in its current state.
Pull Request Summary /gemini summary Provides a summary of the current pull request in its current state.
Comment @gemini-code-assist Responds in comments when explicitly tagged, both in pull request comments and review comments.
Help /gemini help Displays a list of available commands.

Customization

To customize the Gemini Code Assist for GitHub experience, repository maintainers can create a configuration file and/or provide a custom code review style guide (such as PEP-8 for Python) by creating and adding files to a .gemini/ folder in the base of the repository. Detailed instructions can be found here.

Limitations & Feedback

Gemini Code Assist may make mistakes. Please leave feedback on any instances where its feedback is incorrect or counterproductive. You can react with 👍 and 👎 on @gemini-code-assist comments. If you're interested in giving your feedback about your experience with Gemini Code Assist for GitHub and other Google products, sign up here.

Footnotes

  1. Review the Privacy Notices, Generative AI Prohibited Use Policy, Terms of Service, and learn how to configure Gemini Code Assist in GitHub here. Gemini can make mistakes, so double check it and use code with caution. ↩

@gemini-code-assist gemini-code-assist Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Code Review

This pull request updates scripts/start.js to strip CI-detection environment variables, specifically CI and CONTINUOUS_INTEGRATION, before spawning the development child process. This change ensures that the ink library maintains interactive rendering during npm run start, preventing the process from hanging in environments where these variables are set. I have no feedback to provide as there were no review comments.

@pmenic

pmenic commented May 10, 2026

Copy link
Copy Markdown
Contributor Author

Closing in favor of #25287 (aniruddhaadak80, opened 2026-04-13). I missed the existing PR when I picked up #22452 — should have searched for prior PRs first. Left a comment on #25287 with the correctness deltas from this PR's review for whoever lands the final fix.

@pmenic pmenic closed this May 10, 2026
@pmenic
pmenic deleted the fix/issue-22452-ci-var-scrub-dev branch May 10, 2026 22:42
@sripasg sripasg added the size/s A small PR label Jun 2, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

area/core Issues related to User Interface, OS Support, Core Functionality help wanted We will accept PRs from all issues marked as "help wanted". Thanks for your support! size/s A small PR

Projects

None yet

Development

Successfully merging this pull request may close these issues.

BUG: CI_* env var scrub not applied in dev mode (npm run start) — interactive mode hangs

2 participants