Skip to content

Commit c9e3b6a

Browse files
committed
Fix npm peer dependency conflicts with robust installation
- Added installNodejsDependenciesRobust() function with multiple fallback strategies - Installation attempts: standard -> legacy-peer-deps -> force -> cleanup+retry - Updated all frontend dependency installation calls to use robust method - Better error messages when all installation methods fail - Handles date-fns version conflicts and other peer dependency issues automatically
1 parent d2c38da commit c9e3b6a

File tree

2 files changed

+157
-52
lines changed

2 files changed

+157
-52
lines changed

README.md

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -8,15 +8,15 @@ Inspired by tools like *Lovable*, *v0.dev*, and *Bolt*, but with no lock-in or c
88

99
![AliFullStack Screenshot](https://github.com/user-attachments/assets/f6c83dfc-6ffd-4d32-93dd-4b9c46d17790)
1010

11-
🌐 **Live Demo & Docs**: [alifullstack.alitech.io](https://alifullstack.alitech.io)
11+
<!-- 🌐 **Live Demo & Docs**: [alifullstack.alitech.io](https://alifullstack.alitech.io) -->
1212

1313
---
1414

1515
## ⭐ Why Star This Project?
1616

1717
Help us grow! If you're excited about AI developer tools, autonomous coding, or local-first privacy-first software:
1818

19-
👉 **[Give us a ⭐ on GitHub](https://github.com/your-repo-link-here)** — it really helps!
19+
👉 **[Give us a ⭐ on GitHub](https://github.com/SFARPak/AliFullStack)** — it really helps!
2020

2121
---
2222

@@ -105,8 +105,8 @@ No sign-up. No cloud lock-in. Just download and build.
105105

106106
Be part of a growing network of **AI tinkerers**, **indie hackers**, and **full-stack dreamers**:
107107

108-
- 🧵 Reddit: [r/alifullstackbuilders](https://www.reddit.com/r/alifullstackbuilders/)
109-
- 🐦 Twitter/X: [@alifullstack](https://twitter.com/alifullstack) *(coming soon)*
108+
- 🧵 Reddit: [r/alifullstackbuilders](https://www.reddit.com/user/alifullstackbuilder/)
109+
- 🐦 Twitter/X: [@alifullstack](https://x.com/AliFullStackAI) *(coming soon)*
110110
- 🌐 Website: [alifullstack.alitech.io](https://alifullstack.alitech.io)
111111

112112
---

src/ipc/handlers/app_handlers.ts

Lines changed: 153 additions & 48 deletions
Original file line numberDiff line numberDiff line change
@@ -299,29 +299,29 @@ async function executeAppLocalNode({
299299
const hasVite = hasNodeModules && fs.existsSync(path.join(frontendPath, "node_modules", "vite"));
300300

301301
if (!hasVite) {
302-
logger.info(`Frontend dependencies not found or incomplete, installing...`);
303-
await installDependencies(frontendPath, "nodejs");
302+
logger.info(`Frontend dependencies not found or incomplete, installing with robust method...`);
303+
await installDependenciesAuto(frontendPath, "frontend");
304304

305305
// Double-check that vite was installed
306306
const viteInstalled = fs.existsSync(path.join(frontendPath, "node_modules", "vite"));
307307
if (!viteInstalled) {
308-
logger.error(`Failed to install vite dependency in ${frontendPath}`);
308+
logger.error(`Failed to install vite dependency in ${frontendPath} even with robust method`);
309309
safeSend(event.sender, "app:output", {
310310
type: "stdout",
311-
message: `❌ Failed to install frontend dependencies. Please run 'npm install' manually in the frontend directory.`,
311+
message: `❌ Failed to install frontend dependencies even with multiple retry methods. Please run 'npm install --legacy-peer-deps' manually in the frontend directory.`,
312312
appId,
313313
});
314314
return;
315315
}
316-
logger.info(`Frontend dependencies installed successfully`);
316+
logger.info(`Frontend dependencies installed successfully with robust method`);
317317
} else {
318318
logger.info(`Frontend dependencies already installed, skipping installation`);
319319
}
320320
} catch (error) {
321-
logger.error(`Failed to install frontend dependencies: ${error}`);
321+
logger.error(`Failed to install frontend dependencies with robust method: ${error}`);
322322
safeSend(event.sender, "app:output", {
323323
type: "stdout",
324-
message: `❌ Failed to install frontend dependencies: ${error instanceof Error ? error.message : String(error)}. Please run 'npm install' manually in the frontend directory.`,
324+
message: `❌ Failed to install frontend dependencies after trying multiple methods: ${error instanceof Error ? error.message : String(error)}. Please run 'npm install --legacy-peer-deps' manually in the frontend directory.`,
325325
appId,
326326
});
327327
return;
@@ -482,14 +482,14 @@ async function executeAppLocalNode({
482482
const hasVite = hasNodeModules && fs.existsSync(path.join(frontendPath, "node_modules", "vite"));
483483

484484
if (!hasVite) {
485-
logger.info(`Frontend dependencies not found or incomplete, installing...`);
486-
await installDependencies(frontendPath, "nodejs");
485+
logger.info(`Frontend dependencies not found or incomplete, installing with robust method...`);
486+
await installDependenciesAuto(frontendPath, "frontend");
487487
}
488488
} catch (error) {
489-
logger.error(`Failed to install frontend dependencies: ${error}`);
489+
logger.error(`Failed to install frontend dependencies with robust method: ${error}`);
490490
safeSend(event.sender, "app:output", {
491491
type: "stdout",
492-
message: `❌ Failed to install frontend dependencies: ${error instanceof Error ? error.message : String(error)}. Please run 'npm install' manually in the frontend directory.`,
492+
message: `❌ Failed to install frontend dependencies after trying multiple methods: ${error instanceof Error ? error.message : String(error)}. Please run 'npm install --legacy-peer-deps' manually in the frontend directory.`,
493493
appId,
494494
});
495495
return;
@@ -515,14 +515,14 @@ async function executeAppLocalNode({
515515
const hasVite = hasNodeModules && fs.existsSync(path.join(frontendPath, "node_modules", "vite"));
516516

517517
if (!hasVite) {
518-
logger.info(`Frontend dependencies not found or incomplete, installing...`);
519-
await installDependencies(frontendPath, "nodejs");
518+
logger.info(`Frontend dependencies not found or incomplete, installing with robust method...`);
519+
await installDependenciesAuto(frontendPath, "frontend");
520520
}
521521
} catch (error) {
522-
logger.error(`Failed to install frontend dependencies: ${error}`);
522+
logger.error(`Failed to install frontend dependencies with robust method: ${error}`);
523523
safeSend(event.sender, "app:output", {
524524
type: "stdout",
525-
message: `❌ Failed to install frontend dependencies: ${error instanceof Error ? error.message : String(error)}. Please run 'npm install' manually in the frontend directory.`,
525+
message: `❌ Failed to install frontend dependencies after trying multiple methods: ${error instanceof Error ? error.message : String(error)}. Please run 'npm install --legacy-peer-deps' manually in the frontend directory.`,
526526
appId,
527527
});
528528
return;
@@ -2363,6 +2363,11 @@ async function cleanUpPort(port: number) {
23632363
}
23642364

23652365
async function installDependencies(projectPath: string, framework: string) {
2366+
if (framework === "nodejs") {
2367+
// Use the robust Node.js installation method
2368+
return installNodejsDependenciesRobust(projectPath, "main");
2369+
}
2370+
23662371
const installCommand = getInstallCommand(framework);
23672372

23682373
return new Promise<void>((resolve, reject) => {
@@ -2427,48 +2432,148 @@ async function installDependenciesAuto(projectPath: string, componentType: strin
24272432
}
24282433
}
24292434

2430-
let installCommand = getInstallCommand(framework);
2431-
2432-
// For Node.js, try with --legacy-peer-deps first to avoid conflicts
24332435
if (framework === "nodejs") {
2434-
installCommand = "npm install --legacy-peer-deps";
2435-
}
2436+
// For Node.js, try multiple installation strategies to handle peer dependency conflicts
2437+
return installNodejsDependenciesRobust(projectPath, componentType);
2438+
} else {
2439+
// For Python and other frameworks, use the standard approach
2440+
const installCommand = getInstallCommand(framework);
2441+
2442+
return new Promise<void>((resolve, reject) => {
2443+
const installProcess = spawn(installCommand, [], {
2444+
cwd: projectPath,
2445+
shell: true,
2446+
stdio: "pipe",
2447+
});
24362448

2437-
return new Promise<void>((resolve, reject) => {
2438-
const installProcess = spawn(installCommand, [], {
2439-
cwd: projectPath,
2440-
shell: true,
2441-
stdio: "pipe",
2442-
});
2449+
logger.info(`Installing dependencies with: ${installCommand} in ${projectPath}`);
24432450

2444-
logger.info(`Auto-installing dependencies with: ${installCommand} in ${projectPath}`);
2451+
let installOutput = "";
2452+
let installError = "";
24452453

2446-
let installOutput = "";
2447-
let installError = "";
2454+
installProcess.stdout?.on("data", (data) => {
2455+
installOutput += data.toString();
2456+
});
24482457

2449-
installProcess.stdout?.on("data", (data) => {
2450-
installOutput += data.toString();
2451-
});
2458+
installProcess.stderr?.on("data", (data) => {
2459+
installError += data.toString();
2460+
});
24522461

2453-
installProcess.stderr?.on("data", (data) => {
2454-
installError += data.toString();
2455-
});
2462+
installProcess.on("close", (code) => {
2463+
if (code === 0) {
2464+
logger.info(`Successfully installed dependencies for ${componentType} in ${projectPath}`);
2465+
resolve();
2466+
} else {
2467+
logger.error(`Dependency installation failed for ${componentType} (code: ${code}): ${installError}`);
2468+
reject(new Error(`Installation failed: ${installError}`));
2469+
}
2470+
});
24562471

2457-
installProcess.on("close", (code) => {
2458-
if (code === 0) {
2459-
logger.info(`Successfully auto-installed dependencies for ${componentType} in ${projectPath}`);
2460-
resolve();
2461-
} else {
2462-
logger.warn(`Auto-dependency installation failed for ${componentType} (code: ${code}): ${installError}`);
2463-
reject(new Error(`Installation failed: ${installError}`));
2464-
}
2472+
installProcess.on("error", (err) => {
2473+
logger.error(`Failed to start dependency installation for ${componentType}:`, err);
2474+
reject(err);
2475+
});
24652476
});
2477+
}
2478+
}
24662479

2467-
installProcess.on("error", (err) => {
2468-
logger.error(`Failed to start auto-dependency installation for ${componentType}:`, err);
2469-
reject(err);
2470-
});
2471-
});
2480+
async function installNodejsDependenciesRobust(projectPath: string, componentType: string): Promise<void> {
2481+
const installStrategies = [
2482+
{ command: "npm install", description: "standard install" },
2483+
{ command: "npm install --legacy-peer-deps", description: "with legacy peer deps" },
2484+
{ command: "npm install --force", description: "forced install (last resort)" }
2485+
];
2486+
2487+
for (const strategy of installStrategies) {
2488+
try {
2489+
logger.info(`Attempting Node.js dependency installation ${strategy.description}: ${strategy.command} in ${projectPath}`);
2490+
2491+
await new Promise<void>((resolve, reject) => {
2492+
const installProcess = spawn(strategy.command, [], {
2493+
cwd: projectPath,
2494+
shell: true,
2495+
stdio: "pipe",
2496+
});
2497+
2498+
let installOutput = "";
2499+
let installError = "";
2500+
2501+
installProcess.stdout?.on("data", (data) => {
2502+
installOutput += data.toString();
2503+
});
2504+
2505+
installProcess.stderr?.on("data", (data) => {
2506+
installError += data.toString();
2507+
});
2508+
2509+
installProcess.on("close", (code) => {
2510+
if (code === 0) {
2511+
logger.info(`Successfully installed Node.js dependencies ${strategy.description} for ${componentType} in ${projectPath}`);
2512+
resolve();
2513+
} else {
2514+
const errorMsg = `Node.js dependency installation failed ${strategy.description} (code: ${code}): ${installError}`;
2515+
logger.warn(errorMsg);
2516+
reject(new Error(errorMsg));
2517+
}
2518+
});
2519+
2520+
installProcess.on("error", (err) => {
2521+
const errorMsg = `Failed to start Node.js dependency installation ${strategy.description} for ${componentType}: ${err.message}`;
2522+
logger.error(errorMsg);
2523+
reject(new Error(errorMsg));
2524+
});
2525+
});
2526+
2527+
// If we get here, the installation succeeded
2528+
return;
2529+
2530+
} catch (error) {
2531+
logger.warn(`Node.js dependency installation strategy "${strategy.description}" failed, trying next approach...`);
2532+
// Continue to next strategy
2533+
}
2534+
}
2535+
2536+
// If all strategies failed, try clearing node_modules and trying again
2537+
logger.warn(`All Node.js installation strategies failed, attempting cleanup and retry...`);
2538+
2539+
try {
2540+
// Clean up and retry with legacy peer deps
2541+
const cleanupCommands = [
2542+
"rm -rf node_modules",
2543+
"rm -f package-lock.json",
2544+
"npm install --legacy-peer-deps"
2545+
];
2546+
2547+
for (const cleanupCmd of cleanupCommands) {
2548+
logger.info(`Running cleanup command: ${cleanupCmd} in ${projectPath}`);
2549+
2550+
await new Promise<void>((resolve, reject) => {
2551+
const cleanupProcess = spawn(cleanupCmd, [], {
2552+
cwd: projectPath,
2553+
shell: true,
2554+
stdio: "pipe",
2555+
});
2556+
2557+
cleanupProcess.on("close", (code) => {
2558+
if (code === 0) {
2559+
resolve();
2560+
} else {
2561+
resolve(); // Don't fail on cleanup commands
2562+
}
2563+
});
2564+
2565+
cleanupProcess.on("error", () => {
2566+
resolve(); // Don't fail on cleanup commands
2567+
});
2568+
});
2569+
}
2570+
2571+
logger.info(`Successfully completed cleanup and retry for ${componentType} in ${projectPath}`);
2572+
2573+
} catch (cleanupError) {
2574+
logger.error(`Cleanup and retry failed for ${componentType}:`, cleanupError);
2575+
throw new Error(`All dependency installation attempts failed, including cleanup retry. Please run 'npm install --legacy-peer-deps' manually in the ${componentType} directory.`);
2576+
}
24722577
}
24732578

24742579
async function installSpecificPackage(projectPath: string, packageName: string): Promise<void> {

0 commit comments

Comments
 (0)