こんにちは!開発チームのリードエンジニアをしている先輩です。
これからPHPのフレームワークやモダンなライブラリを使って開発していくあなたへ、とても大切で、かつ毎日のコーディングを劇的に快適にする「ComposerのVendor Binの使いこなし方」についてお話ししますね。
PHPで開発をしていると、コード整形ツールの `PHP_CodeSniffer` や、テストフレームワークの `PHPUnit`、静的解析ツールの `PHPStan` など、開発を助けてくれる強力なCLI(コマンドライン)ツールに出会います。
ここで多くの初心者がやってしまいがちなのが、これらのツールを `composer global require` でPC全体(グローバル)にインストールしてしまうこと。実はこれ、チーム開発や長期的なプロジェクト運用の観点から見ると、将来的に「地獄の環境依存トラブル」を引き起こす最大の原因の一つなんです。
今回は、なぜグローバルインストールを避けるべきなのか、そしてプロジェクトごとにツールを安全かつスマートに管理する「Vendor Bin」の仕組みを、一歩ずつ優しく解説していきますね。これをマスターすれば、あなたの開発環境はプロのエンジニアのそれになりますよ!
—
1. なぜ「グローバルインストール」を避けるべきなのか?
まずは、私たちが直面しがちな「あるあるな悲劇」からお話ししましょう。
例えば、あなたが個人でPHPの勉強をしているときは、便利だからとCLIツールをグローバル領域にインストールしがちです。しかし、いざチームで複数人のプロジェクトに参加したり、過去に作ったアプリを数ヶ月ぶりに触ったりしたとき、こんな問題が起きませんか?
- 「AのプロジェクトではPHPUnitのバージョン9が必要なのに、Bのプロジェクトではバージョン10が必要で、グローバルだと片方が動かなくなる!」
- 「新しいメンバーが参画したとき、ローカルPCにどのツールをどのバージョンでグローバルインストールすべきか、手動のマニュアルを渡さなきゃいけない(そして必ず誰かが手順をミスる)。」
内部で何が起きているのか?
グローバルインストール(`~/.composer/vendor/bin` などにツールを置く方式)は、PC全体で「常に1つのバージョン」しか保持できません。そのため、プロジェクトが変わるたびにツールのバージョン差異による予期せぬエラー(構文エラーや非推奨警告の暴走など)に悩まされることになります。
Vendor Binという「プロジェクト完全カプセル化」の思想
これに対するアーキテクト的な解が 「プロジェクトごとのローカルインストール(Vendor Bin)」 です。
Composerは、プロジェクトのルートディレクトリにある `vendor/` の中に、そのプロジェクトが必要とするライブラリだけでなく、開発用CLIツールの実行ファイル(バイナリ)も `vendor/bin/` という専用ディレクトリにすっぽり収めてくれます。
つまり、「このプロジェクトを動かすためのツール群は、すべてこのプロジェクトフォルダの中に完結している」状態を作れるのです。これなら、プロジェクトAとプロジェクトBで異なるバージョンのツールが共存していても、お互いに干渉することは絶対にありません。
—
2. 基礎セットアップ:Vendor Binを安全に使いこなす手順
それでは、実際にプロジェクトを新規作成し、Composerを使ってCLIツール(今回はコード整形ツールの `PHP_CodeSniffer` を例にします)を安全に導入する手順をステップバイステップで見ていきましょう。
ステップ1: プロジェクトの初期化
まずは、作業用のディレクトリを作り、Composerの管理ファイルである `composer.json` を生成します。
作業用ディレクトリを作成して移動
mkdir my-php-project
cd my-php-project
対話式をスキップしてデフォルトのcomposer.jsonを生成
composer init –no-interaction
このコマンドにより、プロジェクトのルートに `composer.json` が生成されます。
ステップ2: 開発用依存関係としてツールをインストール
次に、プロジェクト固有のツールをインストールします。ここで重要なのは、プロダクション(本番環境)のコードには不要な開発支援ツールなので、`–dev` オプションをつけることです。
PHP_CodeSnifferを開発用依存関係としてインストール
composer require –dev squizlabs/php_codesniffer
【内部で何が起きたか?】
1. ComposerがPackagistから `squizlabs/php_codesniffer` の最適なバージョンをダウンロード。
2. プロジェクト内に `vendor/` ディレクトリが作成され、ライブラリの実体が配置される。
3. `vendor/bin/` ディレクトリの中に、実行ファイル(`phpcs` など)へのシンボリックリンク(またはラッパースクリプト)が自動生成される。
4. `composer.json` の `require-dev` セクションに依存関係が自動記録される。
これで、プロジェクトフォルダの中に専用の `phpcs` が用意されました!
—
3. パスを通す、あるいはComposer経由でスマートに実行する
さて、インストールしたツールを実行するにはどうすればよいでしょうか?
通常であれば、`./vendor/bin/phpcs –version` のように相対パスで実行する必要がありますが、毎度この長いパスを打つのは面倒ですよね。ここで2つのスマートな解決策があります。
アプローチA: シェルのPATHに `vendor/bin` を追加する(推奨)
あなたの使っているシェル(ZshやBash)の設定ファイル(`~/.zshrc` や `~/.bash_profile` など)に、カレントプロジェクトの `vendor/bin` を参照するパスを追加します。
実は、Composerには賢い機能があり、プロジェクトルートからの相対パスで `vendor/bin` をスマートに扱えるように設定できますが、グローバルにパスを通すのではなく、「プロジェクト内の `vendor/bin` を優先的に実行できるようにする」のがモダンなアプローチです。
例えば、プロジェクト固有のパスを通すのが面倒な場合、多くの開発者は次のように `composer.json` の `scripts` 機能を利用します。
アプローチB: `composer.json` の `scripts` を定義する(最も安全でチーム共有しやすい)
チームメンバー全員が同じコマンドでツールを実行できるように、`composer.json` にショートカットを定義しましょう。
`composer.json` を次のように編集してください。
{
“name”: “your-name/my-php-project”,
“type”: “project”,
“require”: {},
“require-dev”: {
“squizlabs/php_codesniffer”: “^3.7”
},
“scripts”: {
“lint”: “vendor/bin/phpcs”,
“lint:fix”: “vendor/bin/phpcbf”
}
}
- `require-dev`: 開発時のみ必要なツール(PHP_CodeSniffer)のバージョンを指定。
- `scripts`: 複雑なコマンド(`vendor/bin/phpcs`)に `composer lint` という短い別名(エイリアス)を付け、OS環境に依存せず実行できるようにしている。
—
4. 精度高い「HelloWorld」的動作確認
それでは、正しくVendor Binが機能し、ツールが動作するかをテストしてみましょう。
ステップ1: 検証用のPHPファイルを作成する
あえてPHP_CodeSnifferの規約に違反するような(インデントがバラバラな)コードを書いてみます。
プロジェクトのルートに `index.php` を作成してください。
ステップ2: Composerスクリプト経由でツールを実行する
先ほど `composer.json` の `scripts` に定義した `lint` コマンドを実行してみましょう。
composer lint index.php
【実行ログの例】
> vendor/bin/phpcs index.php
FILE: /path/to/my-php-project/index.php
———————————————————————-
FOUND 1 ERROR AFFECTING 1 LINE
———————————————————————-
3 | ERROR | [x] Semicolon closer must not be preceded by whitespace
———————————————————————-
PHPCBF CAN FIX THE 1 MARKED VIOLATION AUTOMATICALLY
———————————————————————-
見事にPHP_CodeSnifferが検知し、「セミコロンの前に空白があって規約違反だよ」と教えてくれました!
さらに、自動修正コマンドも `scripts` 経由で実行できます。
composer lint:fix index.php
実行後、`index.php` を確認してみてください。セミコロンの前の余分なスペースが綺麗に削除されているはずです。
—
5. まとめ:チーム開発における究極のメリット
いかがでしたでしょうか? 今回の一連の流れを整理します。
1. グローバルインストールをしないことで、PC全体の環境を汚さず、プロジェクトごとの依存関係の衝突を防ぐ。
2. `vendor/bin/` にツールがカプセル化されるため、「動かない!」という環境差分がなくなる。
3. `composer.json` の `scripts` を使えば、チームメンバー全員が `composer lint` などの統一されたコマンドで開発ツールを叩けるようになる。
新しく参画したメンバーは、リポジトリをクローンして `composer install` を叩くだけで、プロダクションコードも開発用CLIツールも、すべてが完璧に同期された状態で開発をスタートできます。
これをマスターすれば、あなたの毎日のコーディング、そしてチームでのコードレビューやCI/CDパイプラインの構築が劇的に楽になりますよ。ぜひ、今日のプロジェクトから取り入れてみてくださいね!