@faapi/faapi 6.22.0 → 6.24.0
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/index.js +245 -101
- package/dist/cli/index.js.map +1 -1
- package/dist/index.d.ts +42 -51
- package/dist/index.js +166 -137
- package/dist/index.js.map +1 -1
- package/dist/{routeTypes-CXWkRx4W.d.ts → routeTypes-D1swYDVC.d.ts} +49 -19
- package/dist/testing.d.ts +3 -1
- package/dist/testing.js +80 -47
- package/dist/testing.js.map +1 -1
- package/package.json +1 -1
package/dist/cli/index.js
CHANGED
|
@@ -3082,8 +3082,6 @@ var init_generateToolArtifacts = __esm({
|
|
|
3082
3082
|
|
|
3083
3083
|
// src/agents/scanAgents.ts
|
|
3084
3084
|
import fg3 from "fast-glob";
|
|
3085
|
-
import path15 from "path";
|
|
3086
|
-
import fs12 from "fs";
|
|
3087
3085
|
function extractAgentNameFromPath(filePath) {
|
|
3088
3086
|
const normalized = filePath.replace(/\\/g, "/");
|
|
3089
3087
|
const match = normalized.match(/(?:^|\/)agents\/(.+)\/handler\.ts$/);
|
|
@@ -3094,11 +3092,6 @@ function extractAgentNameFromPath(filePath) {
|
|
|
3094
3092
|
}
|
|
3095
3093
|
return match[1].replace(/\//g, ".");
|
|
3096
3094
|
}
|
|
3097
|
-
function detectAgentExports(source) {
|
|
3098
|
-
return {
|
|
3099
|
-
hasRun: RUN_EXPORT_RE.test(source)
|
|
3100
|
-
};
|
|
3101
|
-
}
|
|
3102
3095
|
async function scanAgents(rootDir, patterns) {
|
|
3103
3096
|
const files = await fg3(patterns, {
|
|
3104
3097
|
cwd: rootDir,
|
|
@@ -3113,9 +3106,6 @@ async function scanAgents(rootDir, patterns) {
|
|
|
3113
3106
|
if (fileName !== "handler.ts" && fileName !== "handler.js") {
|
|
3114
3107
|
continue;
|
|
3115
3108
|
}
|
|
3116
|
-
const absPath = path15.resolve(rootDir, normalizedFile);
|
|
3117
|
-
const source = await fs12.promises.readFile(absPath, "utf8").catch(() => "");
|
|
3118
|
-
const { hasRun } = detectAgentExports(source);
|
|
3119
3109
|
const name = extractAgentNameFromPath(normalizedFile);
|
|
3120
3110
|
const prevFile = seen.get(name);
|
|
3121
3111
|
if (prevFile) {
|
|
@@ -3126,18 +3116,16 @@ async function scanAgents(rootDir, patterns) {
|
|
|
3126
3116
|
seen.set(name, normalizedFile);
|
|
3127
3117
|
agents.push({
|
|
3128
3118
|
name,
|
|
3129
|
-
filePath: normalizedFile
|
|
3130
|
-
hasRun
|
|
3119
|
+
filePath: normalizedFile
|
|
3131
3120
|
});
|
|
3132
3121
|
}
|
|
3133
3122
|
return agents;
|
|
3134
3123
|
}
|
|
3135
|
-
var DEFAULT_AGENT_PATTERNS
|
|
3124
|
+
var DEFAULT_AGENT_PATTERNS;
|
|
3136
3125
|
var init_scanAgents = __esm({
|
|
3137
3126
|
"src/agents/scanAgents.ts"() {
|
|
3138
3127
|
"use strict";
|
|
3139
3128
|
DEFAULT_AGENT_PATTERNS = ["src/agents/**/handler.ts"];
|
|
3140
|
-
RUN_EXPORT_RE = /export\s+(?:async\s+)?(?:function\s+|const\s+)run\b/;
|
|
3141
3129
|
}
|
|
3142
3130
|
});
|
|
3143
3131
|
|
|
@@ -3146,12 +3134,21 @@ import ts11 from "typescript";
|
|
|
3146
3134
|
function extractAgentMetadata(program, filePath, pathMeta) {
|
|
3147
3135
|
const sourceFile = program.getSourceFile(filePath);
|
|
3148
3136
|
if (!sourceFile) return null;
|
|
3137
|
+
const runOwner = findRunExportOwner(sourceFile);
|
|
3138
|
+
if (runOwner) {
|
|
3139
|
+
throw SchemaExtractionError.at(
|
|
3140
|
+
runOwner,
|
|
3141
|
+
"run",
|
|
3142
|
+
"agent \u81EA\u5B9A\u4E49 run \u5DF2\u79FB\u9664\u2014\u2014agent \u7EDF\u4E00\u4E3A\u58F0\u660E\u5F0F\u6267\u884C\uFF08config + \u9ED8\u8BA4 reactLoop\uFF09\u3002\u7F16\u6392\u573A\u666F\u8BF7\u6CE8\u518C tool\uFF08src/tools/ \u4E0B\u5BFC\u51FA\u51FD\u6570\uFF0C\u6709 schema/trace/\u9274\u6743\u94A9\u5B50\uFF09\uFF0C\u591A agent \u534F\u4F5C\u7528 config.agents \u58F0\u660E sub-agent",
|
|
3143
|
+
sourceFile
|
|
3144
|
+
);
|
|
3145
|
+
}
|
|
3149
3146
|
const configFound = findConfigExport(sourceFile);
|
|
3150
3147
|
if (!configFound) {
|
|
3151
3148
|
throw SchemaExtractionError.at(
|
|
3152
3149
|
sourceFile,
|
|
3153
3150
|
"config.systemPrompt",
|
|
3154
|
-
"agent \u5FC5\u586B\u2014\u2014\u8BF7\u5728 config \u5757\u58F0\u660E\
|
|
3151
|
+
"agent \u5FC5\u586B\u2014\u2014\u8BF7\u5728 config \u5757\u58F0\u660E systemPrompt\uFF08\u5B57\u7B26\u4E32\u5B57\u9762\u91CF\u3001\u65E0\u63D2\u503C\u6A21\u677F\u5B57\u7B26\u4E32\u6216\u5176 + \u62FC\u63A5\uFF09\u6216 systemPromptFile\uFF08\u76F8\u5BF9 resources \u76EE\u5F55\u7684\u8DEF\u5F84\u5B57\u9762\u91CF\uFF09\u4E8C\u9009\u4E00",
|
|
3155
3152
|
sourceFile
|
|
3156
3153
|
);
|
|
3157
3154
|
}
|
|
@@ -3167,16 +3164,13 @@ function extractAgentMetadata(program, filePath, pathMeta) {
|
|
|
3167
3164
|
const jsDoc = getJSDocFromNode(configFound.jsDocOwner);
|
|
3168
3165
|
const description = extractDescription(jsDoc);
|
|
3169
3166
|
const agentNameOverride = extractJSDocTagValue(jsDoc, "agent");
|
|
3170
|
-
const { systemPrompt, tools, agents, model, maxTurns, inputDescription } = extractConfigFields(
|
|
3171
|
-
objectLiteral,
|
|
3172
|
-
sourceFile
|
|
3173
|
-
);
|
|
3167
|
+
const { systemPrompt, systemPromptFile, tools, agents, model, maxTurns, inputDescription } = extractConfigFields(objectLiteral, sourceFile);
|
|
3174
3168
|
return {
|
|
3175
3169
|
name: agentNameOverride ?? pathMeta.name,
|
|
3176
3170
|
description,
|
|
3177
3171
|
filePath: pathMeta.filePath,
|
|
3178
|
-
hasRun: pathMeta.hasRun,
|
|
3179
3172
|
systemPrompt,
|
|
3173
|
+
systemPromptFile,
|
|
3180
3174
|
tools,
|
|
3181
3175
|
agents,
|
|
3182
3176
|
model,
|
|
@@ -3184,6 +3178,25 @@ function extractAgentMetadata(program, filePath, pathMeta) {
|
|
|
3184
3178
|
inputDescription
|
|
3185
3179
|
};
|
|
3186
3180
|
}
|
|
3181
|
+
function findRunExportOwner(sourceFile) {
|
|
3182
|
+
let result = null;
|
|
3183
|
+
ts11.forEachChild(sourceFile, (node) => {
|
|
3184
|
+
if (result) return;
|
|
3185
|
+
if (ts11.isFunctionDeclaration(node) && hasExportModifier(node) && node.name?.text === "run") {
|
|
3186
|
+
result = node;
|
|
3187
|
+
return;
|
|
3188
|
+
}
|
|
3189
|
+
if (ts11.isVariableStatement(node) && hasExportModifier(node)) {
|
|
3190
|
+
for (const decl of node.declarationList.declarations) {
|
|
3191
|
+
if (ts11.isIdentifier(decl.name) && decl.name.text === "run") {
|
|
3192
|
+
result = node;
|
|
3193
|
+
return;
|
|
3194
|
+
}
|
|
3195
|
+
}
|
|
3196
|
+
}
|
|
3197
|
+
});
|
|
3198
|
+
return result;
|
|
3199
|
+
}
|
|
3187
3200
|
function findConfigExport(sourceFile) {
|
|
3188
3201
|
let result = null;
|
|
3189
3202
|
ts11.forEachChild(sourceFile, (node) => {
|
|
@@ -3226,6 +3239,7 @@ function getReturnObjectLiteral(fn) {
|
|
|
3226
3239
|
}
|
|
3227
3240
|
function extractConfigFields(objLit, sourceFile) {
|
|
3228
3241
|
let systemPrompt;
|
|
3242
|
+
let systemPromptFile;
|
|
3229
3243
|
let tools;
|
|
3230
3244
|
let agents;
|
|
3231
3245
|
let model;
|
|
@@ -3249,6 +3263,9 @@ function extractConfigFields(objLit, sourceFile) {
|
|
|
3249
3263
|
case "systemPrompt":
|
|
3250
3264
|
systemPrompt = requireStringValue(prop, "systemPrompt", sourceFile);
|
|
3251
3265
|
break;
|
|
3266
|
+
case "systemPromptFile":
|
|
3267
|
+
systemPromptFile = requireStringValue(prop, "systemPromptFile", sourceFile);
|
|
3268
|
+
break;
|
|
3252
3269
|
case "tools":
|
|
3253
3270
|
tools = requireStringArrayValue(prop, "tools", sourceFile);
|
|
3254
3271
|
break;
|
|
@@ -3268,20 +3285,28 @@ function extractConfigFields(objLit, sourceFile) {
|
|
|
3268
3285
|
throw SchemaExtractionError.at(
|
|
3269
3286
|
prop,
|
|
3270
3287
|
`config.${propName}`,
|
|
3271
|
-
"\u672A\u77E5 config \u5B57\u6BB5\u2014\u2014\u4EC5\u652F\u6301 systemPrompt / tools / agents / model / maxTurns / inputDescription",
|
|
3288
|
+
"\u672A\u77E5 config \u5B57\u6BB5\u2014\u2014\u4EC5\u652F\u6301 systemPrompt / systemPromptFile / tools / agents / model / maxTurns / inputDescription",
|
|
3272
3289
|
sourceFile
|
|
3273
3290
|
);
|
|
3274
3291
|
}
|
|
3275
3292
|
}
|
|
3276
|
-
if (systemPrompt
|
|
3293
|
+
if (systemPrompt !== void 0 && systemPromptFile !== void 0) {
|
|
3294
|
+
throw SchemaExtractionError.at(
|
|
3295
|
+
objLit,
|
|
3296
|
+
"config.systemPrompt",
|
|
3297
|
+
"systemPrompt \u4E0E systemPromptFile \u4E92\u65A5\u2014\u2014\u5185\u8054\u7CFB\u7EDF\u63D0\u793A\u8BCD\u4E0E resources \u6587\u4EF6\u4E8C\u9009\u4E00",
|
|
3298
|
+
sourceFile
|
|
3299
|
+
);
|
|
3300
|
+
}
|
|
3301
|
+
if (systemPrompt === void 0 && systemPromptFile === void 0) {
|
|
3277
3302
|
throw SchemaExtractionError.at(
|
|
3278
3303
|
objLit,
|
|
3279
3304
|
"config.systemPrompt",
|
|
3280
|
-
"agent \u5FC5\u586B\u2014\u2014\u8BF7\u5728 config \u5757\u58F0\u660E\
|
|
3305
|
+
"agent \u5FC5\u586B\u2014\u2014\u8BF7\u5728 config \u5757\u58F0\u660E systemPrompt\uFF08\u5B57\u7B26\u4E32\u5B57\u9762\u91CF\u3001\u65E0\u63D2\u503C\u6A21\u677F\u5B57\u7B26\u4E32\u6216\u5176 + \u62FC\u63A5\uFF09\u6216 systemPromptFile\uFF08\u76F8\u5BF9 resources \u76EE\u5F55\u7684\u8DEF\u5F84\u5B57\u9762\u91CF\uFF09\u4E8C\u9009\u4E00",
|
|
3281
3306
|
sourceFile
|
|
3282
3307
|
);
|
|
3283
3308
|
}
|
|
3284
|
-
return { systemPrompt, tools, agents, model, maxTurns, inputDescription };
|
|
3309
|
+
return { systemPrompt, systemPromptFile, tools, agents, model, maxTurns, inputDescription };
|
|
3285
3310
|
}
|
|
3286
3311
|
function getPropertyName(name) {
|
|
3287
3312
|
if (ts11.isIdentifier(name)) return name.text;
|
|
@@ -3364,13 +3389,13 @@ var init_extractAgentMetadata = __esm({
|
|
|
3364
3389
|
});
|
|
3365
3390
|
|
|
3366
3391
|
// src/cli/generateAgentArtifacts.ts
|
|
3367
|
-
import
|
|
3392
|
+
import path15 from "path";
|
|
3368
3393
|
function serializeAgents(agents, dist = "dist") {
|
|
3369
3394
|
return agents.map((a) => ({
|
|
3370
3395
|
name: a.name,
|
|
3371
3396
|
description: a.description,
|
|
3372
|
-
hasRun: a.hasRun,
|
|
3373
3397
|
systemPrompt: a.systemPrompt,
|
|
3398
|
+
systemPromptFile: a.systemPromptFile,
|
|
3374
3399
|
tools: a.tools,
|
|
3375
3400
|
agents: a.agents,
|
|
3376
3401
|
model: a.model,
|
|
@@ -3390,8 +3415,8 @@ function hydrateAgents(manifest) {
|
|
|
3390
3415
|
name: a.name,
|
|
3391
3416
|
description: a.description ?? void 0,
|
|
3392
3417
|
filePath: a.filePath,
|
|
3393
|
-
hasRun: a.hasRun,
|
|
3394
3418
|
systemPrompt: a.systemPrompt ?? void 0,
|
|
3419
|
+
systemPromptFile: a.systemPromptFile ?? void 0,
|
|
3395
3420
|
tools: a.tools ?? void 0,
|
|
3396
3421
|
agents: a.agents ?? void 0,
|
|
3397
3422
|
model: a.model ?? void 0,
|
|
@@ -3423,14 +3448,13 @@ function validateAgentList(metadata) {
|
|
|
3423
3448
|
}
|
|
3424
3449
|
async function generateAgentArtifacts(agents, rootDir, dist) {
|
|
3425
3450
|
const metadata = [];
|
|
3426
|
-
const programByFile = createPrograms(agents.map((m) =>
|
|
3451
|
+
const programByFile = createPrograms(agents.map((m) => path15.resolve(rootDir, m.filePath)));
|
|
3427
3452
|
for (const manifest of agents) {
|
|
3428
|
-
const absPath =
|
|
3453
|
+
const absPath = path15.resolve(rootDir, manifest.filePath);
|
|
3429
3454
|
const program = programByFile.get(absPath);
|
|
3430
3455
|
const result = extractAgentMetadata(program, absPath, {
|
|
3431
3456
|
name: manifest.name,
|
|
3432
|
-
filePath: manifest.filePath
|
|
3433
|
-
hasRun: manifest.hasRun
|
|
3457
|
+
filePath: manifest.filePath
|
|
3434
3458
|
});
|
|
3435
3459
|
if (!result) {
|
|
3436
3460
|
throw new Error(
|
|
@@ -3441,7 +3465,7 @@ async function generateAgentArtifacts(agents, rootDir, dist) {
|
|
|
3441
3465
|
}
|
|
3442
3466
|
validateAgentList(metadata);
|
|
3443
3467
|
const serialized = serializeAgents(metadata, dist);
|
|
3444
|
-
const agentsPath =
|
|
3468
|
+
const agentsPath = path15.resolve(rootDir, dist, AGENTS_FILE);
|
|
3445
3469
|
await writeAgentsModule(serialized, agentsPath);
|
|
3446
3470
|
return metadata;
|
|
3447
3471
|
}
|
|
@@ -3459,8 +3483,8 @@ var init_generateAgentArtifacts = __esm({
|
|
|
3459
3483
|
|
|
3460
3484
|
// src/task/scanTasks.ts
|
|
3461
3485
|
import fg4 from "fast-glob";
|
|
3462
|
-
import
|
|
3463
|
-
import
|
|
3486
|
+
import path16 from "path";
|
|
3487
|
+
import fs12 from "fs";
|
|
3464
3488
|
function parseNumericLiteral(raw) {
|
|
3465
3489
|
return Number(raw.replace(/_/g, ""));
|
|
3466
3490
|
}
|
|
@@ -3482,12 +3506,12 @@ async function scanTasks(rootDir, patterns) {
|
|
|
3482
3506
|
const seen = /* @__PURE__ */ new Map();
|
|
3483
3507
|
for (const file of files) {
|
|
3484
3508
|
const normalizedFile = file.replace(/\\/g, "/");
|
|
3485
|
-
const fileName =
|
|
3509
|
+
const fileName = path16.posix.basename(normalizedFile);
|
|
3486
3510
|
if (fileName !== TASK_FILENAME) {
|
|
3487
3511
|
continue;
|
|
3488
3512
|
}
|
|
3489
|
-
const absPath =
|
|
3490
|
-
const source = await
|
|
3513
|
+
const absPath = path16.resolve(rootDir, normalizedFile);
|
|
3514
|
+
const source = await fs12.promises.readFile(absPath, "utf8").catch(() => "");
|
|
3491
3515
|
const name = filePathToTaskName(normalizedFile);
|
|
3492
3516
|
const prevFile = seen.get(name);
|
|
3493
3517
|
if (prevFile) {
|
|
@@ -3536,7 +3560,7 @@ var init_scanTasks = __esm({
|
|
|
3536
3560
|
});
|
|
3537
3561
|
|
|
3538
3562
|
// src/cli/generateTaskArtifacts.ts
|
|
3539
|
-
import
|
|
3563
|
+
import path17 from "path";
|
|
3540
3564
|
function serializeTasks(tasks, dist = "dist") {
|
|
3541
3565
|
return tasks.map((t) => ({
|
|
3542
3566
|
name: t.name,
|
|
@@ -3569,7 +3593,7 @@ function collectTaskSchemaSources(tasks, rootDir) {
|
|
|
3569
3593
|
const tasksByFile = /* @__PURE__ */ new Map();
|
|
3570
3594
|
for (const task of tasks) {
|
|
3571
3595
|
if (!task.inputTypeName) continue;
|
|
3572
|
-
const absPath =
|
|
3596
|
+
const absPath = path17.resolve(rootDir, task.filePath);
|
|
3573
3597
|
let list = tasksByFile.get(absPath);
|
|
3574
3598
|
if (!list) {
|
|
3575
3599
|
list = [];
|
|
@@ -3626,9 +3650,9 @@ function generateTaskSchemaFileSource(sources, resolveType, helpersImportPath) {
|
|
|
3626
3650
|
async function generateTaskArtifacts(manifests, rootDir, dist) {
|
|
3627
3651
|
const metadata = [];
|
|
3628
3652
|
if (manifests.length > 0) {
|
|
3629
|
-
const programByFile = createPrograms(manifests.map((m) =>
|
|
3653
|
+
const programByFile = createPrograms(manifests.map((m) => path17.resolve(rootDir, m.filePath)));
|
|
3630
3654
|
for (const manifest of manifests) {
|
|
3631
|
-
const absPath =
|
|
3655
|
+
const absPath = path17.resolve(rootDir, manifest.filePath);
|
|
3632
3656
|
const result = extractToolMetadata(programByFile.get(absPath), absPath, "run", {
|
|
3633
3657
|
name: manifest.name,
|
|
3634
3658
|
filePath: manifest.filePath
|
|
@@ -3639,7 +3663,7 @@ async function generateTaskArtifacts(manifests, rootDir, dist) {
|
|
|
3639
3663
|
}
|
|
3640
3664
|
}
|
|
3641
3665
|
const serialized = serializeTasks(manifests, dist);
|
|
3642
|
-
const tasksPath =
|
|
3666
|
+
const tasksPath = path17.resolve(rootDir, dist, TASKS_FILE);
|
|
3643
3667
|
await writeTasksModule(serialized, tasksPath);
|
|
3644
3668
|
if (metadata.length === 0) {
|
|
3645
3669
|
return hydrateTasks(serialized);
|
|
@@ -3672,8 +3696,8 @@ var init_generateTaskArtifacts = __esm({
|
|
|
3672
3696
|
});
|
|
3673
3697
|
|
|
3674
3698
|
// src/cli/compileSourceFiles.ts
|
|
3675
|
-
import
|
|
3676
|
-
import
|
|
3699
|
+
import path18 from "path";
|
|
3700
|
+
import fs13 from "fs";
|
|
3677
3701
|
import fg5 from "fast-glob";
|
|
3678
3702
|
async function compileSourceFiles(options) {
|
|
3679
3703
|
const { rootDir, dist, files, logLevel = "silent", production, atomicWrite } = options;
|
|
@@ -3681,16 +3705,16 @@ async function compileSourceFiles(options) {
|
|
|
3681
3705
|
cwd: rootDir,
|
|
3682
3706
|
onlyFiles: true,
|
|
3683
3707
|
absolute: true,
|
|
3684
|
-
ignore:
|
|
3708
|
+
ignore: SOURCE_IGNORE
|
|
3685
3709
|
});
|
|
3686
3710
|
if (entryPoints.length === 0) {
|
|
3687
3711
|
return { compiledFiles: [] };
|
|
3688
3712
|
}
|
|
3689
|
-
const absDist =
|
|
3690
|
-
await
|
|
3713
|
+
const absDist = path18.resolve(rootDir, dist);
|
|
3714
|
+
await fs13.promises.mkdir(absDist, { recursive: true });
|
|
3691
3715
|
const plugins = buildAliasPlugins(rootDir);
|
|
3692
3716
|
const esbuild = await import("esbuild");
|
|
3693
|
-
const outbase =
|
|
3717
|
+
const outbase = path18.resolve(rootDir, APP_DIR);
|
|
3694
3718
|
const result = await esbuild.build({
|
|
3695
3719
|
entryPoints,
|
|
3696
3720
|
outdir: absDist,
|
|
@@ -3710,20 +3734,22 @@ async function compileSourceFiles(options) {
|
|
|
3710
3734
|
if (atomicWrite && result.outputFiles) {
|
|
3711
3735
|
await Promise.all(
|
|
3712
3736
|
result.outputFiles.map(async (file) => {
|
|
3713
|
-
await
|
|
3737
|
+
await fs13.promises.mkdir(path18.dirname(file.path), { recursive: true });
|
|
3714
3738
|
const tmp = `${file.path}.tmp-${process.pid}-${Math.random().toString(36).slice(2)}`;
|
|
3715
|
-
await
|
|
3716
|
-
await
|
|
3739
|
+
await fs13.promises.writeFile(tmp, file.contents);
|
|
3740
|
+
await fs13.promises.rename(tmp, file.path);
|
|
3717
3741
|
})
|
|
3718
3742
|
);
|
|
3719
3743
|
}
|
|
3720
3744
|
return { compiledFiles: entryPoints };
|
|
3721
3745
|
}
|
|
3746
|
+
var SOURCE_IGNORE;
|
|
3722
3747
|
var init_compileSourceFiles = __esm({
|
|
3723
3748
|
"src/cli/compileSourceFiles.ts"() {
|
|
3724
3749
|
"use strict";
|
|
3725
3750
|
init_aliasPlugin();
|
|
3726
3751
|
init_prodPaths();
|
|
3752
|
+
SOURCE_IGNORE = ["**/*.test.ts", "**/*.e2e.test.ts", "**/*.d.ts", `${APP_DIR}/resources/**`];
|
|
3727
3753
|
}
|
|
3728
3754
|
});
|
|
3729
3755
|
|
|
@@ -3739,12 +3765,12 @@ var init_compileDevRoutes = __esm({
|
|
|
3739
3765
|
});
|
|
3740
3766
|
|
|
3741
3767
|
// src/cli/compileOnDemand.ts
|
|
3742
|
-
import
|
|
3743
|
-
import
|
|
3768
|
+
import path19 from "path";
|
|
3769
|
+
import fs14 from "fs";
|
|
3744
3770
|
function isProductFresh(sourceAbsPath, productAbsPath) {
|
|
3745
3771
|
try {
|
|
3746
|
-
const srcStat =
|
|
3747
|
-
const prodStat =
|
|
3772
|
+
const srcStat = fs14.statSync(sourceAbsPath);
|
|
3773
|
+
const prodStat = fs14.statSync(productAbsPath);
|
|
3748
3774
|
return prodStat.mtimeMs >= srcStat.mtimeMs;
|
|
3749
3775
|
} catch {
|
|
3750
3776
|
return false;
|
|
@@ -3774,7 +3800,7 @@ async function ensureCompiled(sourceAbsPath, rootDir, dist) {
|
|
|
3774
3800
|
if (state.compiledFiles.has(sourceAbsPath)) {
|
|
3775
3801
|
return false;
|
|
3776
3802
|
}
|
|
3777
|
-
if (!
|
|
3803
|
+
if (!fs14.existsSync(sourceAbsPath)) {
|
|
3778
3804
|
return false;
|
|
3779
3805
|
}
|
|
3780
3806
|
const productPath = prodSourcePathToProductPath(sourceAbsPath, rootDir, dist);
|
|
@@ -3824,11 +3850,11 @@ async function ensureMiddlewaresCompiled(middlewarePaths, rootDir) {
|
|
|
3824
3850
|
}
|
|
3825
3851
|
}
|
|
3826
3852
|
function prodSourcePathToProductPath(sourceAbsPath, rootDir, dist) {
|
|
3827
|
-
const rel =
|
|
3853
|
+
const rel = path19.relative(rootDir, sourceAbsPath).replace(/\\/g, "/");
|
|
3828
3854
|
if (!rel.startsWith("src/")) return null;
|
|
3829
3855
|
const relWithoutSrc = rel.slice(4);
|
|
3830
3856
|
const jsRel = relWithoutSrc.replace(/\.ts$/, ".js");
|
|
3831
|
-
return
|
|
3857
|
+
return path19.resolve(rootDir, dist, jsRel);
|
|
3832
3858
|
}
|
|
3833
3859
|
function clearGeneratedSchemas() {
|
|
3834
3860
|
state.generatedSchemas.clear();
|
|
@@ -3843,9 +3869,9 @@ async function ensureSchemaGenerated(schemaPath, routeFilePath, routes, rootDir,
|
|
|
3843
3869
|
if (state.generatedSchemas.has(schemaPath)) {
|
|
3844
3870
|
return false;
|
|
3845
3871
|
}
|
|
3846
|
-
const prodAbsPath =
|
|
3872
|
+
const prodAbsPath = path19.resolve(rootDir, routeFilePath);
|
|
3847
3873
|
const sourceAbsPath = prodPathToSourcePath(prodAbsPath, rootDir, dist);
|
|
3848
|
-
if (!
|
|
3874
|
+
if (!fs14.existsSync(sourceAbsPath)) {
|
|
3849
3875
|
return false;
|
|
3850
3876
|
}
|
|
3851
3877
|
if (isProductFresh(sourceAbsPath, schemaPath)) {
|
|
@@ -3857,7 +3883,7 @@ async function ensureSchemaGenerated(schemaPath, routeFilePath, routes, rootDir,
|
|
|
3857
3883
|
if (fileRoutes.length === 0 && fileWsRoutes.length === 0) {
|
|
3858
3884
|
return false;
|
|
3859
3885
|
}
|
|
3860
|
-
const sourceRelPath =
|
|
3886
|
+
const sourceRelPath = path19.relative(rootDir, sourceAbsPath).replace(/\\/g, "/");
|
|
3861
3887
|
const sourceRoutes = fileRoutes.map((r) => ({ ...r, filePath: sourceRelPath }));
|
|
3862
3888
|
const sourceWsRoutes = fileWsRoutes.map((r) => ({ ...r, filePath: sourceRelPath }));
|
|
3863
3889
|
const generatePromise = (async () => {
|
|
@@ -3879,7 +3905,7 @@ async function deleteSchemaFiles(routes, rootDir, dist) {
|
|
|
3879
3905
|
if (deleted.has(schemaPath)) continue;
|
|
3880
3906
|
deleted.add(schemaPath);
|
|
3881
3907
|
try {
|
|
3882
|
-
await
|
|
3908
|
+
await fs14.promises.unlink(schemaPath);
|
|
3883
3909
|
} catch {
|
|
3884
3910
|
}
|
|
3885
3911
|
}
|
|
@@ -3887,19 +3913,19 @@ async function deleteSchemaFiles(routes, rootDir, dist) {
|
|
|
3887
3913
|
function prodPathToSourcePath(prodAbsPath, rootDir, dist) {
|
|
3888
3914
|
const cached = sourcePathCache.get(prodAbsPath);
|
|
3889
3915
|
if (cached) return cached;
|
|
3890
|
-
const rel =
|
|
3916
|
+
const rel = path19.relative(rootDir, prodAbsPath).replace(/\\/g, "/");
|
|
3891
3917
|
let relWithoutDist = rel;
|
|
3892
3918
|
if (relWithoutDist.startsWith(`${dist}/`)) {
|
|
3893
3919
|
relWithoutDist = relWithoutDist.slice(dist.length + 1);
|
|
3894
3920
|
}
|
|
3895
3921
|
const srcRel = `src/${relWithoutDist}`;
|
|
3896
3922
|
const tsRel = srcRel.replace(/\.js$/, ".ts");
|
|
3897
|
-
const tsAbs =
|
|
3923
|
+
const tsAbs = path19.resolve(rootDir, tsRel);
|
|
3898
3924
|
let result;
|
|
3899
|
-
if (
|
|
3925
|
+
if (fs14.existsSync(tsAbs)) {
|
|
3900
3926
|
result = tsAbs;
|
|
3901
3927
|
} else {
|
|
3902
|
-
result =
|
|
3928
|
+
result = path19.resolve(rootDir, srcRel);
|
|
3903
3929
|
}
|
|
3904
3930
|
sourcePathCache.set(prodAbsPath, result);
|
|
3905
3931
|
return result;
|
|
@@ -3930,15 +3956,15 @@ var init_compileOnDemand = __esm({
|
|
|
3930
3956
|
});
|
|
3931
3957
|
|
|
3932
3958
|
// src/config/loadConfig.ts
|
|
3933
|
-
import
|
|
3934
|
-
import
|
|
3959
|
+
import path20 from "path";
|
|
3960
|
+
import fs15 from "fs";
|
|
3935
3961
|
async function loadConfig(rootDir, dist) {
|
|
3936
|
-
const configProductPath =
|
|
3937
|
-
if (
|
|
3962
|
+
const configProductPath = path20.resolve(rootDir, dist, CONFIG_PRODUCT_FILE);
|
|
3963
|
+
if (fs15.existsSync(configProductPath)) {
|
|
3938
3964
|
const module = await importWithCacheBust(configProductPath);
|
|
3939
3965
|
return module.default ?? {};
|
|
3940
3966
|
}
|
|
3941
|
-
const hasSourceConfig =
|
|
3967
|
+
const hasSourceConfig = fs15.existsSync(path20.join(rootDir, "faapi.config.ts")) || fs15.existsSync(path20.join(rootDir, "faapi.config.js"));
|
|
3942
3968
|
if (hasSourceConfig) {
|
|
3943
3969
|
throw new Error(
|
|
3944
3970
|
`[faapi] ${dist}/${CONFIG_PRODUCT_FILE} \u4E0D\u5B58\u5728\uFF0C\u8BF7\u5148\u6267\u884C \`faapi build\`\uFF08\u6216 \`faapi dev\`\uFF09\u751F\u6210\u4EA7\u7269\u3002`
|
|
@@ -3956,8 +3982,8 @@ var init_loadConfig = __esm({
|
|
|
3956
3982
|
});
|
|
3957
3983
|
|
|
3958
3984
|
// src/cli/loadEnv.ts
|
|
3959
|
-
import
|
|
3960
|
-
import
|
|
3985
|
+
import fs16 from "fs";
|
|
3986
|
+
import path21 from "path";
|
|
3961
3987
|
function resolveEnv() {
|
|
3962
3988
|
return process.env.NODE_ENV || "development";
|
|
3963
3989
|
}
|
|
@@ -4024,9 +4050,9 @@ function loadEnv(rootDir) {
|
|
|
4024
4050
|
const files = getEnvFiles(env);
|
|
4025
4051
|
const merged = {};
|
|
4026
4052
|
for (const file of files) {
|
|
4027
|
-
const filePath =
|
|
4028
|
-
if (!
|
|
4029
|
-
const content =
|
|
4053
|
+
const filePath = path21.join(rootDir, file);
|
|
4054
|
+
if (!fs16.existsSync(filePath)) continue;
|
|
4055
|
+
const content = fs16.readFileSync(filePath, "utf-8");
|
|
4030
4056
|
const parsed = parseEnvFile(content, merged);
|
|
4031
4057
|
Object.assign(merged, parsed);
|
|
4032
4058
|
}
|
|
@@ -5816,6 +5842,53 @@ var init_rebuildScheduler = __esm({
|
|
|
5816
5842
|
}
|
|
5817
5843
|
});
|
|
5818
5844
|
|
|
5845
|
+
// src/cli/copyResources.ts
|
|
5846
|
+
import path22 from "path";
|
|
5847
|
+
import fs17 from "fs";
|
|
5848
|
+
function isResourceSourcePath(rootDir, absPath) {
|
|
5849
|
+
return isInsideDir(absPath, path22.resolve(rootDir, RESOURCES_DIR));
|
|
5850
|
+
}
|
|
5851
|
+
function resolveResourcesDir(rootDir, dist) {
|
|
5852
|
+
return path22.resolve(rootDir, dist, RESOURCES_OUTPUT_DIR);
|
|
5853
|
+
}
|
|
5854
|
+
async function copyResources(rootDir, dist) {
|
|
5855
|
+
const sourceDir = path22.resolve(rootDir, RESOURCES_DIR);
|
|
5856
|
+
if (!fs17.existsSync(sourceDir)) return false;
|
|
5857
|
+
const outDir = resolveResourcesDir(rootDir, dist);
|
|
5858
|
+
await fs17.promises.rm(outDir, { recursive: true, force: true });
|
|
5859
|
+
await fs17.promises.cp(sourceDir, outDir, { recursive: true });
|
|
5860
|
+
return true;
|
|
5861
|
+
}
|
|
5862
|
+
async function copyResourceFile(rootDir, dist, absSourceFile) {
|
|
5863
|
+
const sourceDir = path22.resolve(rootDir, RESOURCES_DIR);
|
|
5864
|
+
if (!isInsideDir(absSourceFile, sourceDir)) {
|
|
5865
|
+
throw new Error(`[faapi] copyResourceFile: ${absSourceFile} is not under ${RESOURCES_DIR}`);
|
|
5866
|
+
}
|
|
5867
|
+
if (!fs17.existsSync(absSourceFile)) return;
|
|
5868
|
+
const rel = path22.relative(sourceDir, absSourceFile);
|
|
5869
|
+
const dest = path22.join(resolveResourcesDir(rootDir, dist), rel);
|
|
5870
|
+
await fs17.promises.mkdir(path22.dirname(dest), { recursive: true });
|
|
5871
|
+
await fs17.promises.cp(absSourceFile, dest);
|
|
5872
|
+
}
|
|
5873
|
+
async function removeResourceFile(rootDir, dist, absSourceFile) {
|
|
5874
|
+
const sourceDir = path22.resolve(rootDir, RESOURCES_DIR);
|
|
5875
|
+
if (!isInsideDir(absSourceFile, sourceDir)) {
|
|
5876
|
+
throw new Error(`[faapi] removeResourceFile: ${absSourceFile} is not under ${RESOURCES_DIR}`);
|
|
5877
|
+
}
|
|
5878
|
+
const rel = path22.relative(sourceDir, absSourceFile);
|
|
5879
|
+
const dest = path22.join(resolveResourcesDir(rootDir, dist), rel);
|
|
5880
|
+
await fs17.promises.rm(dest, { force: true });
|
|
5881
|
+
}
|
|
5882
|
+
var RESOURCES_DIR, RESOURCES_OUTPUT_DIR;
|
|
5883
|
+
var init_copyResources = __esm({
|
|
5884
|
+
"src/cli/copyResources.ts"() {
|
|
5885
|
+
"use strict";
|
|
5886
|
+
init_prodPaths();
|
|
5887
|
+
RESOURCES_DIR = "src/resources";
|
|
5888
|
+
RESOURCES_OUTPUT_DIR = "resources";
|
|
5889
|
+
}
|
|
5890
|
+
});
|
|
5891
|
+
|
|
5819
5892
|
// src/cli/watcher.ts
|
|
5820
5893
|
import path23 from "path";
|
|
5821
5894
|
import { existsSync as existsSync2 } from "fs";
|
|
@@ -5865,6 +5938,7 @@ function startWatcher(options) {
|
|
|
5865
5938
|
}
|
|
5866
5939
|
if (!stats) return false;
|
|
5867
5940
|
if (stats.isDirectory()) return false;
|
|
5941
|
+
if (isResourceSourcePath(rootDir, path23.resolve(rootDir, filePath))) return false;
|
|
5868
5942
|
return !filePath.endsWith(".ts") && !filePath.endsWith(".js");
|
|
5869
5943
|
}
|
|
5870
5944
|
});
|
|
@@ -5872,6 +5946,15 @@ function startWatcher(options) {
|
|
|
5872
5946
|
watcher.on("change", (file) => handleFileEvent(file));
|
|
5873
5947
|
function handleFileEvent(file) {
|
|
5874
5948
|
const abs = path23.resolve(rootDir, file);
|
|
5949
|
+
if (isResourceSourcePath(rootDir, abs)) {
|
|
5950
|
+
void copyResourceFile(rootDir, devDist, abs).catch((err) => {
|
|
5951
|
+
console.error(
|
|
5952
|
+
"- Error copying resource:",
|
|
5953
|
+
err instanceof Error ? err.message : String(err)
|
|
5954
|
+
);
|
|
5955
|
+
});
|
|
5956
|
+
return;
|
|
5957
|
+
}
|
|
5875
5958
|
if (scheduleOnly.has(abs)) {
|
|
5876
5959
|
scheduler.schedule();
|
|
5877
5960
|
return;
|
|
@@ -5882,7 +5965,17 @@ function startWatcher(options) {
|
|
|
5882
5965
|
scheduler.addFiles([abs]);
|
|
5883
5966
|
}
|
|
5884
5967
|
watcher.on("unlink", (file) => {
|
|
5885
|
-
|
|
5968
|
+
const abs = path23.resolve(rootDir, file);
|
|
5969
|
+
if (isResourceSourcePath(rootDir, abs)) {
|
|
5970
|
+
void removeResourceFile(rootDir, devDist, abs).catch((err) => {
|
|
5971
|
+
console.error(
|
|
5972
|
+
"- Error removing resource:",
|
|
5973
|
+
err instanceof Error ? err.message : String(err)
|
|
5974
|
+
);
|
|
5975
|
+
});
|
|
5976
|
+
return;
|
|
5977
|
+
}
|
|
5978
|
+
scheduler.removeFiles([abs]);
|
|
5886
5979
|
scheduler.schedule();
|
|
5887
5980
|
});
|
|
5888
5981
|
watcher.on("error", (err) => {
|
|
@@ -5903,6 +5996,7 @@ var init_watcher = __esm({
|
|
|
5903
5996
|
init_compileDevRoutes();
|
|
5904
5997
|
init_compileConfig();
|
|
5905
5998
|
init_rebuildScheduler();
|
|
5999
|
+
init_copyResources();
|
|
5906
6000
|
}
|
|
5907
6001
|
});
|
|
5908
6002
|
|
|
@@ -6962,10 +7056,18 @@ function formatSetCookie(name, value, options) {
|
|
|
6962
7056
|
if (options?.sameSite) cookie += `; SameSite=${options.sameSite}`;
|
|
6963
7057
|
return cookie;
|
|
6964
7058
|
}
|
|
6965
|
-
function createContext(request, params, config = {}, ip = "", registries) {
|
|
6966
|
-
return createContextFromUrl(
|
|
7059
|
+
function createContext(request, params, config = {}, ip = "", registries, resourcesDir) {
|
|
7060
|
+
return createContextFromUrl(
|
|
7061
|
+
request,
|
|
7062
|
+
new URL(request.url),
|
|
7063
|
+
params,
|
|
7064
|
+
config,
|
|
7065
|
+
ip,
|
|
7066
|
+
registries,
|
|
7067
|
+
resourcesDir
|
|
7068
|
+
);
|
|
6967
7069
|
}
|
|
6968
|
-
function createContextFromUrl(request, url, params, config = {}, ip = "", registries) {
|
|
7070
|
+
function createContextFromUrl(request, url, params, config = {}, ip = "", registries, resourcesDir) {
|
|
6969
7071
|
const meta = { headers: {}, setCookies: [] };
|
|
6970
7072
|
const parsedCookies = parseCookies(request.headers.get("cookie") ?? "");
|
|
6971
7073
|
const cookiesObj = {};
|
|
@@ -6993,6 +7095,9 @@ function createContextFromUrl(request, url, params, config = {}, ip = "", regist
|
|
|
6993
7095
|
ua: request.headers.get("user-agent") ?? "",
|
|
6994
7096
|
cookies: cookiesObj,
|
|
6995
7097
|
config,
|
|
7098
|
+
// 运行时资源根目录(HTTP/WS 链路由 createServer/handleWsUpgrade 传入;
|
|
7099
|
+
// testing 直调未传时为 undefined,见 contextTypes.resourcesDir 注释)
|
|
7100
|
+
resourcesDir,
|
|
6996
7101
|
meta,
|
|
6997
7102
|
setStatus(status) {
|
|
6998
7103
|
meta.status = status;
|
|
@@ -8528,6 +8633,7 @@ function attachWebSocket(options) {
|
|
|
8528
8633
|
trustedProxy = false,
|
|
8529
8634
|
registries
|
|
8530
8635
|
} = options;
|
|
8636
|
+
const resourcesDir = resolveResourcesDir(rootDir, dist);
|
|
8531
8637
|
const wss = new WebSocketServer({ noServer: true });
|
|
8532
8638
|
server.on("upgrade", async (req, socket, head) => {
|
|
8533
8639
|
try {
|
|
@@ -8559,7 +8665,14 @@ function attachWebSocket(options) {
|
|
|
8559
8665
|
const host = req.headers.host ?? "localhost";
|
|
8560
8666
|
const fullUrl = new URL(`http://${host}${req.url ?? "/"}`);
|
|
8561
8667
|
const request = new Request(fullUrl.toString(), { method: "GET", headers });
|
|
8562
|
-
const ctx = createContext(
|
|
8668
|
+
const ctx = createContext(
|
|
8669
|
+
request,
|
|
8670
|
+
params,
|
|
8671
|
+
config,
|
|
8672
|
+
getClientIp(req, trustedProxy),
|
|
8673
|
+
registries,
|
|
8674
|
+
resourcesDir
|
|
8675
|
+
);
|
|
8563
8676
|
const meta = ctx.meta;
|
|
8564
8677
|
let upgraded = false;
|
|
8565
8678
|
const finalHandler = async () => {
|
|
@@ -8661,6 +8774,7 @@ var init_handleWsUpgrade = __esm({
|
|
|
8661
8774
|
"use strict";
|
|
8662
8775
|
init_matchRoute();
|
|
8663
8776
|
init_createContext();
|
|
8777
|
+
init_copyResources();
|
|
8664
8778
|
init_invokeHandler();
|
|
8665
8779
|
init_importWithCacheBust();
|
|
8666
8780
|
init_getClientIp();
|
|
@@ -8787,6 +8901,7 @@ function createServer(options) {
|
|
|
8787
8901
|
trustedProxy = false
|
|
8788
8902
|
} = options;
|
|
8789
8903
|
const routesRef = { current: routes, wsCurrent: wsRoutes ?? [] };
|
|
8904
|
+
const resourcesDir = resolveResourcesDir(rootDir, dist);
|
|
8790
8905
|
const configMiddlewares = [];
|
|
8791
8906
|
if (compressionOption) {
|
|
8792
8907
|
const compOpts = typeof compressionOption === "object" ? compressionOption : {};
|
|
@@ -8833,7 +8948,8 @@ function createServer(options) {
|
|
|
8833
8948
|
bodyLimit,
|
|
8834
8949
|
trustedProxy,
|
|
8835
8950
|
registries,
|
|
8836
|
-
routesRef.wsCurrent
|
|
8951
|
+
routesRef.wsCurrent,
|
|
8952
|
+
resourcesDir
|
|
8837
8953
|
).catch((err) => {
|
|
8838
8954
|
console.error("[faapi] Request pipeline failed after error response attempt:", err);
|
|
8839
8955
|
try {
|
|
@@ -8859,7 +8975,7 @@ function createServer(options) {
|
|
|
8859
8975
|
});
|
|
8860
8976
|
return { server, routesRef };
|
|
8861
8977
|
}
|
|
8862
|
-
function prepareRequest(req, request, url, config, trustedProxy, registries, preMatched) {
|
|
8978
|
+
function prepareRequest(req, request, url, config, trustedProxy, registries, preMatched, resourcesDir) {
|
|
8863
8979
|
const method = request.method.toUpperCase();
|
|
8864
8980
|
const urlPath = url.pathname;
|
|
8865
8981
|
const ctx = createContextFromUrl(
|
|
@@ -8868,7 +8984,8 @@ function prepareRequest(req, request, url, config, trustedProxy, registries, pre
|
|
|
8868
8984
|
preMatched?.params ?? {},
|
|
8869
8985
|
config,
|
|
8870
8986
|
getClientIp(req, trustedProxy),
|
|
8871
|
-
registries
|
|
8987
|
+
registries,
|
|
8988
|
+
resourcesDir
|
|
8872
8989
|
);
|
|
8873
8990
|
const meta = ctx.meta;
|
|
8874
8991
|
return { request, url, ctx, meta, method, urlPath };
|
|
@@ -9008,7 +9125,7 @@ async function sendErrorResponse(err, meta, res, onError, ctx) {
|
|
|
9008
9125
|
}
|
|
9009
9126
|
}
|
|
9010
9127
|
}
|
|
9011
|
-
async function handleRequest(routes, rootDir, dist, req, res, outerMiddlewares, onError, config, globalInjectors, bodyLimit, trustedProxy, registries, wsRoutes) {
|
|
9128
|
+
async function handleRequest(routes, rootDir, dist, req, res, outerMiddlewares, onError, config, globalInjectors, bodyLimit, trustedProxy, registries, wsRoutes, resourcesDir) {
|
|
9012
9129
|
let meta = { headers: {}, setCookies: [] };
|
|
9013
9130
|
let ctx;
|
|
9014
9131
|
let sseEarlySent = false;
|
|
@@ -9028,7 +9145,8 @@ async function handleRequest(routes, rootDir, dist, req, res, outerMiddlewares,
|
|
|
9028
9145
|
config,
|
|
9029
9146
|
trustedProxy,
|
|
9030
9147
|
registries,
|
|
9031
|
-
preMatched
|
|
9148
|
+
preMatched,
|
|
9149
|
+
resourcesDir
|
|
9032
9150
|
);
|
|
9033
9151
|
ctx = prepared.ctx;
|
|
9034
9152
|
meta = prepared.meta;
|
|
@@ -9097,6 +9215,7 @@ var init_createServer = __esm({
|
|
|
9097
9215
|
init_handleWsUpgrade();
|
|
9098
9216
|
init_serverUtils();
|
|
9099
9217
|
init_generateSchemaFiles();
|
|
9218
|
+
init_copyResources();
|
|
9100
9219
|
init_compileOnDemand();
|
|
9101
9220
|
init_loadMiddlewares();
|
|
9102
9221
|
DEFAULT_BODY_LIMIT = 10 * 1024 * 1024;
|
|
@@ -9317,7 +9436,11 @@ async function runTaskInWorker(options) {
|
|
|
9317
9436
|
worker.postMessage({
|
|
9318
9437
|
type: "run",
|
|
9319
9438
|
payload,
|
|
9320
|
-
taskCtx: {
|
|
9439
|
+
taskCtx: {
|
|
9440
|
+
config: safeConfig(taskCtx.config),
|
|
9441
|
+
resourcesDir: taskCtx.resourcesDir,
|
|
9442
|
+
job: taskCtx.job
|
|
9443
|
+
},
|
|
9321
9444
|
registries: options.registries,
|
|
9322
9445
|
log: options.log
|
|
9323
9446
|
});
|
|
@@ -9541,6 +9664,7 @@ function createTaskQueue(deps) {
|
|
|
9541
9664
|
payload: job.payload,
|
|
9542
9665
|
taskCtx: {
|
|
9543
9666
|
config: deps.config,
|
|
9667
|
+
resourcesDir: deps.resourcesDir,
|
|
9544
9668
|
job: { id: job.id, name: job.name, attempt: job.attempt }
|
|
9545
9669
|
},
|
|
9546
9670
|
registries: snapshotRegistries(),
|
|
@@ -9571,6 +9695,7 @@ function createTaskQueue(deps) {
|
|
|
9571
9695
|
const taskCtx = {
|
|
9572
9696
|
signal: job.signal,
|
|
9573
9697
|
config: deps.config,
|
|
9698
|
+
resourcesDir: deps.resourcesDir,
|
|
9574
9699
|
job: { id: job.id, name: job.name, attempt: job.attempt },
|
|
9575
9700
|
registries: registriesView,
|
|
9576
9701
|
log: createLogger(`task:${job.name}`, {
|
|
@@ -10204,8 +10329,7 @@ function logStartupSummary(routes, wsRoutes, tools, agents, taskMetas, p) {
|
|
|
10204
10329
|
if (agents.length > 0) {
|
|
10205
10330
|
console.log(`- Loaded ${agents.length} agent(s):`);
|
|
10206
10331
|
for (const agent of agents) {
|
|
10207
|
-
|
|
10208
|
-
console.log(` ${agent.name} [${exports}] ${agent.filePath}`);
|
|
10332
|
+
console.log(` ${agent.name} ${agent.filePath}`);
|
|
10209
10333
|
}
|
|
10210
10334
|
}
|
|
10211
10335
|
if (taskMetas.length > 0) {
|
|
@@ -10219,6 +10343,7 @@ function logStartupSummary(routes, wsRoutes, tools, agents, taskMetas, p) {
|
|
|
10219
10343
|
async function createAppBase(options) {
|
|
10220
10344
|
const rootDir = options?.rootDir ?? process.cwd();
|
|
10221
10345
|
const dist = options?.dist ?? process.env.FAAPI_DIST ?? DEFAULT_DIST;
|
|
10346
|
+
const resourcesDir = resolveResourcesDir(rootDir, dist);
|
|
10222
10347
|
const routesPath = path30.resolve(rootDir, dist, ROUTES_FILE);
|
|
10223
10348
|
if (!fs22.existsSync(routesPath)) {
|
|
10224
10349
|
throw new Error(
|
|
@@ -10241,6 +10366,7 @@ async function createAppBase(options) {
|
|
|
10241
10366
|
registry: registries.task,
|
|
10242
10367
|
rootDir,
|
|
10243
10368
|
config,
|
|
10369
|
+
resourcesDir,
|
|
10244
10370
|
registries: createTaskRegistriesView(registries),
|
|
10245
10371
|
driver: taskDriver,
|
|
10246
10372
|
onFailed: config?.task?.onFailed
|
|
@@ -10282,6 +10408,7 @@ async function createAppBase(options) {
|
|
|
10282
10408
|
config?.plugins,
|
|
10283
10409
|
{
|
|
10284
10410
|
rootDir,
|
|
10411
|
+
resourcesDir,
|
|
10285
10412
|
registries,
|
|
10286
10413
|
routes: sorted,
|
|
10287
10414
|
getRoutes: () => sorted,
|
|
@@ -10299,6 +10426,8 @@ async function createAppBase(options) {
|
|
|
10299
10426
|
routes: sorted,
|
|
10300
10427
|
wsRoutes,
|
|
10301
10428
|
rootDir,
|
|
10429
|
+
dist,
|
|
10430
|
+
resourcesDir,
|
|
10302
10431
|
tasks: taskQueue,
|
|
10303
10432
|
async listen(listenPort) {
|
|
10304
10433
|
const envPort = process.env.PORT ? Number(process.env.PORT) : void 0;
|
|
@@ -10310,7 +10439,8 @@ async function createAppBase(options) {
|
|
|
10310
10439
|
routes: sorted,
|
|
10311
10440
|
server,
|
|
10312
10441
|
registries,
|
|
10313
|
-
tasks: taskQueue
|
|
10442
|
+
tasks: taskQueue,
|
|
10443
|
+
resourcesDir
|
|
10314
10444
|
});
|
|
10315
10445
|
console.log("- onBoot hook executed");
|
|
10316
10446
|
} catch (err) {
|
|
@@ -10345,7 +10475,8 @@ async function createAppBase(options) {
|
|
|
10345
10475
|
routes: sorted,
|
|
10346
10476
|
server,
|
|
10347
10477
|
registries,
|
|
10348
|
-
tasks: taskQueue
|
|
10478
|
+
tasks: taskQueue,
|
|
10479
|
+
resourcesDir
|
|
10349
10480
|
});
|
|
10350
10481
|
console.log("- onReady hook executed");
|
|
10351
10482
|
}
|
|
@@ -10369,7 +10500,8 @@ async function createAppBase(options) {
|
|
|
10369
10500
|
routes: sorted,
|
|
10370
10501
|
server,
|
|
10371
10502
|
registries,
|
|
10372
|
-
tasks: taskQueue
|
|
10503
|
+
tasks: taskQueue,
|
|
10504
|
+
resourcesDir
|
|
10373
10505
|
});
|
|
10374
10506
|
}
|
|
10375
10507
|
registries.tool.clear();
|
|
@@ -10451,6 +10583,7 @@ var init_createAppCore = __esm({
|
|
|
10451
10583
|
init_manifestLoader();
|
|
10452
10584
|
init_appSingleton();
|
|
10453
10585
|
init_injectMock();
|
|
10586
|
+
init_copyResources();
|
|
10454
10587
|
init_manifestLoader();
|
|
10455
10588
|
DEFAULT_DIST = "dist";
|
|
10456
10589
|
DEFAULT_PORT = 3e3;
|
|
@@ -10604,6 +10737,10 @@ async function devCommand(options) {
|
|
|
10604
10737
|
await generateAgentArtifactsForDev(rootDir, devDist);
|
|
10605
10738
|
console.log("- Generating task artifacts...");
|
|
10606
10739
|
await generateTaskArtifactsForDev(rootDir, devDist);
|
|
10740
|
+
console.log("- Copying resources...");
|
|
10741
|
+
const copied = await copyResources(rootDir, devDist);
|
|
10742
|
+
if (copied)
|
|
10743
|
+
console.log(` Copied src/resources \u2192 ${path32.resolve(rootDir, devDist, "resources")}`);
|
|
10607
10744
|
console.log("- Starting dev app...");
|
|
10608
10745
|
const app = await createDevApp({ rootDir, port: options?.port });
|
|
10609
10746
|
await app.listen();
|
|
@@ -10653,6 +10790,7 @@ var init_devCommand = __esm({
|
|
|
10653
10790
|
init_watcher();
|
|
10654
10791
|
init_createDevApp();
|
|
10655
10792
|
init_compileOnDemand();
|
|
10793
|
+
init_copyResources();
|
|
10656
10794
|
init_prodPaths();
|
|
10657
10795
|
DEV_DIST = ".faapi";
|
|
10658
10796
|
ROUTES_FILE2 = "faapi-routes.js";
|
|
@@ -10707,7 +10845,7 @@ async function buildCommand(options) {
|
|
|
10707
10845
|
console.log(`- Root: ${rootDir}`);
|
|
10708
10846
|
console.log(`- Source: src/`);
|
|
10709
10847
|
console.log(`- Output: ${outdir}`);
|
|
10710
|
-
console.log("\n[1/
|
|
10848
|
+
console.log("\n[1/9] Compiling TypeScript (bundle: false)...");
|
|
10711
10849
|
const result = await compileBuildRoutes({
|
|
10712
10850
|
rootDir,
|
|
10713
10851
|
dist: outdir,
|
|
@@ -10720,7 +10858,7 @@ async function buildCommand(options) {
|
|
|
10720
10858
|
}
|
|
10721
10859
|
const localPluginSources = extractLocalPluginSources(_config?.plugins, rootDir);
|
|
10722
10860
|
if (localPluginSources.length > 0) {
|
|
10723
|
-
console.log("\n[2.5/
|
|
10861
|
+
console.log("\n[2.5/9] Compiling local plugins...");
|
|
10724
10862
|
const outside = localPluginSources.filter((p) => {
|
|
10725
10863
|
const rel = path33.relative(rootDir, p).replace(/\\/g, "/");
|
|
10726
10864
|
return !rel.startsWith("src/");
|
|
@@ -10730,35 +10868,40 @@ async function buildCommand(options) {
|
|
|
10730
10868
|
}
|
|
10731
10869
|
console.log(` Compiled ${localPluginSources.length} local plugin(s)`);
|
|
10732
10870
|
}
|
|
10733
|
-
console.log("\n[3/
|
|
10871
|
+
console.log("\n[3/9] Scanning routes...");
|
|
10734
10872
|
const { routes, wsRoutes } = await scanRoutes(rootDir, ROUTE_PATTERNS, outdir);
|
|
10735
10873
|
const sorted = sortRoutes(routes);
|
|
10736
10874
|
console.log(` Found ${sorted.length} routes, ${wsRoutes.length} WS routes`);
|
|
10737
10875
|
reportRouteConflicts(sorted);
|
|
10738
|
-
console.log("\n[4/
|
|
10876
|
+
console.log("\n[4/9] Generating schema...");
|
|
10739
10877
|
await generateSchemaFiles(sorted, rootDir, outdir, wsRoutes);
|
|
10740
10878
|
console.log(` Schema: zod.js files under ${path33.resolve(rootDir, outdir)}`);
|
|
10741
|
-
console.log("\n[5/
|
|
10879
|
+
console.log("\n[5/9] Generating routes manifest...");
|
|
10742
10880
|
const routesPath = path33.resolve(rootDir, outdir, "faapi-routes.js");
|
|
10743
10881
|
const serialized = serializeRoutes(sorted, wsRoutes, rootDir, outdir);
|
|
10744
10882
|
await writeRoutesModule(serialized, routesPath);
|
|
10745
10883
|
console.log(` Written to ${routesPath}`);
|
|
10746
|
-
console.log("\n[6/
|
|
10884
|
+
console.log("\n[6/9] Generating tool manifest and schema...");
|
|
10747
10885
|
const tools = await scanTools(rootDir, TOOL_PATTERNS);
|
|
10748
10886
|
const toolMeta = await generateToolArtifacts(tools, rootDir, outdir);
|
|
10749
10887
|
console.log(` Found ${toolMeta.length} tool(s)`);
|
|
10750
10888
|
console.log(` Tool manifest: ${path33.resolve(rootDir, outdir, "faapi-tools.js")}`);
|
|
10751
|
-
console.log("\n[7/
|
|
10889
|
+
console.log("\n[7/9] Generating agent manifest...");
|
|
10752
10890
|
const agents = await scanAgents(rootDir, DEFAULT_AGENT_PATTERNS);
|
|
10753
10891
|
const agentMeta = await generateAgentArtifacts(agents, rootDir, outdir);
|
|
10754
10892
|
console.log(` Found ${agentMeta.length} agent(s)`);
|
|
10755
10893
|
console.log(` Agent manifest: ${path33.resolve(rootDir, outdir, "faapi-agents.js")}`);
|
|
10756
|
-
console.log("\n[7.5/
|
|
10894
|
+
console.log("\n[7.5/9] Generating task manifest and schema...");
|
|
10757
10895
|
const tasks = await scanTasks(rootDir, TASK_PATTERNS);
|
|
10758
10896
|
const taskMeta = await generateTaskArtifacts(tasks, rootDir, outdir);
|
|
10759
10897
|
console.log(` Found ${taskMeta.length} task(s)`);
|
|
10760
10898
|
console.log(` Task manifest: ${path33.resolve(rootDir, outdir, "faapi-tasks.js")}`);
|
|
10761
|
-
console.log("\n[8/
|
|
10899
|
+
console.log("\n[8/9] Copying resources...");
|
|
10900
|
+
const resourcesCopied = await copyResources(rootDir, outdir);
|
|
10901
|
+
if (resourcesCopied) {
|
|
10902
|
+
console.log(` Copied src/resources \u2192 ${path33.resolve(rootDir, outdir, "resources")}`);
|
|
10903
|
+
}
|
|
10904
|
+
console.log("\n[9/9] Generating entry file...");
|
|
10762
10905
|
const mainPath = path33.resolve(rootDir, outdir, "main.js");
|
|
10763
10906
|
const createProdAppArgs = options?.dist && options.dist !== DEFAULT_DIST2 ? `{ dist: ${JSON.stringify(outdir)} }` : "";
|
|
10764
10907
|
const mainContent = `// \u7531 faapi build \u81EA\u52A8\u751F\u6210\uFF0C\u8BF7\u52FF\u624B\u52A8\u7F16\u8F91
|
|
@@ -10814,6 +10957,7 @@ var init_buildCommand = __esm({
|
|
|
10814
10957
|
init_generateSchemaFiles();
|
|
10815
10958
|
init_generateRoutes();
|
|
10816
10959
|
init_compileBuildRoutes();
|
|
10960
|
+
init_copyResources();
|
|
10817
10961
|
init_prodPaths();
|
|
10818
10962
|
init_compileConfig();
|
|
10819
10963
|
init_loadConfig();
|