Python

There is no AI here. All content is human-authored and tested for accuracy.

Fix: error: externally-managed-environment on Mac

How to fix the 'error: externally-managed-environment' message when you run pip install on Mac. Four ways to fix it, ranked from best to last-resort.

This is the error you see when you run pip install:

$ pip install <package>
error: externally-managed-environment

Fixing this error is one step in setting up your Mac for Python development. See the Mac development setup guide.

Before you get started

You'll need a terminal application to fix the error and run Python. Apple includes the Mac terminal but I prefer Warp Terminal. Warp is an easy-to-use terminal application, with AI assistance to help you learn and remember terminal commands. Download Warp Terminal now; it's FREE and worth a try.

Fix the error: externally-managed-environment

You have four ways to fix this, in order of preference:

  1. Use uv (recommended): See Install uv on Mac. Use uv, the modern Python package and project manager. It sidesteps the problem entirely. Best choice for almost everyone.
  2. Use pipx for CLI tools: See Install pipx on Mac. If you're installing a standalone Python tool (such as Black, Ruff, youtube-dl, httpie, or cookiecutter), pipx is purpose-built for this and avoids the error.
  3. Use a virtual environment: create a venv with the standard library venv module, then run pip install inside it. Inline instructions below. (See Python's official venv documentation for full reference.)
  4. Override the lockout with --break-system-packages: Only as a last resort. Explanation and warning below.

Why this happens

Python 3.12+ implements PEP 668, which lets a Python distribution mark its install as "externally managed" so pip install can't write packages into the system site-packages directory. On Mac, this affects Homebrew's Python (the most common installed Python) or Apple's bundled system Python.

The error is by design. It protects your system Python from package conflicts and partially-broken upgrades. The fix is not to bypass the protection. The fix is to install your packages somewhere else (uv, pipx, or a virtual environment).

Choose the right fix

Match your situation to one of the four options:

  • If you are starting a new Python project: use uv. My recommended solution as it replaces pip, venv, and pyenv in one tool.
  • If you are installing a standalone Python CLI tool (such as Black, Ruff, httpie, cookiecutter, or youtube-dl): use pipx.
  • If you are already comfortable with pip and you just need packages for one project: use a virtual environment (python -m venv).
  • If you are installing on a one-off ephemeral system (such as a CI image or throwaway VM) and you understand the risk: use --break-system-packages.

Fix 1: Use uv (recommended)

The tool uv is an all-in-one Python package and project manager from Astral, written in Rust. It manages Python versions, virtual environments, and packages in a single tool. Because it never touches the system Python's site-packages, PEP 668 does not apply.

Install uv with Homebrew (or with the official installer curl -LsSf https://astral.sh/uv/install.sh | sh):

$ brew install uv

Then add packages to a uv-managed project, or use the pip-compatible interface:

$ uv add <package>
$ uv pip install <package>

See the full guide: Install uv on Mac.

Fix 2: Use pipx for CLI tools

The tool pipx installs each Python command-line tool in its own isolated environment, so dependencies never conflict and PEP 668 is not triggered. It is the right tool for standalone applications such as youtube-dl, httpie, cookiecutter, Black, and Ruff.

Install pipx with Homebrew:

$ brew install pipx
$ pipx ensurepath

Then install a tool:

$ pipx install <package>

See the full guide: Install pipx on Mac.

Fix 3: Use a virtual environment (venv)

A virtual environment is a self-contained directory with its own Python and its own site-packages. Running pip install inside an activated venv writes to the venv, not to the system Python, so PEP 668 does not apply.

Create, activate, install, and deactivate:

$ python -m venv .venv
$ source .venv/bin/activate
$ pip install <package>
$ deactivate   # when done

Use python -m pip install <package> instead of pip install <package> to avoid a "shadowed" pip. The python -m prefix ensures the package goes into the Python interpreter you actually have activated.

For full reference, see Python's official venv documentation.

Fix 4: Override the lockout with --break-system-packages

Warning: Bypassing PEP 668 can break your system Python or Homebrew's Python, and can silently introduce dependency conflicts that surface much later. Don't do this on a Mac you rely on for development. Use this only on ephemeral systems (such as CI runners, disposable Docker images, or scratch VMs) where breaking the Python install has no downstream cost.

Pass the flag on a single command:

$ pip install --break-system-packages <package>

Or set the environment variable so every pip install in the session uses it:

$ export PIP_BREAK_SYSTEM_PACKAGES=1

If you're tempted to use this on your main Mac, use uv or pipx instead.

Other common errors

For the error:

$ python ...
zsh: command not found: python

See our guide command not found: python.

For the error:

$ pip install <package>
zsh: command not found: pip

See our guide command not found: pip.

You'll see these errors if Python or Pip is not installed or not in the Mac PATH.

Continue setting up your Mac

Don't miss the full visual roadmap and checklist that shows how to set up a Mac for software development, with all the essential tools and settings you might not yet know about.