web-font/scripts/dev-all.ts
崮生(子虚) 53d170dc90 feat: 前端迁移至 Vue3 + TS,后端构建迁移至 tsdown
- 前端从 SolidJS 迁移到 Vue3 Composition API(<script setup lang="ts">)
- 后端构建从 tsup 迁移到 tsdown,动态 import 改为静态以支持单文件输出
- FontSelector 添加 defineProps 修复下拉无选项问题
- StatsPanel 添加"服务状态"标题

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
2026-04-30 20:46:30 +08:00

57 lines
1.4 KiB
TypeScript

/**
* 同时启动前端 (vite) 和后端 (tsx backend/app.ts) 的开发服务器
* Ctrl+C 会同时终止两个进程
*/
import { execSync, spawn } from "node:child_process";
import { dirname, join } from "node:path";
import { fileURLToPath } from "node:url";
const __dirname = dirname(fileURLToPath(import.meta.url));
const ROOT_DIR = join(__dirname, "..");
/** 子进程列表,用于退出时统一清理 */
const children: ReturnType<typeof spawn>[] = [];
/** 清理所有子进程 */
function cleanup() {
for (const child of children) {
child.kill("SIGTERM");
}
}
/** 杀掉占用指定端口的进程 */
function killPort(port: number) {
try {
execSync(`lsof -ti:${port} | xargs kill -9 2>/dev/null`, { stdio: "ignore" });
} catch {
/** 端口没有被占用,忽略 */
}
}
process.on("SIGINT", () => {
cleanup();
process.exit(0);
});
process.on("SIGTERM", () => {
cleanup();
process.exit(0);
});
killPort(8087);
console.log("Starting frontend and backend dev servers...\n");
const backend = spawn("pnpx", ["tsx", "watch", "backend/app.ts"], {
cwd: ROOT_DIR,
stdio: "inherit",
shell: true,
env: { ...process.env, ENABLE_TEMP_UPLOAD: "true", ADMIN_API_KEY: "dev-key" },
});
children.push(backend);
const frontend = spawn("pnpm", ["dev:frontend"], {
cwd: ROOT_DIR,
stdio: "inherit",
shell: true,
});
children.push(frontend);