「自分のPCでは動くのに」を直す:環境差をAIと洗い出すチェック表
AIを使いこなすClaudeで執筆し、GPTで自動校閲・修正しています。

本番(またはCI、友人のPC)で動かないとき、いちばん効率がよいのは、エラー文を読み込む前に「動く環境」と「動かない環境」を同じ項目で並べることです。差が見つかった項目が、原因の候補になります。AIにはこの比較表の作成と差分の読み取りを任せ、どれが本当の原因かは、人が1項目ずつ揃えて再実行して確かめます。 この記事では、AIが書いたプログラムを直したい人向けに、次の3つを用意しました。 • 両環境の情報を同じ形で書き出す比較シート • シートの情報を自動で集める小さなスクリプト(説明用の例) • 比較結果をAIに渡す依頼文と、差分の優先順位表 なお、スクリプトや依頼文は説明用の例で、この記事のために実行して結果を確かめたものではありません。自分の環境で試して、出力を確認してから使ってください。
まず比較シートを埋める
次の表を、動く環境(A)と動かない環境(B)の両方で埋めます。AIに頼む場合も、この形を崩さずに渡すと差分を見つけてもらいやすくなります。
- 実行環境、項目:OS・CPUの種類、環境A(動く):、環境B(動かない):、確認のしかた:スクリプトのplatform/arch
- 実行環境、項目:Nodeのバージョン、環境A(動く):、環境B(動かない):、確認のしかた:node -v
- 実行環境、項目:npmのバージョン、環境A(動く):、環境B(動かない):、確認のしかた:npm -v
- 依存関係、項目:ロックファイルの有無、環境A(動く):、環境B(動かない):、確認のしかた:スクリプトのlockfile
- 依存関係、項目:インストール方法、環境A(動く):、環境B(動かない):、確認のしかた:実行したコマンドをそのまま書く
- 設定、項目:環境変数(名前と有無のみ)、環境A(動く):、環境B(動かない):、確認のしかた:スクリプトのenv
- 設定、項目:NODE_OPTIONSの有無、環境A(動く):、環境B(動かない):、確認のしかた:環境変数の一覧で確認
- ファイル、項目:作業ディレクトリ、環境A(動く):、環境B(動かない):、確認のしかた:cwd
- ファイル、項目:パス区切り・大文字小文字、環境A(動く):、環境B(動かない):、確認のしかた:pathSep、ファイル名の綴り
- ファイル、項目:改行コード設定、環境A(動く):、環境B(動かない):、確認のしかた:git config core.autocrlf、.gitattributes
- 実行方法、項目:起動コマンド、環境A(動く):、環境B(動かない):、確認のしかた:package.jsonのscriptsなど
ポイントは、環境変数は値ではなく「設定あり/未設定/空文字」で書くことです。APIキーやDBの接続文字列をそのままAIのチャット欄に貼るのは避けます。
情報を集めるスクリプト(説明用の例)
両環境のプロジェクトのルートで実行し、出力をシートに写します。環境変数の値は出さず、有無と文字数だけを表示します。keysは自分のプロジェクトで使っている名前に書き換えてください。
// env-report.mjs (説明用の例)
import fs from 'node:fs';
import path from 'node:path';
import process from 'node:process';
const keys = ['NODE_ENV', 'NODE_OPTIONS', 'DATABASE_URL', 'API_KEY', 'PORT', 'TZ'];
const describe = (v) =>
v === undefined ? '未設定' : v === '' ? '空文字' : `設定あり(${v.length}文字)`;
const report = {
node: process.version,
platform: process.platform,
arch: process.arch,
cwd: process.cwd(),
pathSep: path.sep,
ci: process.env.CI ?? '未設定',
lockfile: ['package-lock.json', 'pnpm-lock.yaml', 'yarn.lock']
.filter((f) => fs.existsSync(f)),
env: Object.fromEntries(keys.map((k) => [k, describe(process.env[k])])),
};
console.log(JSON.stringify(report, null, 2));実行はnode env-report.mjsです。Nodeのprocessには、process.version、process.platform、process.cwd()、process.envが用意されています。platformはlinux、darwin、win32などの文字列で返ります。
項目ごとに、なぜ差が出るのか
OSとパス
Nodeのpathモジュールの説明では、パス区切り(path.sep)はWindowsが\、POSIX系が/です。PATHのような環境変数の区切り文字(path.delimiter)はWindowsが;、POSIX系が:です。AIが書いたコードに'data\\file.txt'のような文字列の直書きやsplit('/')があると、OSが変わった時点で壊れます。
ファイル名の大文字小文字も要注意です。Logo.pngをlogo.pngと書いてしまっても、大文字小文字を区別しない設定の環境では動き、区別する環境では「ファイルが見つからない」になることがあります(編集上の経験則であり、環境の設定によります)。
環境変数
環境変数はプロセスごとに引き継がれるため、ターミナルで設定した値や.envの内容が、本番のサーバーやCIには存在しないことがよくあります。NodeのCLIドキュメントによると、NODE_OPTIONSでもNode.jsのオプションを渡せ、コマンドラインで直接指定した値のほうが優先されます。起動方法が違うと挙動が変わる原因になります。
またprocess.envに代入した値は文字列になる、とNodeのprocessの説明にあります。PORTやDEBUG=falseを数値や真偽値のつもりで比較しているコードは、設定の渡し方で結果が変わります。Windowsでは環境変数名の大文字小文字が区別されない点も、同じページに書かれています。
CIでは、GitHub Actionsの変数のドキュメントのとおりCIとGITHUB_ACTIONSがtrueになり、RUNNER_OSやRUNNER_ARCHなどのランナー情報も設定されます。コードがCIの有無で挙動を変えていないかも見る価値があります。
改行コード
Gitは設定によって、チェックアウト時に改行を変換できます。gitattributesではtextやeol属性、core.autocrlfの扱いが説明されています。シェルスクリプトがCRLFで保存されたためLinuxで失敗する、といった症状は、このあたりを疑います。リポジトリに.gitattributesがあるか、*.sh text eol=lfのように指定されているかを比べてください。
Nodeのバージョン
Nodeにはリリース区分があり、本番アプリケーションにはActive LTSかMaintenance LTSを使うことが案内されています。手元がCurrent版で本番がLTSの場合は、バージョン差を確認する候補になります。バージョンの差が出たら、手元のほうを本番に合わせるのが最初の手です。
AIに渡す依頼文
シートとスクリプトの出力を貼り、次のように頼みます。エラー文があれば、機密部分を伏せて一緒に渡します。
手元(環境A)では動き、本番(環境B)では動かないプログラムの原因を探しています。
下の2つの環境情報を比べて、次の順に答えてください。
1. 差がある項目の一覧(表形式)
2. 各差がエラー内容に関係しそうな理由と、可能性の高さ(高/中/低)
3. 1項目ずつ確かめるための手順(1回に変える項目は1つ)
4. 追加で教えてほしい情報
守ってほしいこと:
- 情報が足りない項目は推測で埋めず「不明」と書く
- 原因を断定せず、確認方法とセットで書く
- 環境変数の値は伏せてあるので、値の中身は想像しない
【エラーメッセージ(伏せ字済み)】
(ここに貼る)
【環境A(動く)】
(スクリプトの出力)
【環境B(動かない)】
(スクリプトの出力)コードの修正案が欲しい場合は、先に原因の候補を確認してから「パス区切りの直書きをなくす修正案」のように範囲を決めて頼むほうが安全です。
差分の優先順位表
AIが返した差分は、次の表で確認の順番を決めます。これは編集上の目安です。
- Nodeのバージョン、エラーの出方の例:構文エラー、未対応のAPI、先に確かめること:Bのバージョンに揃えてAで再実行
- 環境変数が未設定、エラーの出方の例:undefinedの参照、接続失敗、先に確かめること:Bに名前が登録されているか、空文字ではないか
- OS・パス、エラーの出方の例:ファイルが見つからない、先に確かめること:パスをpath.joinなどで組み立てているか
- 改行コード、エラーの出方の例:シェルが起動しない、diffが全行に出る、先に確かめること:.gitattributesとcore.autocrlf
- ロックファイルなし、エラーの出方の例:依存パッケージの版が違う、先に確かめること:ロックファイルをコミットして同じ版を入れる
確かめるときの進め方
- 差分のうち、1つだけを環境Aで本番に揃えます(例:Nodeのバージョンを合わせる)。
- 再現するか確かめます。再現したら、その差が原因の有力候補です。
- 再現しなければ元に戻し、次の項目へ進みます。複数を同時に変えると、何が効いたのか分からなくなります。
- 直ったら、原因になった項目をREADMEやCIの設定に書き残します。
AIは差分の整理と手順の提案には向いていますが、実際に環境を揃えて動かした結果は、人が確かめるものです。結果が想定と違った場合は、その出力をシートに追記して、もう一度同じ依頼文で渡してください。

