start here

macOS Setup

On macOS, PHP is commonly installed through Homebrew, a local development app such as Herd, MAMP, or Laravel Valet, or a project container. The key skill is not memorising one installer. It is proving which PHP your shell and project are actually using.

macOS setup bugs usually come from PATH order, multiple PHP versions, missing extensions, or a mismatch between CLI PHP and the PHP used by a local web server.

Homebrew Paths

Homebrew installs into different default locations depending on the Mac:

Apple Silicon: /opt/homebrew
Intel: /usr/local

That affects where php may live:

/opt/homebrew/bin/php
/usr/local/bin/php

Check the active binary:

which php
php -v

If which php points somewhere unexpected, your shell PATH is choosing a different PHP installation.

PATH Order

Your shell searches PATH from left to right. The first matching php wins.

echo $PATH
which -a php

which -a php is useful because it shows all matching PHP binaries your shell can see, not only the first one.

Common shell config files on macOS include:

~/.zshrc
~/.zprofile
~/.bash_profile

After changing PATH, open a new terminal or reload the shell config before checking again.

Configuration And Extensions

Once the active binary is right, inspect its configuration:

php --ini
php -m
php -i | grep "Loaded Configuration File"

Important project extensions often include:

mbstring
intl
pdo
pdo_mysql
curl
zip
gd

Check one extension quickly:

php -r "var_dump(extension_loaded('mbstring'));"

From a PHP script:

PHP example
<?php

declare(strict_types=1);

foreach (['mbstring', 'intl', 'pdo'] as $extension) {
    echo $extension . ': ';
    echo extension_loaded($extension) ? 'loaded' : 'missing';
    echo PHP_EOL;
}

// Prints:
// mbstring: loaded
// intl: loaded
// pdo: loaded

Composer Checks

After PHP is installed and visible, check the project requirements:

composer check-platform-reqs

If Composer reports the wrong PHP version or a missing extension, compare:

which php
php -v
php -m
composer --version

Composer is only as useful as the PHP runtime it is using. If your editor, terminal, and local web server use different PHP binaries, setup problems will feel random.

Local Web Options

For a quick local request, the built-in server is enough:

php -S 127.0.0.1:8000 -t public

For project-style local development, teams often use Valet, Herd, Docker, or another app that manages DNS, TLS, PHP versions, and services. Those tools are useful, but they do not remove the need to check the active PHP version and extensions.

Services

If PHP-FPM is managed by Homebrew, it may run as a service. The exact service name depends on the installed formula and version, but the professional check is the same: confirm what service is running and which PHP binary/configuration it uses.

Useful commands include:

brew services list
php --ini
php-fpm -v

Do not assume restarting a terminal restarts PHP-FPM. CLI PHP and FPM are different processes.

macOS Setup Checklist

For a macOS project setup, record:

  1. Which tool installs PHP.
  2. Which PHP version the project expects.
  3. What which php returns.
  4. What php -v returns.
  5. What php --ini returns.
  6. Which extensions are required.
  7. How to run composer check-platform-reqs.
  8. How local HTTP requests are served.

This is the information a teammate needs when their machine behaves differently from yours.

What You Should Be Able To Do

After this lesson, you should be able to find the active PHP binary on macOS, understand why Apple Silicon and Intel paths differ, check PATH order, inspect loaded configuration, check extensions, and verify a project with Composer.

For junior PHP work, this matters because macOS setup is common in development teams. The useful skill is proving the environment, not just saying PHP is installed.

Practice

Practice: Create A macOS PHP Setup Note

Create a short macOS setup note for a project.

Task

Include commands to show:

  • active PHP binary
  • all visible PHP binaries
  • PHP version
  • loaded configuration files
  • loaded extensions
  • Composer platform requirements

Also note whether the machine is Apple Silicon or Intel and why that changes likely Homebrew paths.

Show solution

A useful macOS setup note proves the runtime instead of only naming the installer.

uname -m
which php
which -a php
php -v
php --ini
php -m
composer check-platform-reqs

Example notes:

Architecture: arm64
Expected Homebrew prefix: /opt/homebrew
Active PHP: /opt/homebrew/bin/php
Project PHP requirement: check composer.json

Apple Silicon Macs usually use /opt/homebrew; Intel Macs usually use /usr/local. If PATH points at the wrong prefix, the terminal may run a different PHP version from the one the project expects.

Task: Path Check

Create a short checklist for diagnosing a wrong PHP version on macOS.

Requirements

Include:

  • commands to inspect PATH
  • commands to list all visible php binaries
  • likely Homebrew prefixes for Apple Silicon and Intel
  • which shell config files you would inspect

Afterward, add a short note explaining why opening a new terminal can matter after PATH changes.

Show solution
echo $PATH
which php
which -a php
php -v

Likely Homebrew prefixes:

Apple Silicon: /opt/homebrew
Intel: /usr/local

Shell files to inspect:

~/.zshrc
~/.zprofile
~/.bash_profile

Opening a new terminal can matter because shell configuration is read when the shell starts. If you edit PATH and keep using the old shell session, it may still have the previous PATH value.

Task: Extension Check

Create a macOS extension check for a PHP project.

Requirements

Include:

  • a terminal command to list extensions
  • a terminal command to check one extension
  • a PHP snippet that checks mbstring, intl, and pdo
  • a Composer command that checks project platform requirements

Use strict types in the PHP snippet. Keep example output inside the PHP code block as comments.

Show solution
php -m

Check one extension:

php -r "var_dump(extension_loaded('mbstring'));"

Check project requirements:

composer check-platform-reqs

Use PHP when you want a repeatable project check:

PHP example
<?php

declare(strict_types=1);

foreach (['mbstring', 'intl', 'pdo'] as $extension) {
    echo $extension . ': ';
    echo extension_loaded($extension) ? 'loaded' : 'missing';
    echo PHP_EOL;
}

// Prints:
// mbstring: loaded
// intl: loaded
// pdo: loaded

If an extension is missing, confirm which PHP binary is active before installing anything. Installing an extension for a different PHP runtime will not fix the project.