@dimples/apa 0.1.0-dev.1 → 0.1.0-dev.11

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/cli.mjs CHANGED
@@ -1,16 +1,17 @@
1
+ #!/usr/bin/env node
1
2
  import { spawn } from "node:child_process";
2
3
  import { Command } from "commander";
3
4
  import { readFile } from "node:fs/promises";
5
+ import { existsSync } from "node:fs";
4
6
  import { fileURLToPath } from "node:url";
5
7
  import { serve } from "@hono/node-server";
6
8
  import { serveStatic } from "@hono/node-server/serve-static";
7
9
  import { Hono } from "hono";
8
- import { existsSync } from "node:fs";
9
- //#region ../../packages/shared/src/mock.ts
10
+ //#region ../../packages/shared/dist/index.mjs
10
11
  const mockProjects = [
11
12
  {
12
13
  id: "p-001",
13
- cover: "/covers/p-001.jpg",
14
+ cover: "covers/p-001.jpg",
14
15
  name: "长安十二时辰 · 重制",
15
16
  logline: "上元节前夕,死囚张小敬受命拯救长安城,十二个时辰内揪出隐藏的阴谋。",
16
17
  genre: "古装悬疑",
@@ -25,7 +26,7 @@ const mockProjects = [
25
26
  },
26
27
  {
27
28
  id: "p-002",
28
- cover: "/covers/p-002.jpg",
29
+ cover: "covers/p-002.jpg",
29
30
  name: "星际摆渡人",
30
31
  logline: "末日地球最后一位星际摆渡人,驾驶旧飞船护送三千沉睡者前往新家园。",
31
32
  genre: "科幻",
@@ -46,7 +47,7 @@ const mockProjects = [
46
47
  },
47
48
  {
48
49
  id: "p-003",
49
- cover: "/covers/p-003.jpg",
50
+ cover: "covers/p-003.jpg",
50
51
  name: "弄堂风云",
51
52
  logline: "九十年代上海弄堂里,两家理发店三代人的恩怨与和解。",
52
53
  genre: "年代剧",
@@ -67,7 +68,7 @@ const mockProjects = [
67
68
  },
68
69
  {
69
70
  id: "p-005",
70
- cover: "/covers/p-005.jpg",
71
+ cover: "covers/p-005.jpg",
71
72
  name: "无声证词",
72
73
  logline: "一位失聪法医通过微表情与物证破译凶案真相,却卷入旧日悬案。",
73
74
  genre: "刑侦",
@@ -84,7 +85,7 @@ const mockProjects = [
84
85
  const mockActors = [
85
86
  {
86
87
  id: "a-001",
87
- avatar: "/avatars/a-001.jpg",
88
+ avatar: "avatars/a-001.jpg",
88
89
  name: "沈青",
89
90
  persona: "眉眼冷峻的刑侦专家,惯用低沉嗓音压住全场;长于审讯对手戏",
90
91
  tags: ["悬疑", "正剧"],
@@ -94,7 +95,7 @@ const mockActors = [
94
95
  },
95
96
  {
96
97
  id: "a-002",
97
- avatar: "/avatars/a-002.jpg",
98
+ avatar: "avatars/a-002.jpg",
98
99
  name: "白鹿",
99
100
  persona: "清冷少女感,台词干净利落;在失重与奔跑戏里肢体控制力惊人",
100
101
  tags: ["科幻", "青春"],
@@ -122,7 +123,7 @@ const mockActors = [
122
123
  },
123
124
  {
124
125
  id: "a-005",
125
- avatar: "/avatars/a-005.jpg",
126
+ avatar: "avatars/a-005.jpg",
126
127
  name: "段飞白",
127
128
  persona: "满脸风霜的硬汉,不用台词也能演完整场内心戏",
128
129
  tags: ["刑侦", "硬汉"],
@@ -212,8 +213,6 @@ const mockCostumes = [
212
213
  createdAt: "2026-10-02T09:00:00.000Z"
213
214
  }
214
215
  ];
215
- //#endregion
216
- //#region ../../packages/shared/src/index.ts
217
216
  /** 应用版本(package.json 同步) */
218
217
  const APP_VERSION = "0.1.0";
219
218
  //#endregion
@@ -237,6 +236,75 @@ function startServer(opts) {
237
236
  app.get("/api/actors", (c) => c.json(actors));
238
237
  app.get("/api/scenes", (c) => c.json(scenes));
239
238
  app.get("/api/costumes", (c) => c.json(costumes));
239
+ const seq = (prefix, existing) => {
240
+ const max = existing.reduce((acc, x) => {
241
+ const n = Number.parseInt(x.id.replace(prefix, ""), 10);
242
+ return Number.isNaN(n) ? acc : Math.max(acc, n);
243
+ }, 0);
244
+ return `${prefix}${String(max + 1).padStart(3, "0")}`;
245
+ };
246
+ app.post("/api/projects", async (c) => {
247
+ const b = await c.req.json();
248
+ if (!b.name?.trim()) return c.json({ error: "name 必填" }, 400);
249
+ const project = {
250
+ id: seq("p-", projects),
251
+ cover: b.cover || void 0,
252
+ name: b.name.trim(),
253
+ logline: b.logline?.trim() || "",
254
+ genre: b.genre?.trim() || "未分类",
255
+ status: b.status ?? "planning",
256
+ progress: 0,
257
+ members: b.members ?? [],
258
+ updatedAt: (/* @__PURE__ */ new Date()).toISOString()
259
+ };
260
+ projects.push(project);
261
+ return c.json(project, 201);
262
+ });
263
+ app.post("/api/actors", async (c) => {
264
+ const b = await c.req.json();
265
+ if (!b.name?.trim()) return c.json({ error: "name 必填" }, 400);
266
+ const actor = {
267
+ id: seq("a-", actors),
268
+ avatar: b.avatar || void 0,
269
+ name: b.name.trim(),
270
+ persona: b.persona?.trim() || "",
271
+ accent: b.accent || "indigo",
272
+ tags: b.tags ?? [],
273
+ projectCount: 0,
274
+ createdAt: (/* @__PURE__ */ new Date()).toISOString()
275
+ };
276
+ actors.push(actor);
277
+ return c.json(actor, 201);
278
+ });
279
+ app.post("/api/scenes", async (c) => {
280
+ const b = await c.req.json();
281
+ if (!b.name?.trim()) return c.json({ error: "name 必填" }, 400);
282
+ const scene = {
283
+ id: seq("s-", scenes),
284
+ name: b.name.trim(),
285
+ description: b.description?.trim() || "",
286
+ timeOfDay: b.timeOfDay?.trim() || "日",
287
+ tags: b.tags ?? [],
288
+ projectName: b.projectName?.trim() || "未关联",
289
+ createdAt: (/* @__PURE__ */ new Date()).toISOString()
290
+ };
291
+ scenes.push(scene);
292
+ return c.json(scene, 201);
293
+ });
294
+ app.post("/api/costumes", async (c) => {
295
+ const b = await c.req.json();
296
+ if (!b.name?.trim()) return c.json({ error: "name 必填" }, 400);
297
+ const costume = {
298
+ id: seq("c-", costumes),
299
+ name: b.name.trim(),
300
+ description: b.description?.trim() || "",
301
+ era: b.era?.trim() || "当代",
302
+ tags: b.tags ?? [],
303
+ createdAt: (/* @__PURE__ */ new Date()).toISOString()
304
+ };
305
+ costumes.push(costume);
306
+ return c.json(costume, 201);
307
+ });
240
308
  app.use("*", async (c, next) => {
241
309
  await next();
242
310
  if (!c.req.path.startsWith("/api")) c.header("Cache-Control", "public, max-age=604800");
@@ -260,7 +328,7 @@ function startServer(opts) {
260
328
  //#region src/cli.ts
261
329
  const program = new Command();
262
330
  program.name("apa").description("APA — AI Pipeline for Auteur").version(APP_VERSION);
263
- program.command("serve").description("启动 APA Web 服务,通过浏览器访问").option("-p, --port <port>", "监听端口", "4310").option("-H, --host <host>", "监听地址", "127.0.0.1").option("--open", "启动后自动打开浏览器", false).action(async (opts) => {
331
+ function startServe(opts) {
264
332
  const port = Number.parseInt(opts.port, 10);
265
333
  const url = `http://${opts.host}:${port}`;
266
334
  startServer({
@@ -275,7 +343,13 @@ program.command("serve").description("启动 APA Web 服务,通过浏览器访
275
343
  stdio: "ignore"
276
344
  }).unref();
277
345
  }
278
- });
346
+ }
347
+ program.command("serve").description("启动 APA Web 服务,通过浏览器访问").option("-p, --port <port>", "监听端口", "4310").option("-H, --host <host>", "监听地址", "127.0.0.1").option("--open", "启动后自动打开浏览器", false).action(startServe);
348
+ program.action(() => startServe({
349
+ port: "4310",
350
+ host: "127.0.0.1",
351
+ open: false
352
+ }));
279
353
  program.parse();
280
354
  //#endregion
281
355
  export {};