Files
qiming/qiming-file-server/src/utils/build/restartDevUtils.js

130 lines
3.5 KiB
JavaScript
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
import path from "path";
import fs from "fs";
import { log } from "../log/logUtils.js";
import { BusinessError, FileError, ResourceError } from "../error/errorHandler.js";
import {
isProjectStarting,
addStartingProject,
removeStartingProject,
startDev_NonBlocking,
} from "./processManager.js";
import ERROR_CODES from "../error/errorCodes.js";
import { stopDevServer } from "./stopDevUtils.js";
import { removeNodeModules } from "../buildDependency/dependencyManager.js";
import { createPnpmNpmrc } from "../common/npmrcUtils.js";
import {
extractIsolationContext,
resolveProjectPath,
} from "../common/projectPathUtils.js";
// 重启开发服务器
async function restartDevServer(req, projectId) {
log(projectId, "INFO", "Start restarting development server", {
projectId,
requestId: req.requestId,
});
// 检查项目是否存在
const isolationContext = extractIsolationContext(req?.query || {});
const projectPath = resolveProjectPath(projectId, isolationContext);
const jsonFilePath = path.join(projectPath, "package.json");
const exists = fs.existsSync(jsonFilePath);
if (!exists) {
log(projectId, "WARN", "Project missing package.json file", {
projectId,
requestId: req.requestId,
});
throw new ResourceError("Project missing package.json file", {
projectId,
projectPath,
});
}
let jsonContent;
try {
jsonContent = JSON.parse(fs.readFileSync(jsonFilePath, "utf8"));
} catch (error) {
throw new FileError("package.json file format error", {
projectId,
jsonFilePath,
originalError: error.message,
});
}
const jsonScripts = jsonContent.scripts;
const devScript = jsonScripts.dev;
if (!devScript) {
log(projectId, "WARN", "Project missing dev script", {
projectId,
requestId: req.requestId,
});
throw new BusinessError("Project missing dev script", { projectId });
}
// 如果项目正在启动中,等待完成
// if (isProjectStarting(projectId)) {
// throw new BusinessError("Project is starting, please try again later", {
// projectId,
// code: ERROR_CODES.PROJECT_STARTING,
// });
// }
addStartingProject(projectId);
try {
// 1. 停止现有的开发服务器
const pidFromQuery = req.query.pid;
await stopDevServer(req, projectId, pidFromQuery, {
strict: false, // 非严格模式,停止失败不抛出异常
waitForStop: true, // 等待进程完全停止
});
// 2. 删除node_modules
log(projectId, "INFO", "Start deleting node_modules and lock file", {
projectId,
requestId: req.requestId,
});
await removeNodeModules(projectPath, projectId);
// 3. 创建.npmrc文件
log(projectId, "INFO", "Create .npmrc file", {
projectId,
requestId: req.requestId,
});
await createPnpmNpmrc(projectPath, projectId);
// 4. 启动dev服务器依赖安装会在 startDev_NonBlocking 中执行)
log(projectId, "INFO", "Start starting dev server", {
projectId,
requestId: req.requestId,
});
const { pid, port: actualPort } = await startDev_NonBlocking({
req,
projectId,
projectPath,
devScript,
});
log(projectId, "INFO", "Dev server restart completed", {
projectId,
pid,
port: actualPort,
requestId: req.requestId,
});
return {
success: true,
message: "Development server restart successfully",
projectId,
pid,
port: actualPort,
};
} finally {
removeStartingProject(projectId);
}
}
export { restartDevServer };