Skip to content
CH SCShop classgeneral · beginner · ~25 min · 6 steps

How to install Composer (and understand what it actually does)

Install PHP's package manager and read a composer.json well enough to run updates on purpose instead of on faith.

August 10, 2026 · by Dane Petersen

Composer is the package manager for PHP — the tool that fetches Drupal core, WordPress libraries, and everything they depend on, in versions that agree with each other. Modern PHP sites assume it the way a canoe assumes a paddle. This lesson installs it on your own computer and, more importantly, teaches you to read what it’s about to do before you let it do it. You’ll need a terminal and PHP; if you’re working on a remote server instead, connect with SSH first and run the same commands there.

Check your PHP version

php -v

Composer 2 needs PHP 7.2.5 or newer, and in practice you want PHP 8.x — if php -v shows anything older, fix that first, because your site’s requirements will be stricter than Composer’s. No PHP at all? Install it with your package manager (brew install php on macOS, apt install php-cli on Debian/Ubuntu).

Download and install Composer

On macOS with Homebrew, brew install composer and skip to the next step. Everywhere else, use the official installer, which verifies its own checksum against the published signature:

php -r "copy('https://getcomposer.org/installer', 'composer-setup.php');"
php -r "if (hash_file('sha384', 'composer-setup.php') === trim(file_get_contents('https://composer.github.io/installer.sig'))) { echo 'Installer verified'.PHP_EOL; } else { echo 'Installer corrupt'.PHP_EOL; unlink('composer-setup.php'); exit(1); }"
php composer-setup.php
php -r "unlink('composer-setup.php');"

If it prints anything but “Installer verified”, stop and re-download — don’t run an installer that fails its own checksum.

Make it runnable from anywhere

The installer leaves a composer.phar in the current folder. Move it somewhere on your PATH so plain composer works from any directory:

sudo mv composer.phar /usr/local/bin/composer
composer --version

Read what composer.json is telling you

Open the composer.json at the root of any PHP project. The part that matters is require: each line is a package and a version constraint. "drupal/core-recommended": "^11.2" means “11.2 or any newer 11.x, never 12” — the caret is a promise to stay within the major version. require-dev lists tools for development only, and composer.lock is the trip log: the exact version of every package the last successful install actually used, written down so the trip can be repeated.

Learn the difference between install and update

This distinction prevents more outages than any other fact in this lesson. composer install reads the lock file and reproduces exactly what’s written there — safe, boring, what servers should run. composer update goes shopping for newer versions and rewrites the lock file — powerful, and never something to run casually on a live site. When you do update, name the package:

composer update drupal/MODULE_NAME --with-dependencies

A bare composer update updates everything at once, which turns “one module changed” into “what changed?” the moment something breaks.

Verify with a dry run

Composer will tell you its plans without acting on them:

composer update --dry-run

Run that in any project and read the list — every line is a change it would make, and nothing on disk moves. If composer --version prints a version and the dry run prints a plan instead of an error, you’re installed, and you now know the one habit that matters: read the plan, then decide. That’s the whole difference between updating on purpose and updating on faith.

That's the lesson. Back to the shop for more — or if this is the chore your organization never gets to,that's literally what we're for.