pypa/pip · error · CommandError

Target path exists but is not a directory, will not continue

Error message

Target path exists but is not a directory, will not continue.

What it means

Raised in InstallCommand.run() at install.py:416-424 when the path passed to --target exists on the filesystem but is not a directory (it is a regular file, a symlink to a file, a device node, etc.). pip needs a real directory to move installed package files into, so it refuses to overwrite a non-directory path.

Source

Thrown at src/pip/_internal/commands/install.py:422

            options.use_user_site,
            prefix_path=options.prefix_path,
            target_dir=options.target_dir,
            root_path=options.root_path,
            isolated_mode=options.isolated_mode,
        )

        target_temp_dir: TempDirectory | None = None
        target_temp_dir_path: str | None = None
        if options.target_dir:
            options.ignore_installed = True
            options.target_dir = os.path.abspath(options.target_dir)
            if (
                # fmt: off
                os.path.exists(options.target_dir) and
                not os.path.isdir(options.target_dir)
                # fmt: on
            ):
                raise CommandError(
                    "Target path exists but is not a directory, will not continue."
                )

            # Create a target directory for using with the target option
            target_temp_dir = TempDirectory(kind="target")
            target_temp_dir_path = target_temp_dir.path
            self.enter_context(target_temp_dir)

        session = self.get_default_session(options)

        target_python = make_target_python(options)
        finder = self._build_package_finder(
            options=options,
            session=session,
            target_python=target_python,
            ignore_requires_python=options.ignore_requires_python,
        )
        build_tracker = self.enter_context(get_build_tracker())

View on GitHub (pinned to d7d0d0a394)

Solutions

  1. Remove or rename the existing non-directory path, then re-run.
  2. Choose a different --target path that is a directory or does not yet exist (pip will create it).
  3. If it is a stale symlink, delete it with 'rm <path>' first.
  4. Verify the path with 'ls -la <path>' to confirm its type before re-running.

Example fix

# before (./build is a regular file)
pip install --target ./build requests
# after
rm ./build && pip install --target ./build requests
Defensive patterns

Strategy: validation

Validate before calling

import os, sys

target = None
for i, a in enumerate(sys.argv):
    if a in ('-t','--target') and i+1 < len(sys.argv):
        target = sys.argv[i+1]
    elif a.startswith('--target='):
        target = a.split('=',1)[1]
if target and os.path.exists(target) and not os.path.isdir(target):
    print(f'ERROR: --target {target} is not a directory', file=sys.stderr)
    sys.exit(2)

Prevention

When it happens

Trigger: Running 'pip install --target <path>' where <path> resolves via os.path.exists() but fails os.path.isdir(). Commonly <path> is an existing file, a broken or file-pointing symlink, or a named pipe.

Common situations: Typing a filename instead of a directory name for --target; a previous build created a file at that path; using --target ./requirements.txt by confusing it with -r; leftover symlinks from a broken setup.

Related errors


AI-assisted analysis of pypa/pip@d7d0d0a394 (2026-08-04). Data as JSON: /data/errors/9fb4d734bd5c1b8b.json. Report an issue: GitHub.