できない.dev

npm scripts で環境変数が設定できない(Windows で動かない)

"FOO=bar node app.js" の前置記法は POSIX シェル専用で、Windows 既定の cmd.exe では環境変数として解釈されない。
cross-env で OS 差を吸収するか、script-shell の変更や Node.js の --env-file で対処する。

#npm#scripts#env#windows#cross-env

公開:

要約

"build": "NODE_ENV=production node build.js" のような npm scripts が Windows で「'NODE_ENV' は、内部コマンドまたは外部コマンド…として認識されていません」と失敗するのは、FOO=bar command という環境変数の前置が POSIX シェルの構文だからです。
npm scripts は POSIX 環境では sh、Windows では cmd.exe で実行されます(npm config の script-shell)。
cmd.exe はこの記法を解釈できないため、環境変数が設定できないどころかコマンド自体が失敗します。

よくある原因

  1. 前置記法は sh 専用: FOO=bar node app.js は sh が「この 1 コマンドの間だけ FOO を設定する」と解釈する構文。
    cmd.exe では FOO=bar を実行ファイル名として探しに行く。
  2. set の空白混入: cmd.exe 流に set FOO=bar && node app.js と書くと、bar&& の間の半角スペースが値の末尾に入り、比較が一致しなくなる。
  3. .env の自動読み込みは無い: npm scripts は .env を読まない。
    dotenv や --env-file などの明示的な仕組みが必要。
  4. 参照記法の違い: スクリプト内の $FOO は cmd.exe では展開されず、%FOO% は sh では展開されない。

解決策

1. cross-env で OS 差を吸収する

npm install --save-dev cross-env
{
  "scripts": {
    "build": "cross-env NODE_ENV=production node build.js"
  }
}

cross-env が変数設定を OS ごとの正しい方法に変換するため、同じ script が Windows / macOS / Linux で動きます。

2. script-shell を POSIX シェルに変更する

npm config set script-shell "C:\\Program Files\\Git\\bin\\bash.exe"

Git Bash を npm scripts の実行シェルにすると、前置記法や $FOO がそのまま動きます。
ただしチーム全員の環境設定が前提になる点に注意してください。

3. --env-file で .env を読み込む

node --env-file=.env app.js

Node.js 20.6 以降は --env-file フラグで .env ファイルを process.env に読み込めます。
シェル非依存なので npm scripts に書いても OS を問わず動作します。

この記事は役立ちましたか?