silgi 0.37.52 → 0.38.1

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.
@@ -164,12 +164,6 @@ async function h3Framework(silgi, skip = false) {
164
164
  specifier: "nitropack/types"
165
165
  }
166
166
  ]);
167
- data.events.push({
168
- key: "H3Event",
169
- value: "H3Event",
170
- extends: true,
171
- isSilgiContext: false
172
- });
173
167
  });
174
168
  silgi.hook("prepare:types", (opts) => {
175
169
  addTemplate({
@@ -435,18 +429,18 @@ async function registerModuleExportScan(silgi) {
435
429
  });
436
430
  options.runtimeHooks.push({ key: configKey, value: importName });
437
431
  }
438
- if (hasTypeExport("ModuleRuntimeActions")) {
439
- const importName = hash(`${configKey}ModuleRuntimeActions`);
432
+ if (hasTypeExport("SetupModuleOption")) {
433
+ const importName = hash(`${configKey}SetupModuleOption`);
440
434
  options.addImportItemType({
441
435
  imports: [
442
436
  {
443
437
  as: importName,
444
- name: "ModuleRuntimeActions"
438
+ name: "SetupModuleOption"
445
439
  }
446
440
  ],
447
441
  specifier
448
442
  });
449
- options.actions.push({ key: configKey, value: importName });
443
+ options.setupModuleOption.push({ key: configKey, value: importName });
450
444
  }
451
445
  if (hasTypeExport("ModuleRuntimeMethods")) {
452
446
  const importName = hash(`${configKey}ModuleRuntimeMethods`);
@@ -461,6 +455,19 @@ async function registerModuleExportScan(silgi) {
461
455
  });
462
456
  options.methods.push({ key: configKey, value: importName });
463
457
  }
458
+ if (hasTypeExport("RouteRules")) {
459
+ const importName = hash(`${configKey}RouteRules`);
460
+ options.addImportItemType({
461
+ imports: [
462
+ {
463
+ as: importName,
464
+ name: "RouteRules"
465
+ }
466
+ ],
467
+ specifier
468
+ });
469
+ options.routeRules.push({ key: configKey, value: importName });
470
+ }
464
471
  }
465
472
  });
466
473
  }
@@ -560,7 +567,7 @@ function resolveGroupSyntax(group) {
560
567
  return groups;
561
568
  }
562
569
 
563
- const DEFAULT_FUNCTION_EXPORT_NAMES = ["createSchema", "createService", "createRoute", "createShared"];
570
+ const DEFAULT_FUNCTION_EXPORT_NAMES = ["createSchema", "createService", "createRoute", "createShared", "createMiddleware"];
564
571
  const DEFAULT_INTERFACE_EXTENDS_NAMES = ["ExtendShared", "ExtendContext"];
