Skip to content

Commit e57a88d

Browse files
committed
[FIX] Installation Process.
1 parent 13c2779 commit e57a88d

File tree

2 files changed

+43
-2763
lines changed

2 files changed

+43
-2763
lines changed

src/Commands/InstallCommand.php

Lines changed: 43 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1298,10 +1298,19 @@ protected function setupComposer(string $projectPath): void
12981298
$composerCommand = $this->resolveComposerCommand($composerWorkDir);
12991299

13001300
try {
1301+
$vendorDir = $composerWorkDir . '/vendor';
1302+
if (is_dir($vendorDir) && !$this->isComposerVendorHealthy($composerWorkDir)) {
1303+
$this->tui->addLog('Detected incomplete vendor directory. Removing and reinstalling...', 'warning');
1304+
$this->removeDirectory($vendorDir);
1305+
}
1306+
13011307
$installArgs = ['install', '--no-dev', '--prefer-dist', '--no-scripts', '--no-cache'];
13021308
$process = $this->runComposer($composerCommand, $installArgs, $composerWorkDir);
13031309
if ($process->isSuccessful() && !$this->isComposerVendorHealthy($composerWorkDir)) {
1304-
$this->tui->addLog('Composer install finished but vendor is incomplete. Retrying with --prefer-source (this can happen due to GitHub rate limits)...', 'warning');
1310+
$this->tui->addLog('Composer install finished but vendor is incomplete. Retrying with clean vendor and --prefer-source (this can happen due to GitHub rate limits)...', 'warning');
1311+
if (is_dir($vendorDir)) {
1312+
$this->removeDirectory($vendorDir);
1313+
}
13051314
$process = $this->runComposer($composerCommand, ['install', '--no-dev', '--prefer-source', '--no-scripts', '--no-cache'], $composerWorkDir);
13061315
}
13071316
if ($process->isSuccessful() && $this->isComposerVendorHealthy($composerWorkDir)) {
@@ -1399,25 +1408,52 @@ protected function setupComposer(string $projectPath): void
13991408
protected function isComposerVendorHealthy(string $composerWorkDir): bool
14001409
{
14011410
$autoload = $composerWorkDir . '/vendor/autoload.php';
1402-
if (!is_file($autoload)) {
1411+
if (!is_file($autoload) || !$this->isNonEmptyFile($autoload)) {
14031412
return false;
14041413
}
14051414

14061415
// Migrations/seeders use Artisan (Illuminate Console) which requires Symfony Console.
14071416
$requiredFiles = [
1408-
$composerWorkDir . '/vendor/symfony/console/Application.php',
1409-
$composerWorkDir . '/vendor/symfony/http-kernel/Kernel.php',
1410-
$composerWorkDir . '/vendor/symfony/routing/RouteCollection.php',
1417+
[$composerWorkDir . '/vendor/symfony/console/Application.php', 'class Application'],
1418+
[$composerWorkDir . '/vendor/symfony/http-kernel/Kernel.php', 'class Kernel'],
1419+
[$composerWorkDir . '/vendor/symfony/routing/RouteCollection.php', 'class RouteCollection'],
14111420
];
1412-
foreach ($requiredFiles as $file) {
1413-
if (!is_file($file)) {
1421+
foreach ($requiredFiles as $it) {
1422+
[$file, $needle] = $it;
1423+
if (!$this->fileContains($file, $needle)) {
14141424
return false;
14151425
}
14161426
}
14171427

14181428
return true;
14191429
}
14201430

1431+
protected function isNonEmptyFile(string $path): bool
1432+
{
1433+
$size = @filesize($path);
1434+
return is_int($size) && $size > 0;
1435+
}
1436+
1437+
protected function fileContains(string $path, string $needle): bool
1438+
{
1439+
if (!is_file($path) || !$this->isNonEmptyFile($path)) {
1440+
return false;
1441+
}
1442+
$fh = @fopen($path, 'rb');
1443+
if (!is_resource($fh)) {
1444+
return false;
1445+
}
1446+
try {
1447+
$buf = @fread($fh, 8192);
1448+
} finally {
1449+
@fclose($fh);
1450+
}
1451+
if (!is_string($buf) || $buf === '') {
1452+
return false;
1453+
}
1454+
return strpos($buf, $needle) !== false;
1455+
}
1456+
14211457
protected function ensureArtisanDependencies(string $projectPath): void
14221458
{
14231459
$composerWorkDir = is_file($projectPath . '/core/composer.json') ? ($projectPath . '/core') : $projectPath;

0 commit comments

Comments
 (0)