composer/composer · error · RuntimeException
You are on an old Windows / old PHP combo which does not all
Error message
You are on an old Windows / old PHP combo which does not allow Composer to use junctions/symlinks and this path repository has symlink:true in its options so copying is not allowed
What it means
Thrown by PathDownloader::computeAllowedStrategies() (line 297-303) on Windows when the symlink strategy is selected but safeJunctions() returns false. safeJunctions() requires proc_open and Windows >= 7 (version 6.1) due to a PHP bug (bugs.php.net/77552) that makes junction removal data-loss-prone on older combos. If mirror is not an allowed fallback (symlink:true forced), it throws.
Source
Thrown at src/Composer/Downloader/PathDownloader.php:299
$mirrorPathRepos = Platform::getEnv('COMPOSER_MIRROR_PATH_REPOS');
if ((bool) $mirrorPathRepos) {
$currentStrategy = self::STRATEGY_MIRROR;
}
$symlinkOption = $transportOptions['symlink'] ?? null;
if (true === $symlinkOption) {
$currentStrategy = self::STRATEGY_SYMLINK;
$allowedStrategies = [self::STRATEGY_SYMLINK];
} elseif (false === $symlinkOption) {
$currentStrategy = self::STRATEGY_MIRROR;
$allowedStrategies = [self::STRATEGY_MIRROR];
}
// Check we can use junctions safely if we are on Windows
if (Platform::isWindows() && self::STRATEGY_SYMLINK === $currentStrategy && !$this->safeJunctions()) {
if (!in_array(self::STRATEGY_MIRROR, $allowedStrategies, true)) {
throw new \RuntimeException('You are on an old Windows / old PHP combo which does not allow Composer to use junctions/symlinks and this path repository has symlink:true in its options so copying is not allowed');
}
$currentStrategy = self::STRATEGY_MIRROR;
$allowedStrategies = [self::STRATEGY_MIRROR];
}
// Check we can use symlink() otherwise
if (!Platform::isWindows() && self::STRATEGY_SYMLINK === $currentStrategy && !function_exists('symlink')) {
if (!in_array(self::STRATEGY_MIRROR, $allowedStrategies, true)) {
throw new \RuntimeException('Your PHP has the symlink() function disabled which does not allow Composer to use symlinks and this path repository has symlink:true in its options so copying is not allowed');
}
$currentStrategy = self::STRATEGY_MIRROR;
$allowedStrategies = [self::STRATEGY_MIRROR];
}
return [$currentStrategy, $allowedStrategies];
}
/**View on GitHub (pinned to 6ffc117740)
Solutions
- Upgrade PHP to 7.2.16+ or 7.3.3+ so junctions are safe
- Upgrade to Windows 7 (6.1) or newer
- Remove the symlink:true option so Composer can mirror instead of junction
Example fix
// before
"options":{"symlink":true}
// after (allows mirror fallback on old Windows/PHP)
"options":{"symlink":null} Defensive patterns
Strategy: validation
Validate before calling
// On old Windows/PHP, do not force symlink-only
$options = $package->getTransportOptions();
if (PHP_OS_FAMILY === 'Windows' && PHP_VERSION_ID < 70216 && ($options['symlink'] ?? null) === true) {
$options['symlink'] = null; // allow mirror fallback
$package->setTransportOptions($options);
} Prevention
- Upgrade PHP to 7.2.16+/7.3.3+ on Windows for safe junctions
- Do not set symlink:true on old Windows/PHP combos; allow mirroring
- Document platform requirements when distributing composer configs that force symlinks
When it happens
Trigger: Platform::isWindows() is true, STRATEGY_SYMLINK is current, safeJunctions() is false (Windows < 7 or PHP < 7.2.16/7.3.3), and symlink:true in transport options excludes mirroring.
Common situations: Running Composer on an old Windows Server / old PHP where junctions are unsafe, while a path repo forces symlink:true.
Related errors
- Cannot junction to "%s" as it is not a directory.
- Symlink from "%s" to "%s" failed!
- Could not reliably remove junction for package {name}
- Failed to create junction to "%s" at "%s".
- %s is not a junction and thus cannot be removed as one
AI-assisted analysis of composer/composer@6ffc117740 (2026-08-07).
Data as JSON: /api/errors/0d6e688cb304e4d7.
Report an issue: GitHub.