565
572
  function generateUniqueIdentifier(filePath, exportName) {
566
573
  const fileBaseName = basename(filePath);
@@ -571,7 +578,8 @@ function categorizeExports(exportedEntities, filePath, functionExportCategories
571
578
  createService: "service",
572
579
  createSchema: "schema",
573
580
  createShared: "shared",
574
- createRoute: "route"
581
+ createRoute: "route",
582
+ createMiddleware: "middleware"
575
583
  }, interfaceExportCategories = {
576
584
  ExtendShared: "shared",
577
585
  ExtendContext: "context"
@@ -640,6 +648,9 @@ function registerExportsWithHooks(silgiInstance, runtimeExports, typeExports, pa
640
648
  case "route":
641
649
  options.routers.push(uniqueId);
642
650
  break;
651
+ case "middleware":
652
+ options.middlewares?.push?.(uniqueId);
653
+ break;
643
654
  }
644
655
  options.addImportItem({
645
656
  specifier: transformImportPath(path, packageName, silgiInstance.options.silgi.serverDir),
@@ -740,6 +751,8 @@ async function scanSilgiExports(path, packageName, silgiInstance = useSilgiCLI()
740
751
  functionExportCategories[name] = "shared";
741
752
  else if (name === "createRoute")
742
753
  functionExportCategories[name] = "route";
754
+ else if (name === "createMiddleware")
755
+ functionExportCategories[name] = "middleware";
743
756
  else functionExportCategories[name] = name;
744
757
  });
745
758
  const interfaceExportCategories = {};
@@ -1116,6 +1129,7 @@ async function prepareScanFile(silgi) {
1116
1129
  shareds: [],
1117
1130
  routers: [],
1118
1131
  schemas: [],
1132
+ middlewares: [],
1119
1133
  addImportItem,
1120
1134
  addImportItemType
1121
1135
  };
@@ -1150,7 +1164,8 @@ async function prepareScanFile(silgi) {
1150
1164
  ...generateExport("schemas", scanned.schemas),
1151
1165
  ...generateExport("services", scanned.services),
1152
1166
  ...generateExport("shareds", scanned.shareds, "undefined"),
1153
- ...generateExport("routers", scanned.routers)
1167
+ ...generateExport("routers", scanned.routers),
1168
+ ...generateExport("middlewares", scanned.middlewares)
1154
1169
  ];
1155
1170
  await silgi.callHook("after:scan.ts", importData);
1156
1171
  importData.unshift(...importsContent);
@@ -1420,6 +1435,7 @@ async function createSilgiCLI(config = {}, opts = {}) {
1420
1435
  const silgi = {
1421
1436
  scannedURIs: /* @__PURE__ */ new Map(),
1422
1437
  services: {},
1438
+ middleware: [],
1423
1439
  shareds: {},
1424
1440
  schemas: {},
1425
1441
  unimport: void 0,
@@ -1674,6 +1690,9 @@ async function prepareCoreFile(silgi) {
1674
1690
  },
1675
1691
  {
1676
1692
  name: "schemas"
1693
+ },
1694
+ {
1695
+ name: "middlewares"
1677
1696
  }
1678
1697
  ]
1679
1698
  },
@@ -1763,6 +1782,7 @@ async function prepareCoreFile(silgi) {
1763
1782
  " framework: option?.framework,",
1764
1783
  " shared: shareds,",
1765
1784
  " services: services,",
1785
+ " middlewares: middlewares,",
1766
1786
  " schemas: schemas,",
1767
1787
  ` plugins: [${plugins.join(", ")}],`,
1768
1788
  "",
@@ -1842,13 +1862,14 @@ async function prepareSchema(silgi) {
1842
1862
  addImportItemType,
1843
1863
  options: [],
1844
1864
  contexts: [],
1845
- actions: [],
1865
+ setupModuleOption: [],
1846
1866
  shareds: [],
1847
1867
  events: [],
1848
1868
  hooks: [],
1849
1869
  runtimeHooks: [],
1850
1870
  runtimeOptions: [],
1851
- methods: []
1871
+ methods: [],
1872
+ routeRules: []
1852
1873
  };
1853
1874
  await silgi.callHook("before:schema.ts", data);
1854
1875
  const silgiScanTS = relativeWithDot(silgi.options.build.typesDir, `${silgi.options.silgi.serverDir}/scan`);
@@ -1879,7 +1900,7 @@ async function prepareSchema(silgi) {
1879
1900
  }).join(",\n")}
1880
1901
  }` : "interface SilgiModuleEventsExtends {}",
1881
1902
  "",
1882
- `type RuntimeActionExtends = ${data.actions?.length ? data.actions.map(({ value }) => `${value}`).join(" & ") : "{}"}`,
1903
+ `type SetupModuleOptionExtend = ${data.setupModuleOption?.length ? data.setupModuleOption.map(({ value }) => `${value}`).join(" & ") : "{}"}`,
1883
1904
  "",
1884
1905
  `type RuntimeMethodExtends = ${data.methods?.length ? data.methods.map(({ value }) => `${value}`).join(" & ") : "{}"}`,
1885
1906
  "",
@@ -1889,6 +1910,7 @@ async function prepareSchema(silgi) {
1889
1910
  "",
1890
1911
  `type SilgiRuntimeOptionExtends = ${data.runtimeOptions?.length ? data.runtimeOptions.map(({ value }) => `${value}`).join(" & ") : "{}"}`,
1891
1912
  "",
1913
+ `type RouteRulesExtend = ${data.routeRules?.length ? data.routeRules.map(({ value }) => `${value}`).join(" & ") : "{}"}`,
1892
1914
  silgi.options.typescript.generateRuntimeConfigTypes ? generateTypes(
1893
1915
  await resolveSchema(
1894
1916
  {
@@ -1939,14 +1961,15 @@ async function prepareSchema(silgi) {
1939
1961
  SilgiRuntimeContext: [{}, { extends: ["SilgiModuleContextExtends"] }],
1940
1962
  SilgiEvent: [{}, { extends: ["SilgiModuleEventsExtends"] }],
1941
1963
  SilgiRuntimeSharedsExtend: [{}, { extends: ["SilgiModuleSharedExtends"] }],
1942
- SilgiRuntimeActions: [{}, { extends: ["RuntimeActionExtends"] }],
1964
+ SetupModuleOption: [{}, { extends: ["SetupModuleOptionExtend"] }],
1943
1965
  SilgiRuntimeOptions: [{}, { extends: ["SilgiRuntimeOptionExtends"] }],
1944
1966
  SilgiRuntimeHooks: [{}, { extends: ["SilgiRuntimeHooksExtends"] }],
1945
1967
  SilgiRuntimeConfig: [{}, { extends: ["SilgiRuntimeConfigExtends"] }],
1946
1968
  SilgiHooks: [{}, { extends: ["ModuleHooksExtend"] }],
1947
1969
  SilgiRuntimeMethods: [{}, { extends: ["RuntimeMethodExtends"] }],
1948
1970
  Routers: [{}, { extends: ["RoutersExtend"] }],
1949
- SilgiModuleOptions: [{}, { extends: ["SilgiModuleOptionExtend"] }]
1971
+ SilgiModuleOptions: [{}, { extends: ["SilgiModuleOptionExtend"] }],
1972
+ RouteRules: [{}, { extends: ["RouteRulesExtend"] }]
1950
1973
  }).replace(/,\s*/g, "\n"),
1951
1974
  "",
1952
1975
  "export {}"
@@ -1,7 +1,7 @@
1
1
  #!/usr/bin/env node
2
2
  import { defineCommand, runMain } from 'citty';
3
3
 
4
- const version = "0.37.52";
4
+ const version = "0.38.1";
5
5
  const packageJson = {
6
6
  version: version};
7
7
 
@@ -1,4 +1,4 @@
1
- import { SilgiConfig, Silgi, SilgiEvent, SilgiSchema, CustomRequestInit, SilgiRuntimeContext, AllPrefixes, NamespacesForPrefix, RoutesForPrefixAndNamespace, MethodSchemas, MergeAll, ServiceMethods, SilgiRuntimeShareds, RouteConfig, SilgiURL, StorageConfig, SilgiCLI, SilgiStorageBase, SilgiRuntimeConfig } from 'silgi/types';
1
+ import { SilgiConfig, Silgi, SilgiEvent, SilgiSchema, CustomRequestInit, SilgiRuntimeContext, AllPrefixes, NamespacesForPrefix, RoutesForPrefixAndNamespace, MethodSchemas, MergeAll, MiddlewareDefinition, HttpMethod, ServiceMethods, SilgiRuntimeShareds, RouteConfig, SilgiURL, StorageConfig, SilgiCLI, SilgiStorageBase, SilgiRuntimeConfig } from 'silgi/types';
2
2
  import { Storage, StorageValue } from 'unstorage';
3
3
  import { UseContext } from 'unctx';
4
4
 
@@ -240,6 +240,26 @@ declare function createService<Schema extends SilgiSchema, Path extends keyof Sc
240
240
  [M in keyof Methods]: Methods[M];
241
241
  };
242
242
  };
243
+ type WildcardVariants<Path extends string, Acc extends string = ''> = Path extends `${infer Head}/${infer Tail}` ? Tail extends '' ? `${Acc}${Head}` : `${Acc}${Head}/${Tail}` | `${Acc}${Head}/*` | `${Acc}${Head}/**` | WildcardVariants<Tail, `${Acc}${Head}/`> : `${Acc}${Path}`;
244
+ type MiddlewareParams<Schema extends SilgiSchema, Path extends keyof Schema & string, S extends string = WildcardVariants<Path>, Service extends MiddlewareDefinition = MiddlewareDefinition, Method extends string = HttpMethod, UsedMethod extends readonly Method[] = readonly never[]> = ({
245
+ path: S;
246
+ method?: UsedMethod;
247
+ setup: Service;
248
+ }) | ({
249
+ global: true;
250
+ key: S;
251
+ method?: UsedMethod;
252
+ setup: Service;
253
+ });
254
+ type MiddlewareReturn<S extends string, Service extends MiddlewareDefinition, UsedMethod extends readonly string[]> = {
255
+ [K in S]: {
256
+ method: boolean;
257
+ global: boolean;
258
+ } & (UsedMethod extends readonly [] | undefined ? Service : {
259
+ [M in UsedMethod[number]]: Service;
260
+ }) & (S extends string ? (never extends S ? object : object) : Service) & (Service);
261
+ };
262
+ declare function createMiddleware<Schema extends SilgiSchema, Path extends keyof Schema & string, S extends string = WildcardVariants<Path>, Service extends MiddlewareDefinition = MiddlewareDefinition, Method extends string = HttpMethod, UsedMethod extends readonly Method[] = readonly never[]>(params: MiddlewareParams<Schema, Path, S, Service, Method, UsedMethod>): MiddlewareReturn<S, Service, UsedMethod>;
243
263
 
244
264
  declare function createShared(shared: Partial<SilgiRuntimeShareds>): SilgiRuntimeShareds;
245
265
 
@@ -292,4 +312,4 @@ declare function useRuntime(): SilgiRuntimeConfig;
292
312
 
293
313
  declare const autoImportTypes: string[];
294
314
 
295
- export { SilgiError, autoImportTypes, createError, createRoute, createSchema, createService, createShared, createSilgi, createStorage, deepMergeObjects, getEvent, getEventContext, getUrlPrefix, handleResponse, handler, isError, replaceRuntimeValues, silgiCLICtx, silgiCtx, silgiFetch, storageMount, tryUseSilgi, tryUseSilgiCLI, updateRuntimeStorage, useRuntime, useSilgi, useSilgiCLI, useSilgiStorage };
315
+ export { SilgiError, autoImportTypes, createError, createMiddleware, createRoute, createSchema, createService, createShared, createSilgi, createStorage, deepMergeObjects, getEvent, getEventContext, getUrlPrefix, handleResponse, handler, isError, replaceRuntimeValues, silgiCLICtx, silgiCtx, silgiFetch, storageMount, tryUseSilgi, tryUseSilgiCLI, updateRuntimeStorage, useRuntime, useSilgi, useSilgiCLI, useSilgiStorage };
@@ -1,7 +1,7 @@
1
1
  import { createConsola } from 'consola';
2
2
  import { defu } from 'defu';
3
3
  import { createHooks } from 'hookable';
4
- import { createRouter, addRoute, findRoute } from 'rou3';
4
+ import { createRouter, addRoute, findRoute, findAllRoutes } from 'rou3';
5
5
  import { useRuntimeConfig, sharedRuntimeConfig } from 'silgi/runtime';
6
6
  import { getContext, createContext } from 'unctx';
7
7
  import { Buffer } from 'node:buffer';
@@ -260,9 +260,12 @@ async function createSilgi(config) {
260
260
  const hooks = createHooks();
261
261
  const silgi = {
262
262
  router: void 0,
263
+ _middlewareRouter: void 0,
263
264
  routerPrefixs: [],
264
265
  schemas: config.schemas ?? {},
265
266
  services: config.services ?? {},
267
+ middlewares: config.middlewares ?? {},
268
+ globalMiddlewares: config.globalMiddlewares ?? [],
266
269
  shared: config.shared ?? {},
267
270
  plugins: config.plugins ?? [],
268
271
  framework: config.framework ?? {},
@@ -308,12 +311,50 @@ async function createSilgi(config) {
308
311
  addRoute(silgi.router, _method, route, {
309
312
  method: _method,
310
313
  route,
311
- service: methodObject,
314
+ setup: methodObject,
312
315
  schema: schemaWrapper
313
316
  });
314
317
  }
315
318
  }
316
319
  }
320
+ if (!silgi._middlewareRouter) {
321
+ silgi._middlewareRouter = createRouter();
322
+ }
323
+ for (const route in silgi.middlewares) {
324
+ const routeObject = silgi.middlewares[route];
325
+ if ("global" in routeObject || "method" in routeObject) {
326
+ const global = routeObject.global ?? false;
327
+ const method = routeObject.method ?? false;
328
+ if (global && !method) {
329
+ silgi.globalMiddlewares.push({
330
+ setup: routeObject.setup,
331
+ route
332
+ });
333
+ } else if (method) {
334
+ for (const methodKey in routeObject) {
335
+ if (["global", "setup", "method"].includes(methodKey))
336
+ continue;
337
+ const _method = (methodKey || "").toUpperCase();
338
+ const object = routeObject[methodKey];
339
+ silgi.globalMiddlewares.push({
340
+ setup: object.setup,
341
+ method: _method,
342
+ route
343
+ });
344
+ }
345
+ }
346
+ } else {
347
+ for (const method in routeObject) {
348
+ const _method = (method || "").toUpperCase();
349
+ const routeObjectMethod = routeObject[method];
350
+ addRoute(silgi._middlewareRouter, _method, route, {
351
+ setup: routeObjectMethod.setup,
352
+ method: _method,
353
+ route
354
+ });
355
+ }
356
+ }
357
+ }
317
358
  silgi.hooks.addHooks(silgi.options.hooks);
318
359
  await runSilgiPlugins(silgi);
319
360
  if (!silgi.storage) {
@@ -381,13 +422,32 @@ async function parseRequestInput(req) {
381
422
  const text = await req.text();
382
423
  if (!text)
383
424
  return void 0;
384
- return JSON.parse(text);
425
+ try {
426
+ return JSON.parse(text);
427
+ } catch {
428
+ throw createError({
429
+ statusCode: 400,
430
+ statusMessage: "Invalid JSON",
431
+ data: text
432
+ });
433
+ }
434
+ }
435
+ if (contentType.startsWith("application/x-www-form-urlencoded")) {
436
+ const text = await req.text();
437
+ return Object.fromEntries(new URLSearchParams(text));
385
438
  }
386
439
  if (contentType.startsWith("text/")) {
387
440
  return await req.text();
388
441
  }
389
442
  if (contentType.startsWith("application/octet-stream")) {
390
- return new File([await req.arrayBuffer()], "uploaded.bin", { type: contentType });
443
+ const buffer = await req.arrayBuffer();
444
+ if (typeof File !== "undefined") {
445
+ return new File([buffer], "uploaded.bin", { type: contentType });
446
+ }
447
+ if (typeof Buffer !== "undefined") {
448
+ return Buffer.from(buffer);
449
+ }
450
+ return new Uint8Array(buffer);
391
451
  }
392
452
  return await req.text();
393
453
  }
@@ -534,8 +594,28 @@ function getUrlPrefix(path, method) {
534
594
 
535
595
  async function orchestrate(route, event, _input) {
536
596
  const silgiCtx = useSilgi();
597
+ if (route.method !== event.req.method) {
598
+ throw createError({
599
+ statusCode: 405,
600
+ statusMessage: "Method Not Allowed",
601
+ data: {
602
+ method: event.method,
603
+ expected: route.method,
604
+ route: route.route
605
+ }
606
+ });
607
+ }
608
+ if (!route.route) {
609
+ throw createError({
610
+ statusCode: 500,
611
+ statusMessage: "Route not found",
612
+ data: {
613
+ route
614
+ }
615
+ });
616
+ }
537
617
  const silgiURL = getUrlPrefix(route.route, route.method);
538
- const input = _input || (route.service.routerRule?.readBeforeBody === false ? {} : await parseRequestInput(event.req));
618
+ const input = _input || (route.setup.rules?.readBeforeBody === false ? {} : await parseRequestInput(event.req));
539
619
  const hookContext = { earlyReturnValue: false };
540
620
  const routerParams = _input ? input.path : getRouterParams(event);
541
621
  const queryParams = _input ? input.query : getQuery(event);
@@ -553,7 +633,7 @@ async function orchestrate(route, event, _input) {
553
633
  }
554
634
  };
555
635
  try {
556
- const service = route.service;
636
+ const setup = route.setup;
557
637
  const cachePromise = cacheExecute(input, route, silgiURL, event);
558
638
  const beforeHookPromise = silgiCtx.callHook("fetch:before", {
559
639
  url: silgiURL,
@@ -583,7 +663,7 @@ async function orchestrate(route, event, _input) {
583
663
  }
584
664
  silgiCtx.shared.$fetch = silgiFetch;
585
665
  silgiCtx.shared.silgi = silgiCtx;
586
- const result = await service?.handler(
666
+ const result = await setup?.handler(
587
667
  inputData,
588
668
  silgiCtx.shared,
589
669
  event,
@@ -598,12 +678,12 @@ async function orchestrate(route, event, _input) {
598
678
  route,
599
679
  hookContext
600
680
  });
601
- if (service.storage && cacheData?.cachedKey) {
602
- await useSilgiStorage(service.storage.base).setItem(
681
+ if (setup.storage && cacheData?.cachedKey) {
682
+ await useSilgiStorage(setup.storage.base).setItem(
603
683
  cacheData.cachedKey,
604
684
  result,
605
685
  // Cast to StorageValue if needed
606
- service.storage.options
686
+ setup.storage.options
607
687
  );
608
688
  }
609
689
  return result;
@@ -633,7 +713,7 @@ async function orchestrate(route, event, _input) {
633
713
  }
634
714
  }
635
715
  async function cacheExecute(input, route, silgiURL, event) {
636
- const setup = route.service;
716
+ const setup = route.setup;
637
717
  if (!setup.storage)
638
718
  return;
639
719
  const cacheKey = setup.storage ? await generateStorageKey({
@@ -829,7 +909,7 @@ function withDuplexIfBody(options) {
829
909
  return options;
830
910
  }
831
911
  async function silgiFetch(_request, options, context) {
832
- const silgiCtx = useSilgi();
912
+ useSilgi();
833
913
  let request;
834
914
  if (typeof _request === "string") {
835
915
  _request = substitutePathParams(_request, options?.pathParams);
@@ -845,15 +925,6 @@ async function silgiFetch(_request, options, context) {
845
925
  } else {
846
926
  request = _request;
847
927
  }
848
- const silgiURL = getUrlPrefix(request.url, request.method);
849
- const match = findRoute(silgiCtx.router, request.method, silgiURL.path);
850
- if (!match) {
851
- throw createError({
852
- message: "Route not found",
853
- statusCode: 404,
854
- statusMessage: "Route not found"
855
- });
856
- }
857
928
  const silgiEvent = new _SilgiEvent(request, context);
858
929
  let handlerRes;
859
930
  try {
@@ -863,11 +934,59 @@ async function silgiFetch(_request, options, context) {
863
934
  }
864
935
  return handleResponse(handlerRes, silgiEvent, {});
865
936
  }
937
+ async function middleware(event, url) {
938
+ const silgiContext = useSilgi();
939
+ const pathname = url?.path || event.url.pathname;
940
+ let _chain = void 0;
941
+ const _middleware = silgiContext.globalMiddlewares;
942
+ if (_middleware) {
943
+ _chain = _chain || Promise.resolve();
944
+ for (const m of _middleware) {
945
+ _chain = _chain.then(async (_previous) => {
946
+ if (_previous !== void 0 && _previous !== kNotFound) {
947
+ return _previous;
948
+ }
949
+ if (m.method && m.method !== event.req.method) {
950
+ return;
951
+ }
952
+ if (m.method && m.method !== event.req.method) {
953
+ return;
954
+ }
955
+ await silgiContext.callHook("middleware:global:on", event, m.setup);
956
+ return m.setup.handler(event, silgiContext);
957
+ });
958
+ }
959
+ }
960
+ const _mRouter = silgiContext._middlewareRouter;
961
+ if (_mRouter) {
962
+ const matches = findAllRoutes(_mRouter, event.req.method, pathname);
963
+ if (matches.length > 0) {
964
+ _chain = _chain || Promise.resolve();
965
+ for (const match of matches) {
966
+ _chain = _chain.then(async (_previous) => {
967
+ if (_previous !== void 0 && _previous !== kNotFound) {
968
+ return _previous;
969
+ }
970
+ if (match.data.method && match.data.method !== event.req.method) {
971
+ return;
972
+ }
973
+ event.context.params = match.params;
974
+ event.context.matchedRoute = match.data;
975
+ await silgiContext.callHook("middleware:router:on", event, match.data.setup);
976
+ return match.data.setup.handler(event, silgiContext);
977
+ });
978
+ }
979
+ }
980
+ }
981
+ return _chain;
982
+ }
866
983
  async function handler(event, url, input) {
867
984
  const silgiCtx = useSilgi();
868
985
  const pathname = url?.path || event.url.pathname;
869
986
  let _chain = void 0;
870
987
  _chain = Promise.resolve(await silgiCtx.callHook("request:on", event));
988
+ const data = middleware(event, url);
989
+ _chain = data;
871
990
  if (silgiCtx.router) {
872
991
  const match = findRoute(silgiCtx.router, url?.method || event.req.method, pathname);
873
992
  if (match) {
@@ -940,6 +1059,52 @@ function createService(params) {
940
1059
  [path]: methods
941
1060
  };
942
1061
  }
1062
+ function createMiddleware(params) {
1063
+ if (params.key) {
1064
+ if (!params.method || params.method.length === 0) {
1065
+ return {
1066
+ [params.key]: {
1067
+ method: false,
1068
+ global: params.global,
1069
+ setup: params.setup
1070
+ }
1071
+ };
1072
+ }
1073
+ const result2 = {
1074
+ [params.key]: {
1075
+ global: params.global,
1076
+ method: true
1077
+ }
1078
+ };
1079
+ for (const m of params.method) {
1080
+ result2[params.key][m] = {
1081
+ setup: params.setup,
1082
+ global: true,
1083
+ method: m
1084
+ };
1085
+ }
1086
+ return result2;
1087
+ }
1088
+ if (!params.method || params.method.length === 0) {
1089
+ return {
1090
+ [params.path]: {
1091
+ method: true,
1092
+ global: false,
1093
+ setup: params.setup
1094
+ }
1095
+ };
1096
+ }
1097
+ const result = {
1098
+ [params.path]: {}
1099
+ };
1100
+ for (const m of params.method) {
1101
+ result[params.path][m] = {
1102
+ setup: params.setup,
1103
+ method: m
1104
+ };
1105
+ }
1106
+ return result;
1107
+ }
943
1108
 
944
1109
  function createShared(shared) {
945
1110
  return shared;
@@ -984,4 +1149,4 @@ const autoImportTypes = [
984
1149
  "ExtractQueryParamsFromURI"
985
1150
  ];
986
1151
 
987
- export { SilgiError, autoImportTypes, createError, createRoute, createSchema, createService, createShared, createSilgi, createStorage, deepMergeObjects, getEvent, getEventContext, getUrlPrefix, handleResponse, handler, isError, replaceRuntimeValues, silgiCtx, silgiFetch, storageMount, tryUseSilgi, updateRuntimeStorage, useRuntime, useSilgi, useSilgiStorage };
1152
+ export { SilgiError, autoImportTypes, createError, createMiddleware, createRoute, createSchema, createService, createShared, createSilgi, createStorage, deepMergeObjects, getEvent, getEventContext, getUrlPrefix, handleResponse, handler, isError, replaceRuntimeValues, silgiCtx, silgiFetch, storageMount, tryUseSilgi, updateRuntimeStorage, useRuntime, useSilgi, useSilgiStorage };
package/dist/index.d.mts CHANGED
@@ -1,4 +1,4 @@
1
- export { SilgiError, autoImportTypes, createError, createRoute, createSchema, createService, createShared, createSilgi, createStorage, deepMergeObjects, getEvent, getEventContext, getUrlPrefix, handleResponse, handler, isError, replaceRuntimeValues, silgiCLICtx, silgiCtx, silgiFetch, storageMount, tryUseSilgi, tryUseSilgiCLI, updateRuntimeStorage, useRuntime, useSilgi, useSilgiCLI, useSilgiStorage } from './core/index.mjs';
1
+ export { SilgiError, autoImportTypes, createError, createMiddleware, createRoute, createSchema, createService, createShared, createSilgi, createStorage, deepMergeObjects, getEvent, getEventContext, getUrlPrefix, handleResponse, handler, isError, replaceRuntimeValues, silgiCLICtx, silgiCtx, silgiFetch, storageMount, tryUseSilgi, tryUseSilgiCLI, updateRuntimeStorage, useRuntime, useSilgi, useSilgiCLI, useSilgiStorage } from './core/index.mjs';
2
2
  import 'silgi/types';
3
3
  import 'unstorage';
4
4
  import 'unctx';
package/dist/index.mjs CHANGED
@@ -1,4 +1,4 @@
1
- export { SilgiError, autoImportTypes, createError, createRoute, createSchema, createService, createShared, createSilgi, createStorage, deepMergeObjects, getEvent, getEventContext, getUrlPrefix, handleResponse, handler, isError, replaceRuntimeValues, silgiCtx, silgiFetch, storageMount, tryUseSilgi, updateRuntimeStorage, useRuntime, useSilgi, useSilgiStorage } from './core/index.mjs';
1
+ export { SilgiError, autoImportTypes, createError, createMiddleware, createRoute, createSchema, createService, createShared, createSilgi, createStorage, deepMergeObjects, getEvent, getEventContext, getUrlPrefix, handleResponse, handler, isError, replaceRuntimeValues, silgiCtx, silgiFetch, storageMount, tryUseSilgi, updateRuntimeStorage, useRuntime, useSilgi, useSilgiStorage } from './core/index.mjs';
2
2
  export { s as silgiCLICtx, t as tryUseSilgiCLI, u as useSilgiCLI } from './_chunks/silgiApp.mjs';
3
3
  import 'consola';
4
4
  import 'defu';
@@ -44,7 +44,7 @@ type RequiredServiceType<T> = {
44
44
  [P in keyof T[K]]-?: any;
45
45
  } : never;
46
46
  };
47
- type EventHandlerResponse<T = undefined> = T extends undefined ? void : void | T | Promise<T>;
47
+ type EventHandlerResponse<T = unknown> = T | Promise<T>;
48
48
  type HookResult = Promise<void> | void;
49
49
  interface EnvOptions {
50
50
  prefix?: string;
@@ -280,7 +280,7 @@ interface StorageMounts {
280
280
  interface SilgiStorageBase {
281
281
  }
282
282
  type StorageKeyGenerator<TInput> = (input: TInput) => string | Promise<string>;
283
- interface StorageConfig<TInput> {
283
+ interface StorageConfig<TInput = unknown> {
284
284
  options: TransactionOptions;
285
285
  base: 'memory' | keyof SilgiStorageBase;
286
286
  key?: StorageKeyGenerator<TInput>;
@@ -356,8 +356,8 @@ type ServiceHandler<Schema extends SilgiSchema, Route extends keyof Schema, Meth
356
356
  */
357
357
  interface ServiceSetup<Schema extends SilgiSchema = SilgiSchema, Route extends keyof Schema = keyof Schema, Method extends keyof Schema[Route] = keyof Schema[Route], Resolved extends boolean = false, HiddenParameters extends boolean = false> {
358
358
  handler: ServiceHandler<Schema, Route, Method, Resolved, HiddenParameters>;
359
- routerRule?: RouteConfigService;
360
- modules?: Partial<SilgiRuntimeActions>;
359
+ rules?: RouteConfigService;
360
+ modules?: Partial<SetupModuleOption>;
361
361
  storage?: StorageConfig<ServiceHandlerInput<Schema, Route, Method, HiddenParameters>>;
362
362
  }
363
363
  /**
@@ -371,9 +371,7 @@ interface ResolvedServiceDefinition {
371
371
  [routePath: string]: {
372
372
  [method: string]: {
373
373
  handler: (...args: any[]) => Promise<any>;
374
- modules?: Partial<SilgiRuntimeActions>;
375
- storage?: StorageConfig<any>;
376
- };
374
+ } & Omit<ServiceSetup, 'handler'>;
377
375
  };
378
376
  }
379
377
  /**
@@ -388,6 +386,36 @@ interface SilgiURL {
388
386
  pathParams?: Record<string, string | undefined>;
389
387
  queryParams?: Record<string, string>;
390
388
  }
389
+ interface RouteRules extends Record<string, unknown> {
390
+ }
391
+ type MiddlewareHandler<Response extends EventHandlerResponse = EventHandlerResponse> = (event: SilgiEvent, silgi: Silgi) => Response;
392
+ /**
393
+ * Middleware Setup tipi
394
+ */
395
+ interface MiddlewareSetup {
396
+ handler: MiddlewareHandler;
397
+ rules?: RouteRules;
398
+ modules?: Partial<SetupModuleOption>;
399
+ storage?: StorageConfig;
400
+ }
401
+ type MiddlewareDefinition = MiddlewareSetup;
402
+ type ResolvedMiddlewareDefinition = {
403
+ [routePath: string]: {
404
+ global: boolean;
405
+ method: false;
406
+ setup: MiddlewareSetup;
407
+ };
408
+ } | {
409
+ [routePath: string]: {
410
+ [method: string]: {
411
+ setup: MiddlewareSetup;
412
+ method: string;
413
+ } & {
414
+ global: boolean;
415
+ method: boolean;
416
+ };
417
+ };
418
+ };
391
419
 
392
420
  interface SilgiCLI {
393
421
  _ignore?: Ignore;
@@ -396,6 +424,7 @@ interface SilgiCLI {
396
424
  path?: string;
397
425
  }[];
398
426
  services: ResolvedServiceDefinition;
427
+ middleware: SilgiRoute[];
399
428
  shareds: SilgiRuntimeShareds;
400
429
  schemas: Record<string, any>;
401
430
  scannedURIs: Map<string, string>;
@@ -484,7 +513,7 @@ interface ResolvedSilgiTemplate<Options = TemplateDefaultOptions> extends SilgiT
484
513
  modified?: boolean;
485
514
  }
486
515
 
487
- interface SilgiRuntimeActions {
516
+ interface SetupModuleOption {
488
517
  }
489
518
  interface SilgiModuleOptions {
490
519
  }
@@ -629,6 +658,8 @@ interface SilgiRuntimeHooks {
629
658
  * @returns Promise
630
659
  */
631
660
  'close': (silgi: Silgi) => HookResult;
661
+ 'middleware:global:on': (event: SilgiEvent, setup: MiddlewareSetup) => HookResult;
662
+ 'middleware:router:on': (event: SilgiEvent, setup: MiddlewareSetup) => HookResult;
632
663
  'request:on': (event: SilgiEvent) => HookResult;
633
664
  'fetch:before': (context: ModuleHookContext) => HookResult;
634
665
  'fetch:after': (context: ModuleHookContext) => HookResult;
@@ -673,13 +704,21 @@ type HTTPMethod = SilgiRuntimeMethods extends Record<string, any> ? keyof SilgiR
673
704
  interface SilgiMeta extends Record<string, unknown> {
674
705
  }
675
706
  interface SilgiRoute {
676
- route: string;
677
- method: HTTPMethod;
678
- service: ServiceSetup;
679
- schema: ResolvedSchemaDefinition;
707
+ route?: string;
708
+ method?: HTTPMethod;
709
+ schema?: ResolvedSchemaDefinition;
710
+ setup: ServiceSetup;
711
+ }
712
+ interface MiddlewareRoute {
713
+ route?: string;
714
+ method?: HTTPMethod;
715
+ setup: MiddlewareSetup;
680
716
  }
681
717
  interface Silgi {
682
718
  router: RouterContext<SilgiRoute>;
719
+ _middlewareRouter: RouterContext<MiddlewareRoute>;
720
+ middlewares: ResolvedMiddlewareDefinition;
721
+ globalMiddlewares: MiddlewareRoute[];
683
722
  routerPrefixs: string[];
684
723
  schemas: ResolvedSchemaDefinition;
685
724
  services: ResolvedServiceDefinition;
@@ -810,6 +849,7 @@ interface SilgiCLIHooks extends SilgiHooks {
810
849
  shareds: string[];
811
850
  routers: string[];
812
851
  schemas: string[];
852
+ middlewares: string[];
813
853
  addImportItem: (data: GenImport | GenImport[]) => void;
814
854
  addImportItemType: (data: GenImport | GenImport[]) => void;
815
855
  }) => HookResult;
@@ -833,7 +873,7 @@ interface SilgiCLIHooks extends SilgiHooks {
833
873
  key: string;
834
874
  value: string;
835
875
  }[];
836
- actions: {
876
+ setupModuleOption: {
837
877
  key: string;
838
878
  value: string;
839
879
  }[];
@@ -841,6 +881,10 @@ interface SilgiCLIHooks extends SilgiHooks {
841
881
  key: string;
842
882
  value: string;
843
883
  }[];
884
+ routeRules: {
885
+ key: string;
886
+ value: string;
887
+ }[];
844
888
  events: {
845
889
  key: string;
846
890
  value: string;
@@ -1185,12 +1229,4 @@ interface LoadConfigOptions {
1185
1229
  consola?: ConsolaInstance;
1186
1230
  }
1187
1231
 
1188
- interface GraphQLJSON {
1189
- queries: any;
1190
- mutations: any;
1191
- types: any;
1192
- inputs: any;
1193
- references: any;
1194
- }
1195
-
1196
- export type { AllPaths, AllPrefixes, AppConfig, Awaitable, BuildSilgi, CaptureError, CapturedErrorContext, CommandType, Commands, CustomRequestInit, DeepPartial, DeepRequired, DefaultHooks, DefineFrameworkOptions, DotenvOptions, EnvOptions, EventHandlerResponse, ExtendContext, ExtendShared, ExtractNamespace, ExtractPathParamKeys, ExtractPathParams, ExtractPrefix, ExtractRoute, GenImport, GenerateAppOptions, GraphQLJSON, HTTPMethod, HookResult, HttpMethod, LoadConfigOptions, MergeAll, MergedSilgiSchema, MethodSchemas, ModuleDefinition, ModuleHookContext, ModuleMeta, ModuleOptionsCustom, ModuleSetupInstallResult, ModuleSetupReturn, NamespacesForPrefix, NitroBuildInfo, RequiredServiceType, ResolvedModuleMeta, ResolvedModuleOptions, ResolvedSchema, ResolvedSchemaDefinition, ResolvedServiceDefinition, ResolvedSilgiTemplate, RouteConfig, RouteConfigService, RouterParams, Routers, RoutesForPrefixAndNamespace, ScanFile, Schema, ServiceHandler, ServiceHandlerInput, ServiceHandlerOutput, ServiceHandlerSource, ServiceMethods, ServiceSetup, Silgi, SilgiAppPlugin, SilgiCLI, SilgiCLIConfig, SilgiCLIHooks, SilgiCLIOptions, SilgiCommands, SilgiCompatibility, SilgiCompatibilityIssue, SilgiCompatibilityIssues, SilgiConfig, SilgiEvent, SilgiFetchClient, SilgiFetchOptions, SilgiFrameworkInfo, SilgiHooks, SilgiMeta, SilgiModule, SilgiModuleInput, SilgiModuleOptions, SilgiOptions, SilgiPreset, SilgiPresetMeta, SilgiRoute, SilgiRouterTypes, SilgiRuntimeActions, SilgiRuntimeConfig, SilgiRuntimeContext, SilgiRuntimeDefaultConfig, SilgiRuntimeHooks, SilgiRuntimeMethods, SilgiRuntimeOptions, SilgiRuntimeShareds, SilgiRuntimeSharedsExtend, SilgiSchema, SilgiStorageBase, SilgiTemplate, SilgiURL, StandardHTTPMethod, StorageConfig, StorageKeyGenerator, StorageKeyParams, StorageMounts, TSReference, TrimAfterFourSlashes, WithPathParams };
1232
+ export type { AllPaths, AllPrefixes, AppConfig, Awaitable, BuildSilgi, CaptureError, CapturedErrorContext, CommandType, Commands, CustomRequestInit, DeepPartial, DeepRequired, DefaultHooks, DefineFrameworkOptions, DotenvOptions, EnvOptions, EventHandlerResponse, ExtendContext, ExtendShared, ExtractNamespace, ExtractPathParamKeys, ExtractPathParams, ExtractPrefix, ExtractRoute, GenImport, GenerateAppOptions, HTTPMethod, HookResult, HttpMethod, LoadConfigOptions, MergeAll, MergedSilgiSchema, MethodSchemas, MiddlewareDefinition, MiddlewareHandler, MiddlewareRoute, MiddlewareSetup, ModuleDefinition, ModuleHookContext, ModuleMeta, ModuleOptionsCustom, ModuleSetupInstallResult, ModuleSetupReturn, NamespacesForPrefix, NitroBuildInfo, RequiredServiceType, ResolvedMiddlewareDefinition, ResolvedModuleMeta, ResolvedModuleOptions, ResolvedSchema, ResolvedSchemaDefinition, ResolvedServiceDefinition, ResolvedSilgiTemplate, RouteConfig, RouteConfigService, RouteRules, RouterParams, Routers, RoutesForPrefixAndNamespace, ScanFile, Schema, ServiceHandler, ServiceHandlerInput, ServiceHandlerOutput, ServiceHandlerSource, ServiceMethods, ServiceSetup, SetupModuleOption, Silgi, SilgiAppPlugin, SilgiCLI, SilgiCLIConfig, SilgiCLIHooks, SilgiCLIOptions, SilgiCommands, SilgiCompatibility, SilgiCompatibilityIssue, SilgiCompatibilityIssues, SilgiConfig, SilgiEvent, SilgiFetchClient, SilgiFetchOptions, SilgiFrameworkInfo, SilgiHooks, SilgiMeta, SilgiModule, SilgiModuleInput, SilgiModuleOptions, SilgiOptions, SilgiPreset, SilgiPresetMeta, SilgiRoute, SilgiRouterTypes, SilgiRuntimeConfig, SilgiRuntimeContext, SilgiRuntimeDefaultConfig, SilgiRuntimeHooks, SilgiRuntimeMethods, SilgiRuntimeOptions, SilgiRuntimeShareds, SilgiRuntimeSharedsExtend, SilgiSchema, SilgiStorageBase, SilgiTemplate, SilgiURL, StandardHTTPMethod, StorageConfig, StorageKeyGenerator, StorageKeyParams, StorageMounts, TSReference, TrimAfterFourSlashes, WithPathParams };
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "silgi",
3
3
  "type": "module",
4
- "version": "0.37.52",
4
+ "version": "0.38.1",
5
5
  "private": false,
6
6
  "sideEffects": false,
7
7
  "exports": {