befly 3.13.7 → 3.13.9

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/befly.js CHANGED
@@ -83,30 +83,6 @@ function normalizePositiveInt(value, fallback, min, max) {
83
83
  return max;
84
84
  return v;
85
85
  }
86
- function isEmpty(value) {
87
- if (value === null || value === undefined) {
88
- return true;
89
- }
90
- if (typeof value === "string") {
91
- return value.trim().length === 0;
92
- }
93
- if (typeof value === "number") {
94
- return value === 0 || Number.isNaN(value);
95
- }
96
- if (typeof value === "boolean") {
97
- return value === false;
98
- }
99
- if (Array.isArray(value)) {
100
- return value.length === 0;
101
- }
102
- if (value instanceof Map || value instanceof Set) {
103
- return value.size === 0;
104
- }
105
- if (isPlainObject(value)) {
106
- return Object.keys(value).length === 0;
107
- }
108
- return false;
109
- }
110
86
  function forOwn(obj, iteratee) {
111
87
  if (typeof iteratee !== "function") {
112
88
  return;
@@ -203,17 +179,6 @@ var keysToCamel = (obj) => {
203
179
  if (!arr || !Array.isArray(arr))
204
180
  return arr;
205
181
  return arr.map((item) => keysToCamel(item));
206
- }, pickFields = (obj, keys) => {
207
- if (!obj || !isPlainObject(obj) && !Array.isArray(obj)) {
208
- return {};
209
- }
210
- const result = {};
211
- for (const key of keys) {
212
- if (key in obj) {
213
- result[key] = obj[key];
214
- }
215
- }
216
- return result;
217
182
  };
218
183
  var init_util = () => {};
219
184
 
@@ -1013,6 +978,43 @@ var init_logger = __esm(() => {
1013
978
  Logger = new LoggerFacade;
1014
979
  });
1015
980
 
981
+ // utils/importDefault.ts
982
+ import { isAbsolute } from "path";
983
+ import { pathToFileURL } from "url";
984
+ function isWindowsAbsPath(file) {
985
+ return /^[a-zA-Z]:[\\/]/.test(file);
986
+ }
987
+ function toFileImportUrl(file) {
988
+ if (isAbsolute(file) || isWindowsAbsPath(file)) {
989
+ return pathToFileURL(file).href;
990
+ }
991
+ return file;
992
+ }
993
+ async function importDefault(file, defaultValue) {
994
+ try {
995
+ const isJson = file.endsWith(".json");
996
+ const mod = isJson ? await import(toFileImportUrl(file), { with: { type: "json" } }) : await import(file);
997
+ const value = mod?.default;
998
+ if (value === null || value === undefined) {
999
+ return defaultValue;
1000
+ }
1001
+ const expectedType = getTypeTag(defaultValue);
1002
+ const actualType = getTypeTag(value);
1003
+ if (expectedType !== actualType) {
1004
+ Logger.warn({ file, msg: "importDefault \u5BFC\u5165\u7C7B\u578B\u4E0E\u9ED8\u8BA4\u503C\u4E0D\u4E00\u81F4\uFF0C\u5DF2\u56DE\u9000\u5230\u9ED8\u8BA4\u503C", expectedType, actualType });
1005
+ return defaultValue;
1006
+ }
1007
+ return value;
1008
+ } catch (err) {
1009
+ Logger.warn({ err, file, msg: "importDefault \u5BFC\u5165\u5931\u8D25\uFF0C\u5DF2\u56DE\u9000\u5230\u9ED8\u8BA4\u503C" });
1010
+ return defaultValue;
1011
+ }
1012
+ }
1013
+ var init_importDefault = __esm(() => {
1014
+ init_logger();
1015
+ init_util();
1016
+ });
1017
+
1016
1018
  // ../../node_modules/.bun/pathe@2.0.3/node_modules/pathe/dist/shared/pathe.M-eThtNZ.mjs
1017
1019
  function normalizeWindowsPath(input = "") {
1018
1020
  if (!input) {
@@ -1240,31 +1242,18 @@ var init_isDirentDirectory = __esm(() => {
1240
1242
 
1241
1243
  // utils/loadMenuConfigs.ts
1242
1244
  import { existsSync as existsSync2 } from "fs";
1243
- import { readdir, readFile } from "fs/promises";
1244
- function cleanDirName(name) {
1245
- return String(name).replace(/_\d+$/, "");
1246
- }
1247
- function extractScriptSetupBlock(vueContent) {
1248
- const openTag = /<script\b[^>]*\bsetup\b[^>]*>/i.exec(vueContent);
1249
- if (!openTag) {
1250
- return null;
1251
- }
1252
- const start = openTag.index + openTag[0].length;
1253
- const closeIndex = vueContent.indexOf("</script>", start);
1254
- if (closeIndex < 0) {
1245
+ import { readdir } from "fs/promises";
1246
+ function normalizeViewDirMeta(input) {
1247
+ if (!input || typeof input !== "object") {
1255
1248
  return null;
1256
1249
  }
1257
- return vueContent.slice(start, closeIndex);
1258
- }
1259
- function extractDefinePageMetaFromScriptSetup(scriptSetup) {
1260
- const titleMatch = scriptSetup.match(/definePage\s*\([\s\S]*?meta\s*:\s*\{[\s\S]*?title\s*:\s*(["'`])([^"'`]+)\1/);
1261
- if (!titleMatch) {
1250
+ if (typeof input.title !== "string" || !input.title) {
1262
1251
  return null;
1263
1252
  }
1264
- const orderMatch = scriptSetup.match(/definePage\s*\([\s\S]*?meta\s*:\s*\{[\s\S]*?order\s*:\s*(\d+)/);
1253
+ const order = typeof input.order === "number" && Number.isFinite(input.order) && Number.isInteger(input.order) && input.order >= 0 ? input.order : undefined;
1265
1254
  return {
1266
- title: titleMatch[2],
1267
- order: orderMatch ? Number(orderMatch[1]) : undefined
1255
+ title: input.title,
1256
+ order
1268
1257
  };
1269
1258
  }
1270
1259
  async function scanViewsDirToMenuConfigs(viewsDir, prefix, parentPath = "") {
@@ -1278,31 +1267,26 @@ async function scanViewsDirToMenuConfigs(viewsDir, prefix, parentPath = "") {
1278
1267
  continue;
1279
1268
  }
1280
1269
  const dirPath = join2(viewsDir, entry.name);
1270
+ const metaJsonPath = join2(dirPath, "meta.json");
1281
1271
  const indexVuePath = join2(dirPath, "index.vue");
1272
+ let meta = null;
1273
+ if (!existsSync2(metaJsonPath)) {
1274
+ continue;
1275
+ }
1282
1276
  if (!existsSync2(indexVuePath)) {
1277
+ Logger.warn({ path: dirPath, msg: "\u76EE\u5F55\u5B58\u5728 meta.json \u4F46\u7F3A\u5C11 index.vue\uFF0C\u5DF2\u8DF3\u8FC7\u8BE5\u76EE\u5F55\u83DC\u5355\u540C\u6B65" });
1283
1278
  continue;
1284
1279
  }
1285
- let meta = null;
1286
- try {
1287
- const content = await readFile(indexVuePath, "utf-8");
1288
- const scriptSetup = extractScriptSetupBlock(content);
1289
- if (!scriptSetup) {
1290
- Logger.warn({ path: indexVuePath, msg: "index.vue \u7F3A\u5C11 <script setup>\uFF0C\u5DF2\u8DF3\u8FC7\u8BE5\u76EE\u5F55\u83DC\u5355\u540C\u6B65" });
1291
- continue;
1292
- }
1293
- meta = extractDefinePageMetaFromScriptSetup(scriptSetup);
1294
- if (!meta?.title) {
1295
- Logger.warn({ path: indexVuePath, msg: "index.vue \u672A\u58F0\u660E definePage({ meta: { title, order? } })\uFF0C\u5DF2\u8DF3\u8FC7\u8BE5\u76EE\u5F55\u83DC\u5355\u540C\u6B65" });
1296
- continue;
1297
- }
1298
- } catch (error) {
1299
- Logger.warn({ err: error, path: indexVuePath, msg: "\u8BFB\u53D6 index.vue \u5931\u8D25" });
1280
+ const metaRaw = await importDefault(metaJsonPath, {});
1281
+ meta = normalizeViewDirMeta(metaRaw);
1282
+ if (!meta?.title) {
1283
+ Logger.warn({ path: metaJsonPath, msg: "meta.json \u7F3A\u5C11\u6709\u6548\u7684 title\uFF08\u4EE5\u53CA\u53EF\u9009 order:number\uFF09\uFF0C\u5DF2\u8DF3\u8FC7\u8BE5\u76EE\u5F55\u83DC\u5355\u540C\u6B65" });
1300
1284
  continue;
1301
1285
  }
1302
1286
  if (!meta?.title) {
1303
1287
  continue;
1304
1288
  }
1305
- const cleanName = cleanDirName(entry.name);
1289
+ const cleanName = String(entry.name).replace(/_\d+$/, "");
1306
1290
  let menuPath;
1307
1291
  if (cleanName === "index") {
1308
1292
  menuPath = parentPath;
@@ -1360,16 +1344,11 @@ async function loadMenuConfigs(addons) {
1360
1344
  }
1361
1345
  const menusJsonPath = join2(process.cwd(), "menus.json");
1362
1346
  if (existsSync2(menusJsonPath)) {
1363
- try {
1364
- const content = await readFile(menusJsonPath, "utf-8");
1365
- const appMenus = JSON.parse(content);
1366
- if (Array.isArray(appMenus) && appMenus.length > 0) {
1367
- for (const menu of appMenus) {
1368
- allMenus.push(menu);
1369
- }
1347
+ const appMenus = await importDefault(menusJsonPath, []);
1348
+ if (Array.isArray(appMenus) && appMenus.length > 0) {
1349
+ for (const menu of appMenus) {
1350
+ allMenus.push(menu);
1370
1351
  }
1371
- } catch (error) {
1372
- Logger.warn({ err: error, msg: "\u8BFB\u53D6\u9879\u76EE menus.json \u5931\u8D25" });
1373
1352
  }
1374
1353
  }
1375
1354
  return allMenus;
@@ -1377,6 +1356,7 @@ async function loadMenuConfigs(addons) {
1377
1356
  var init_loadMenuConfigs = __esm(() => {
1378
1357
  init_dist();
1379
1358
  init_logger();
1359
+ init_importDefault();
1380
1360
  init_isDirentDirectory();
1381
1361
  });
1382
1362
 
@@ -7443,43 +7423,9 @@ var require_src = __commonJS((exports, module) => {
7443
7423
  });
7444
7424
 
7445
7425
  // befly.config.ts
7426
+ init_importDefault();
7446
7427
  import { join } from "path";
7447
7428
 
7448
- // utils/importDefault.ts
7449
- init_logger();
7450
- init_util();
7451
- import { isAbsolute } from "path";
7452
- import { pathToFileURL } from "url";
7453
- function isWindowsAbsPath(file) {
7454
- return /^[a-zA-Z]:[\\/]/.test(file);
7455
- }
7456
- function toFileImportUrl(file) {
7457
- if (isAbsolute(file) || isWindowsAbsPath(file)) {
7458
- return pathToFileURL(file).href;
7459
- }
7460
- return file;
7461
- }
7462
- async function importDefault(file, defaultValue) {
7463
- try {
7464
- const isJson = file.endsWith(".json");
7465
- const mod = isJson ? await import(toFileImportUrl(file), { with: { type: "json" } }) : await import(file);
7466
- const value = mod?.default;
7467
- if (value === null || value === undefined) {
7468
- return defaultValue;
7469
- }
7470
- const expectedType = getTypeTag(defaultValue);
7471
- const actualType = getTypeTag(value);
7472
- if (expectedType !== actualType) {
7473
- Logger.warn({ file, msg: "importDefault \u5BFC\u5165\u7C7B\u578B\u4E0E\u9ED8\u8BA4\u503C\u4E0D\u4E00\u81F4\uFF0C\u5DF2\u56DE\u9000\u5230\u9ED8\u8BA4\u503C", expectedType, actualType });
7474
- return defaultValue;
7475
- }
7476
- return value;
7477
- } catch (err) {
7478
- Logger.warn({ err, file, msg: "importDefault \u5BFC\u5165\u5931\u8D25\uFF0C\u5DF2\u56DE\u9000\u5230\u9ED8\u8BA4\u503C" });
7479
- return defaultValue;
7480
- }
7481
- }
7482
-
7483
7429
  // utils/mergeAndConcat.ts
7484
7430
  init_util();
7485
7431
  function cloneDeepLoose(value) {
@@ -8851,7 +8797,7 @@ async function syncApi(ctx, apis) {
8851
8797
  }
8852
8798
  const allDbApis = await ctx.db.getAll({
8853
8799
  table: tableName,
8854
- fields: ["id", "routePath", "name", "addonName", "state"],
8800
+ fields: ["id", "routePath", "name", "addonName", "auth", "state"],
8855
8801
  where: { state$gte: 0 }
8856
8802
  });
8857
8803
  const dbLists = allDbApis.data.lists || [];
@@ -8865,16 +8811,24 @@ async function syncApi(ctx, apis) {
8865
8811
  if (apiType && apiType !== "api") {
8866
8812
  continue;
8867
8813
  }
8868
- const routePath = api.routePath;
8869
- apiRouteKeys.add(api.routePath);
8814
+ const normalizedAuth = api.auth === 0 || api.auth === false ? 0 : 1;
8815
+ const normalizedApi = {
8816
+ name: api.name,
8817
+ routePath: api.routePath,
8818
+ addonName: api.addonName,
8819
+ auth: normalizedAuth
8820
+ };
8821
+ const routePath = normalizedApi.routePath;
8822
+ apiRouteKeys.add(routePath);
8870
8823
  const item = allDbApiMap[routePath];
8871
8824
  if (item) {
8872
- const shouldUpdate = api.name !== item.name || api.routePath !== item.routePath || api.addonName !== item.addonName;
8825
+ const dbAuth = item.auth === 0 || item.auth === false ? 0 : 1;
8826
+ const shouldUpdate = normalizedApi.name !== item.name || normalizedApi.routePath !== item.routePath || normalizedApi.addonName !== item.addonName || normalizedAuth !== dbAuth;
8873
8827
  if (shouldUpdate) {
8874
- updData.push({ id: item.id, api });
8828
+ updData.push({ id: item.id, api: normalizedApi });
8875
8829
  }
8876
8830
  } else {
8877
- insData.push(api);
8831
+ insData.push(normalizedApi);
8878
8832
  }
8879
8833
  }
8880
8834
  for (const record of dbLists) {
@@ -8890,7 +8844,8 @@ async function syncApi(ctx, apis) {
8890
8844
  data: {
8891
8845
  name: item.api.name,
8892
8846
  routePath: item.api.routePath,
8893
- addonName: item.api.addonName
8847
+ addonName: item.api.addonName,
8848
+ auth: item.api.auth === 0 || item.api.auth === false ? 0 : 1
8894
8849
  }
8895
8850
  };
8896
8851
  }));
@@ -8904,7 +8859,8 @@ async function syncApi(ctx, apis) {
8904
8859
  return {
8905
8860
  name: api.name,
8906
8861
  routePath: api.routePath,
8907
- addonName: api.addonName
8862
+ addonName: api.addonName,
8863
+ auth: api.auth === 0 || api.auth === false ? 0 : 1
8908
8864
  };
8909
8865
  }));
8910
8866
  } catch (error) {
@@ -12127,7 +12083,6 @@ class XMLParser {
12127
12083
  }
12128
12084
 
12129
12085
  // hooks/parser.ts
12130
- init_util();
12131
12086
  var xmlParser = new XMLParser;
12132
12087
  var parserHook = {
12133
12088
  name: "parser",
@@ -12143,11 +12098,7 @@ var parserHook = {
12143
12098
  if (ctx.req.method === "GET") {
12144
12099
  const url = new URL(ctx.req.url);
12145
12100
  const params = Object.fromEntries(url.searchParams);
12146
- if (isPlainObject(ctx.api.fields) && !isEmpty(ctx.api.fields)) {
12147
- ctx.body = pickFields(params, Object.keys(ctx.api.fields));
12148
- } else {
12149
- ctx.body = params;
12150
- }
12101
+ ctx.body = params;
12151
12102
  } else if (ctx.req.method === "POST") {
12152
12103
  const contentType = ctx.req.headers.get("content-type") || "";
12153
12104
  const url = new URL(ctx.req.url);
@@ -12156,22 +12107,14 @@ var parserHook = {
12156
12107
  if (contentType.includes("application/json")) {
12157
12108
  const body = await ctx.req.json();
12158
12109
  const merged = { ...queryParams, ...body };
12159
- if (isPlainObject(ctx.api.fields) && !isEmpty(ctx.api.fields)) {
12160
- ctx.body = pickFields(merged, Object.keys(ctx.api.fields));
12161
- } else {
12162
- ctx.body = merged;
12163
- }
12110
+ ctx.body = merged;
12164
12111
  } else if (contentType.includes("application/xml") || contentType.includes("text/xml")) {
12165
12112
  const text = await ctx.req.text();
12166
12113
  const parsed = xmlParser.parse(text);
12167
12114
  const rootKey = Object.keys(parsed)[0];
12168
12115
  const body = rootKey && typeof parsed[rootKey] === "object" ? parsed[rootKey] : parsed;
12169
12116
  const merged = { ...queryParams, ...body };
12170
- if (isPlainObject(ctx.api.fields) && !isEmpty(ctx.api.fields)) {
12171
- ctx.body = pickFields(merged, Object.keys(ctx.api.fields));
12172
- } else {
12173
- ctx.body = merged;
12174
- }
12117
+ ctx.body = merged;
12175
12118
  } else {
12176
12119
  ctx.response = ErrorResponse(ctx, "\u65E0\u6548\u7684\u8BF7\u6C42\u53C2\u6570\u683C\u5F0F", 1, null, {
12177
12120
  location: "content-type",
@@ -12326,7 +12269,7 @@ class Validator {
12326
12269
  }
12327
12270
  for (const field of required) {
12328
12271
  const value = data[field];
12329
- if (value === undefined || value === null || value === "") {
12272
+ if (value === undefined || value === null) {
12330
12273
  const label = rules[field]?.name || field;
12331
12274
  fieldErrors[field] = `${label}\u4E3A\u5FC5\u586B\u9879`;
12332
12275
  }
@@ -12499,6 +12442,7 @@ class Validator {
12499
12442
  }
12500
12443
 
12501
12444
  // hooks/validator.ts
12445
+ init_util();
12502
12446
  var validatorHook = {
12503
12447
  name: "validator",
12504
12448
  enable: true,
@@ -12509,10 +12453,25 @@ var validatorHook = {
12509
12453
  if (!ctx.api.fields) {
12510
12454
  return;
12511
12455
  }
12512
- for (const [field, fieldDef] of Object.entries(ctx.api.fields)) {
12513
- if (ctx.body[field] === undefined && fieldDef?.default !== undefined && fieldDef?.default !== null) {
12514
- ctx.body[field] = fieldDef.default;
12456
+ if (isPlainObject(ctx.api.fields)) {
12457
+ const rawBody = isPlainObject(ctx.body) ? ctx.body : {};
12458
+ const nextBody = {};
12459
+ for (const [field, fieldDef] of Object.entries(ctx.api.fields)) {
12460
+ let value = rawBody[field];
12461
+ if (value === undefined) {
12462
+ const snakeField = snakeCase(field);
12463
+ if (rawBody[snakeField] !== undefined) {
12464
+ value = rawBody[snakeField];
12465
+ }
12466
+ }
12467
+ if (value === undefined && fieldDef?.default !== undefined && fieldDef?.default !== null) {
12468
+ value = fieldDef.default;
12469
+ }
12470
+ if (value !== undefined) {
12471
+ nextBody[field] = value;
12472
+ }
12515
12473
  }
12474
+ ctx.body = nextBody;
12516
12475
  }
12517
12476
  const result = Validator.validate(ctx.body, ctx.api.fields, ctx.api.required || []);
12518
12477
  if (result.code !== 0) {
@@ -15120,8 +15079,9 @@ function scanCoreBuiltinHooks() {
15120
15079
 
15121
15080
  // utils/scanFiles.ts
15122
15081
  init_dist();
15123
- import { existsSync as existsSync4 } from "fs";
15082
+ init_importDefault();
15124
15083
  init_util();
15084
+ import { existsSync as existsSync4 } from "fs";
15125
15085
  function parseAddonNameFromPath(normalizedPath) {
15126
15086
  const parts = normalizedPath.split("/").filter(Boolean);
15127
15087
  const idx = parts.indexOf("@befly-addon");