@forinda/kickjs 6.7.0 → 7.0.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/{application-VxxP88FH.mjs → application-Bflo42Wr.mjs} +3 -3
- package/dist/{application-VxxP88FH.mjs.map → application-Bflo42Wr.mjs.map} +1 -1
- package/dist/{bootstrap-F6IShJ1f.mjs → bootstrap-DtlMl3-0.mjs} +3 -3
- package/dist/{bootstrap-F6IShJ1f.mjs.map → bootstrap-DtlMl3-0.mjs.map} +1 -1
- package/dist/config/index.mjs +2 -2
- package/dist/{config-D035b21X.mjs → config-Dx_Nbh79.mjs} +3 -3
- package/dist/{config-D035b21X.mjs.map → config-Dx_Nbh79.mjs.map} +1 -1
- package/dist/{container-CFVAdwXa.mjs → container-BmZciE3k.mjs} +3 -3
- package/dist/{container-CFVAdwXa.mjs.map → container-BmZciE3k.mjs.map} +1 -1
- package/dist/{context-errors-Ce44238b.mjs → context-errors-DDYA51Nf.mjs} +2 -2
- package/dist/{context-errors-Ce44238b.mjs.map → context-errors-DDYA51Nf.mjs.map} +1 -1
- package/dist/{context-CAN3t2jg.mjs → context-vG6HXwHB.mjs} +3 -3
- package/dist/{context-CAN3t2jg.mjs.map → context-vG6HXwHB.mjs.map} +1 -1
- package/dist/core/adapter.mjs +1 -1
- package/dist/core/app-module.mjs +1 -1
- package/dist/core/cache.mjs +1 -1
- package/dist/core/container.mjs +2 -2
- package/dist/core/cron.mjs +2 -2
- package/dist/core/decorators.mjs +2 -2
- package/dist/core/errors.mjs +1 -1
- package/dist/core/interfaces.mjs +1 -1
- package/dist/core/logger.mjs +1 -1
- package/dist/core/path.mjs +1 -1
- package/dist/core/plugin.mjs +1 -1
- package/dist/core/reactivity.mjs +1 -1
- package/dist/{core-DW5uoNhO.mjs → core-kFuUx8FW.mjs} +3 -3
- package/dist/{core-DW5uoNhO.mjs.map → core-kFuUx8FW.mjs.map} +1 -1
- package/dist/{csrf-MbsM7-58.mjs → csrf-Dna2I7cx.mjs} +2 -2
- package/dist/{csrf-MbsM7-58.mjs.map → csrf-Dna2I7cx.mjs.map} +1 -1
- package/dist/define-adapter-D3dAhxuu.mjs +12 -0
- package/dist/define-adapter-D3dAhxuu.mjs.map +1 -0
- package/dist/{disposables-QYOU5_Eg.mjs → disposables-C4BbFv_2.mjs} +2 -2
- package/dist/{disposables-QYOU5_Eg.mjs.map → disposables-C4BbFv_2.mjs.map} +1 -1
- package/dist/{env-DPEhlEC4.mjs → env-C5TMXJ7h.mjs} +3 -3
- package/dist/{env-DPEhlEC4.mjs.map → env-C5TMXJ7h.mjs.map} +1 -1
- package/dist/{handler-DcxBY95X.mjs → handler-BKqb8K_H.mjs} +3 -3
- package/dist/{handler-DcxBY95X.mjs.map → handler-BKqb8K_H.mjs.map} +1 -1
- package/dist/http/application.mjs +2 -2
- package/dist/http/bootstrap.mjs +2 -2
- package/dist/http/context.mjs +2 -2
- package/dist/http/middleware/cors.mjs +1 -1
- package/dist/http/middleware/csrf.mjs +2 -2
- package/dist/http/middleware/error-handler.mjs +2 -2
- package/dist/http/middleware/helmet.mjs +1 -1
- package/dist/http/middleware/rate-limit.mjs +2 -2
- package/dist/http/middleware/request-id.mjs +1 -1
- package/dist/http/middleware/request-logger.mjs +2 -2
- package/dist/http/middleware/session.mjs +2 -2
- package/dist/http/middleware/spa.d.mts +2 -2
- package/dist/http/middleware/spa.mjs +2 -2
- package/dist/http/middleware/spa.mjs.map +1 -1
- package/dist/http/middleware/upload.mjs +2 -2
- package/dist/http/middleware/validate.mjs +1 -1
- package/dist/http/middleware/views.d.mts +1 -1
- package/dist/http/middleware/views.mjs +3 -2
- package/dist/http/middleware/views.mjs.map +1 -0
- package/dist/http/query/index.mjs +2 -2
- package/dist/http/router-builder.mjs +2 -2
- package/dist/http/runtimes/fastify.mjs +2 -2
- package/dist/http/runtimes/h3-web.mjs +2 -2
- package/dist/http/runtimes/h3.mjs +2 -2
- package/dist/index.d.mts +3 -4
- package/dist/index.mjs +2 -2
- package/dist/index.mjs.map +1 -1
- package/dist/{kv-stores-VfJbg9Gs.mjs → kv-stores-zApd2iLD.mjs} +2 -2
- package/dist/{kv-stores-VfJbg9Gs.mjs.map → kv-stores-zApd2iLD.mjs.map} +1 -1
- package/dist/{metadata-DjW8JOQZ.mjs → metadata-Cf6JPQax.mjs} +2 -2
- package/dist/{metadata-DjW8JOQZ.mjs.map → metadata-Cf6JPQax.mjs.map} +1 -1
- package/dist/{module-registry-cbndPnlY.mjs → module-registry-Cpf01UdE.mjs} +2 -2
- package/dist/{module-registry-cbndPnlY.mjs.map → module-registry-Cpf01UdE.mjs.map} +1 -1
- package/dist/{query-B_YnIZ2-.mjs → query-tx53xRSZ.mjs} +2 -2
- package/dist/{query-B_YnIZ2-.mjs.map → query-tx53xRSZ.mjs.map} +1 -1
- package/dist/{reply-Y50qUtDy.mjs → reply-dxkvXqNo.mjs} +3 -3
- package/dist/{reply-Y50qUtDy.mjs.map → reply-dxkvXqNo.mjs.map} +1 -1
- package/dist/{router-builder-DtonR20n.mjs → router-builder-BjLsf6w0.mjs} +3 -3
- package/dist/{router-builder-DtonR20n.mjs.map → router-builder-BjLsf6w0.mjs.map} +1 -1
- package/dist/{views-BBY9_PUV.d.mts → spa-DJbVV_4F.d.mts} +131 -5
- package/dist/spa-DJbVV_4F.d.mts.map +1 -0
- package/dist/{upload-config-Dxr2BxTi.mjs → upload-config-BlmVJI4n.mjs} +2 -2
- package/dist/{upload-config-Dxr2BxTi.mjs.map → upload-config-BlmVJI4n.mjs.map} +1 -1
- package/dist/web.mjs +2 -2
- package/package.json +1 -1
- package/dist/spa-CCi-hC2M.d.mts +0 -97
- package/dist/spa-CCi-hC2M.d.mts.map +0 -1
- package/dist/views-3TYTcdyF.mjs +0 -12
- package/dist/views-3TYTcdyF.mjs.map +0 -1
- package/dist/views-BBY9_PUV.d.mts.map +0 -1
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* @forinda/kickjs
|
|
2
|
+
* @forinda/kickjs v7.0.0
|
|
3
3
|
*
|
|
4
4
|
* Copyright (c) Felix Orinda
|
|
5
5
|
*
|
|
@@ -9,4 +9,4 @@
|
|
|
9
9
|
* @license MIT
|
|
10
10
|
*/
|
|
11
11
|
import{HttpException,HttpStatus}from"./core/errors.mjs";const MIME_MAP={jpg:`image/jpeg`,jpeg:`image/jpeg`,png:`image/png`,gif:`image/gif`,webp:`image/webp`,svg:`image/svg+xml`,bmp:`image/bmp`,ico:`image/x-icon`,tiff:`image/tiff`,tif:`image/tiff`,avif:`image/avif`,pdf:`application/pdf`,doc:`application/msword`,docx:`application/vnd.openxmlformats-officedocument.wordprocessingml.document`,xls:`application/vnd.ms-excel`,xlsx:`application/vnd.openxmlformats-officedocument.spreadsheetml.sheet`,ppt:`application/vnd.ms-powerpoint`,pptx:`application/vnd.openxmlformats-officedocument.presentationml.presentation`,odt:`application/vnd.oasis.opendocument.text`,ods:`application/vnd.oasis.opendocument.spreadsheet`,odp:`application/vnd.oasis.opendocument.presentation`,rtf:`application/rtf`,txt:`text/plain`,csv:`text/csv`,zip:`application/zip`,gz:`application/gzip`,tar:`application/x-tar`,rar:`application/vnd.rar`,"7z":`application/x-7z-compressed`,mp3:`audio/mpeg`,wav:`audio/wav`,ogg:`audio/ogg`,flac:`audio/flac`,aac:`audio/aac`,mp4:`video/mp4`,webm:`video/webm`,avi:`video/x-msvideo`,mov:`video/quicktime`,mkv:`video/x-matroska`,json:`application/json`,xml:`application/xml`,html:`text/html`};function resolveMimeTypes(types){return types.map(t=>{let lower=t.toLowerCase().replace(/^\./,``);return MIME_MAP[lower]??t})}function buildFileTypeFilter(allowedTypes,customMimeMap){if(!allowedTypes)return()=>!0;if(typeof allowedTypes==`function`)return allowedTypes;let mimeMap=customMimeMap?{...MIME_MAP,...customMimeMap}:MIME_MAP,resolved=allowedTypes.map(t=>mimeMap[t.toLowerCase().replace(/^\./,``)]??t);return mimetype=>resolved.some(type=>type.endsWith(`/*`)?mimetype.startsWith(type.replace(`/*`,`/`)):mimetype===type)}function applyUploadConfig(parts,config){if(config.mode===`none`)return{};let field=config.fieldName??`file`,maxSize=config.maxSize??5242880,typeAllowed=buildFileTypeFilter(config.allowedTypes,config.customMimeMap),files=parts.filter(p=>p.fieldname===field).map(p=>{if(!typeAllowed(p.mimetype,p.filename))throw new HttpException(HttpStatus.UNSUPPORTED_MEDIA_TYPE,`File type ${p.mimetype} is not allowed`);if(p.buffer.length>maxSize)throw new HttpException(HttpStatus.PAYLOAD_TOO_LARGE,`File ${p.filename} exceeds the ${maxSize}-byte limit`);return{fieldname:p.fieldname,originalname:p.filename,encoding:`7bit`,mimetype:p.mimetype,size:p.buffer.length,buffer:p.buffer}});if(config.mode===`single`)return{file:files[0]};let maxCount=config.maxCount??10;return{files:files.slice(0,maxCount)}}export{buildFileTypeFilter as n,resolveMimeTypes as r,applyUploadConfig as t};
|
|
12
|
-
//# sourceMappingURL=upload-config-
|
|
12
|
+
//# sourceMappingURL=upload-config-BlmVJI4n.mjs.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"upload-config-
|
|
1
|
+
{"version":3,"file":"upload-config-BlmVJI4n.mjs","names":[],"sources":["../src/http/middleware/upload-config.ts"],"sourcesContent":["// Pure (edge-safe) upload core — the engine-neutral half of the upload\n// middleware. Extracted from `upload.ts` so the `@forinda/kickjs/web` entry\n// graph can validate/shape buffered multipart parts WITHOUT dragging in\n// upload.ts's node-only surface (multer peer loading via `node:module`,\n// disk cleanup via `node:fs/promises`). `upload.ts` re-exports everything\n// here, so existing import sites are unchanged.\n\nimport { HttpException, HttpStatus } from '../../core/errors'\nimport type { BaseUploadOptions, FileUploadConfig } from '../../core/decorators'\n\nexport const MIME_MAP: Record<string, string> = {\n // Images\n jpg: 'image/jpeg',\n jpeg: 'image/jpeg',\n png: 'image/png',\n gif: 'image/gif',\n webp: 'image/webp',\n svg: 'image/svg+xml',\n bmp: 'image/bmp',\n ico: 'image/x-icon',\n tiff: 'image/tiff',\n tif: 'image/tiff',\n avif: 'image/avif',\n // Documents\n pdf: 'application/pdf',\n doc: 'application/msword',\n docx: 'application/vnd.openxmlformats-officedocument.wordprocessingml.document',\n xls: 'application/vnd.ms-excel',\n xlsx: 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet',\n ppt: 'application/vnd.ms-powerpoint',\n pptx: 'application/vnd.openxmlformats-officedocument.presentationml.presentation',\n odt: 'application/vnd.oasis.opendocument.text',\n ods: 'application/vnd.oasis.opendocument.spreadsheet',\n odp: 'application/vnd.oasis.opendocument.presentation',\n rtf: 'application/rtf',\n txt: 'text/plain',\n csv: 'text/csv',\n // Archives\n zip: 'application/zip',\n gz: 'application/gzip',\n tar: 'application/x-tar',\n rar: 'application/vnd.rar',\n '7z': 'application/x-7z-compressed',\n // Audio\n mp3: 'audio/mpeg',\n wav: 'audio/wav',\n ogg: 'audio/ogg',\n flac: 'audio/flac',\n aac: 'audio/aac',\n // Video\n mp4: 'video/mp4',\n webm: 'video/webm',\n avi: 'video/x-msvideo',\n mov: 'video/quicktime',\n mkv: 'video/x-matroska',\n // Other\n json: 'application/json',\n xml: 'application/xml',\n html: 'text/html',\n}\n\n/**\n * Resolves a list of file type identifiers to MIME type strings.\n * Accepts short extensions (`'jpg'`, `'pdf'`) or full MIME types (`'image/jpeg'`).\n *\n * @example\n * ```ts\n * resolveMimeTypes(['jpg', 'png', 'application/pdf'])\n * // → ['image/jpeg', 'image/png', 'application/pdf']\n * ```\n */\nexport function resolveMimeTypes(types: string[]): string[] {\n return types.map((t) => {\n const lower = t.toLowerCase().replace(/^\\./, '')\n return MIME_MAP[lower] ?? t\n })\n}\n\n/**\n * Build a runtime-agnostic `(mimetype, filename) => boolean` file-type filter\n * from `allowedTypes` (a predicate, or a list of extensions / MIME types /\n * wildcards). Returned by both the multer middleware (Express) and the\n * Fastify / h3 / web multipart paths so the accept/reject rule stays\n * identical across engines. No `allowedTypes` → accept everything.\n */\nexport function buildFileTypeFilter(\n allowedTypes: BaseUploadOptions['allowedTypes'],\n customMimeMap?: Record<string, string>,\n): (mimetype: string, filename: string) => boolean {\n if (!allowedTypes) return () => true\n if (typeof allowedTypes === 'function') return allowedTypes\n const mimeMap = customMimeMap ? { ...MIME_MAP, ...customMimeMap } : MIME_MAP\n const resolved = allowedTypes.map((t) => mimeMap[t.toLowerCase().replace(/^\\./, '')] ?? t)\n return (mimetype: string) =>\n resolved.some((type) =>\n type.endsWith('/*') ? mimetype.startsWith(type.replace('/*', '/')) : mimetype === type,\n )\n}\n\n/** A multer-shaped uploaded file — what `ctx.file` / `ctx.files` expose. */\nexport interface UploadedFileLike {\n fieldname: string\n originalname: string\n encoding: string\n mimetype: string\n size: number\n buffer: Buffer\n}\n\n/** A buffered multipart file part, as the runtime hands it to {@link applyUploadConfig}. */\nexport interface RawUploadPart {\n fieldname: string\n filename: string\n mimetype: string\n buffer: Buffer\n}\n\nconst DEFAULT_MAX_SIZE = 5 * 1024 * 1024\n\n/**\n * Apply a `@FileUpload` config to already-buffered multipart parts and return\n * the multer-shaped `file` / `files` for `ctx`. Enforces the field name, type\n * filter, per-file size limit, and (array mode) max count — throwing\n * `HttpException` on a violation, mirroring the Express/multer error path.\n * Used by the Fastify, h3 and web runtimes; Express keeps using multer directly.\n */\nexport function applyUploadConfig(\n parts: RawUploadPart[],\n config: FileUploadConfig,\n): { file?: UploadedFileLike; files?: UploadedFileLike[] } {\n if (config.mode === 'none') return {}\n\n const field = config.fieldName ?? 'file'\n const maxSize = config.maxSize ?? DEFAULT_MAX_SIZE\n const typeAllowed = buildFileTypeFilter(config.allowedTypes, config.customMimeMap)\n\n const matched = parts.filter((p) => p.fieldname === field)\n const files: UploadedFileLike[] = matched.map((p) => {\n if (!typeAllowed(p.mimetype, p.filename)) {\n throw new HttpException(\n HttpStatus.UNSUPPORTED_MEDIA_TYPE,\n `File type ${p.mimetype} is not allowed`,\n )\n }\n if (p.buffer.length > maxSize) {\n throw new HttpException(\n HttpStatus.PAYLOAD_TOO_LARGE,\n `File ${p.filename} exceeds the ${maxSize}-byte limit`,\n )\n }\n return {\n fieldname: p.fieldname,\n originalname: p.filename,\n encoding: '7bit',\n mimetype: p.mimetype,\n size: p.buffer.length,\n buffer: p.buffer,\n }\n })\n\n if (config.mode === 'single') return { file: files[0] }\n const maxCount = config.maxCount ?? 10\n return { files: files.slice(0, maxCount) }\n}\n"],"mappings":";;;;;;;;;;wDAUA,MAAa,SAAmC,CAE9C,IAAK,aACL,KAAM,aACN,IAAK,YACL,IAAK,YACL,KAAM,aACN,IAAK,gBACL,IAAK,YACL,IAAK,eACL,KAAM,aACN,IAAK,aACL,KAAM,aAEN,IAAK,kBACL,IAAK,qBACL,KAAM,0EACN,IAAK,2BACL,KAAM,oEACN,IAAK,gCACL,KAAM,4EACN,IAAK,0CACL,IAAK,iDACL,IAAK,kDACL,IAAK,kBACL,IAAK,aACL,IAAK,WAEL,IAAK,kBACL,GAAI,mBACJ,IAAK,oBACL,IAAK,sBACL,KAAM,8BAEN,IAAK,aACL,IAAK,YACL,IAAK,YACL,KAAM,aACN,IAAK,YAEL,IAAK,YACL,KAAM,aACN,IAAK,kBACL,IAAK,kBACL,IAAK,mBAEL,KAAM,mBACN,IAAK,kBACL,KAAM,WACR,EAYA,SAAgB,iBAAiB,MAA2B,CAC1D,OAAO,MAAM,IAAK,GAAM,CACtB,IAAM,MAAQ,EAAE,YAAY,CAAC,CAAC,QAAQ,MAAO,EAAE,EAC/C,OAAO,SAAS,QAAU,CAC5B,CAAC,CACH,CASA,SAAgB,oBACd,aACA,cACiD,CACjD,GAAI,CAAC,aAAc,UAAa,GAChC,GAAI,OAAO,cAAiB,WAAY,OAAO,aAC/C,IAAM,QAAU,cAAgB,CAAE,GAAG,SAAU,GAAG,aAAc,EAAI,SAC9D,SAAW,aAAa,IAAK,GAAM,QAAQ,EAAE,YAAY,CAAC,CAAC,QAAQ,MAAO,EAAE,IAAM,CAAC,EACzF,MAAQ,WACN,SAAS,KAAM,MACb,KAAK,SAAS,IAAI,EAAI,SAAS,WAAW,KAAK,QAAQ,KAAM,GAAG,CAAC,EAAI,WAAa,IACpF,CACJ,CA6BA,SAAgB,kBACd,MACA,OACyD,CACzD,GAAI,OAAO,OAAS,OAAQ,MAAO,CAAC,EAEpC,IAAM,MAAQ,OAAO,WAAa,OAC5B,QAAU,OAAO,SAAW,QAC5B,YAAc,oBAAoB,OAAO,aAAc,OAAO,aAAa,EAG3E,MADU,MAAM,OAAQ,GAAM,EAAE,YAAc,KACZ,CAAC,CAAC,IAAK,GAAM,CACnD,GAAI,CAAC,YAAY,EAAE,SAAU,EAAE,QAAQ,EACrC,MAAM,IAAI,cACR,WAAW,uBACX,aAAa,EAAE,SAAS,gBAC1B,EAEF,GAAI,EAAE,OAAO,OAAS,QACpB,MAAM,IAAI,cACR,WAAW,kBACX,QAAQ,EAAE,SAAS,eAAe,QAAQ,YAC5C,EAEF,MAAO,CACL,UAAW,EAAE,UACb,aAAc,EAAE,SAChB,SAAU,OACV,SAAU,EAAE,SACZ,KAAM,EAAE,OAAO,OACf,OAAQ,EAAE,MACZ,CACF,CAAC,EAED,GAAI,OAAO,OAAS,SAAU,MAAO,CAAE,KAAM,MAAM,EAAG,EACtD,IAAM,SAAW,OAAO,UAAY,GACpC,MAAO,CAAE,MAAO,MAAM,MAAM,EAAG,QAAQ,CAAE,CAC3C"}
|
package/dist/web.mjs
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* @forinda/kickjs
|
|
2
|
+
* @forinda/kickjs v7.0.0
|
|
3
3
|
*
|
|
4
4
|
* Copyright (c) Felix Orinda
|
|
5
5
|
*
|
|
@@ -8,5 +8,5 @@
|
|
|
8
8
|
*
|
|
9
9
|
* @license MIT
|
|
10
10
|
*/
|
|
11
|
-
import{t as Container}from"./container-
|
|
11
|
+
import{t as Container}from"./container-BmZciE3k.mjs";import{t as MutableModuleRegistry}from"./module-registry-Cpf01UdE.mjs";import{normalizePath}from"./core/path.mjs";import{n as assertRouteUnique,r as buildRouteTable,t as _setExternalContributorSources}from"./router-builder-BjLsf6w0.mjs";import{i as requestStore}from"./context-vG6HXwHB.mjs";import{n as isReply,r as reply}from"./reply-dxkvXqNo.mjs";import{n as KvSessionStore,r as rateLimitGuard,t as KvRateLimitStore}from"./kv-stores-zApd2iLD.mjs";import{n as WebRequestShim,r as WebResponseDriver,t as compileWebRoute}from"./handler-BKqb8K_H.mjs";function createWebApp(options){let h3mod=options.h3;if(typeof h3mod?.H3!=`function`)throw Error(`@forinda/kickjs/web: pass the h3 v2 module — \`createWebApp({ h3: await import("h3"), ... })\`. The installed h3 must be v2 (npm dist-tag 'latest'); v1 has no H3 class.`);let container=Container.getInstance();if(options.env){let env=options.env;Container._envResolver=key=>env[key]}Container._requestStoreProvider=()=>requestStore.getStore()??null;let registry=new MutableModuleRegistry;for(let m of options.modules)registry.mount(m);let modules=registry.entries.map(entry=>{let mod=typeof entry==`function`?new entry:entry;return mod.register?.(container),mod});container.bootstrap();let app=new h3mod.H3,apiPrefix=options.apiPrefix??`/api`,defaultVersion=options.defaultVersion??1,globalMiddleware=options.middleware??[],globalSources=(options.contributors??[]).map(registration=>({source:`global`,registration,label:`createWebApp`})),seenRoutes=new Map;for(let mod of modules){let declaredName=mod.name,moduleLabel=typeof declaredName==`string`&&declaredName.length>0?declaredName:mod.constructor?.name??`module`;_setExternalContributorSources([...(mod.contributors?.()??[]).map(registration=>({source:`module`,registration,label:moduleLabel})),...globalSources]);try{let result=mod.routes();if(!result)continue;let routeSets=Array.isArray(result)?result:[result];for(let route of routeSets){if(!route.controller)throw Error(`@forinda/kickjs/web: module route at '${route.path}' has no controller. Express-style \`router\` mounts are not supported on the web entry.`);let mountPath=`${apiPrefix}/v${route.version??defaultVersion}${normalizePath(route.path)}`;for(let entry of buildRouteTable(route.controller)){let url=joinPath(mountPath,entry.path),owner=`${route.controller.name??`controller`}.${String(entry.meta.handlerName??`?`)}`;assertRouteUnique(seenRoutes,entry.method,url,owner),globalMiddleware.length>0&&(entry.middlewares=[...globalMiddleware,...entry.middlewares]);let run=compileWebRoute(entry);app.on(entry.method,url,event=>run({request:event.req,url:event.url,params:event.context.params??{}}))}}}finally{_setExternalContributorSources([])}}return{fetch:request=>app.fetch(request),h3:app}}function createFetchHandler(build){let app;return{fetch:(request,env={})=>(app??=createWebApp(build(env)),app.fetch(request))}}function joinPath(mountPath,path){let a=mountPath.endsWith(`/`)?mountPath.slice(0,-1):mountPath;return path===`/`||path===``?a===``?`/`:a:`${a}${path.startsWith(`/`)?path:`/${path}`}`}export{KvRateLimitStore,KvSessionStore,WebRequestShim,WebResponseDriver,compileWebRoute,createFetchHandler,createWebApp,isReply,rateLimitGuard,reply};
|
|
12
12
|
//# sourceMappingURL=web.mjs.map
|
package/package.json
CHANGED
package/dist/spa-CCi-hC2M.d.mts
DELETED
|
@@ -1,97 +0,0 @@
|
|
|
1
|
-
|
|
2
|
-
import { r as AppAdapter, t as AdapterContext } from "./adapter-diFqgxGR.mjs";
|
|
3
|
-
//#region src/http/middleware/spa.d.ts
|
|
4
|
-
interface SpaAdapterOptions {
|
|
5
|
-
/**
|
|
6
|
-
* Directory containing the built SPA files (index.html, assets, etc.)
|
|
7
|
-
* Default: 'dist/client'
|
|
8
|
-
*
|
|
9
|
-
* @example
|
|
10
|
-
* ```ts
|
|
11
|
-
* // Vue: 'dist'
|
|
12
|
-
* // React (Vite): 'dist'
|
|
13
|
-
* // React (CRA): 'build'
|
|
14
|
-
* // Svelte: 'build'
|
|
15
|
-
* // Angular: 'dist/my-app/browser'
|
|
16
|
-
* ```
|
|
17
|
-
*/
|
|
18
|
-
clientDir?: string;
|
|
19
|
-
/**
|
|
20
|
-
* URL prefix for API routes. SPA fallback only applies to
|
|
21
|
-
* non-API routes (routes NOT starting with this prefix).
|
|
22
|
-
* Default: '/api'
|
|
23
|
-
*
|
|
24
|
-
* Set to an array for multiple prefixes:
|
|
25
|
-
* ```ts
|
|
26
|
-
* apiPrefix: ['/api', '/graphql', '/_debug']
|
|
27
|
-
* ```
|
|
28
|
-
*/
|
|
29
|
-
apiPrefix?: string | string[];
|
|
30
|
-
/**
|
|
31
|
-
* Additional paths to exclude from SPA fallback.
|
|
32
|
-
* These paths will NOT serve index.html.
|
|
33
|
-
*
|
|
34
|
-
* @example
|
|
35
|
-
* ```ts
|
|
36
|
-
* exclude: ['/health', '/metrics', '/ws']
|
|
37
|
-
* ```
|
|
38
|
-
*/
|
|
39
|
-
exclude?: string[];
|
|
40
|
-
/**
|
|
41
|
-
* Cache-Control header for static assets (default: 'public, max-age=31536000, immutable')
|
|
42
|
-
* Set to false to disable caching headers.
|
|
43
|
-
*/
|
|
44
|
-
cacheControl?: string | false;
|
|
45
|
-
/**
|
|
46
|
-
* Cache-Control for index.html (default: 'no-cache')
|
|
47
|
-
* index.html should not be cached to ensure clients get fresh builds.
|
|
48
|
-
*/
|
|
49
|
-
indexCacheControl?: string;
|
|
50
|
-
}
|
|
51
|
-
/**
|
|
52
|
-
* SPA adapter — serve a Vue, React, Svelte, or Angular build alongside
|
|
53
|
-
* your KickJS API. API routes are handled by controllers; everything else
|
|
54
|
-
* falls back to index.html for client-side routing.
|
|
55
|
-
*
|
|
56
|
-
* @example
|
|
57
|
-
* ```ts
|
|
58
|
-
* import { SpaAdapter } from '@forinda/kickjs/spa'
|
|
59
|
-
*
|
|
60
|
-
* bootstrap({
|
|
61
|
-
* modules,
|
|
62
|
-
* adapters: [
|
|
63
|
-
* new SpaAdapter({
|
|
64
|
-
* clientDir: 'dist/client', // or 'build', 'dist', etc.
|
|
65
|
-
* apiPrefix: '/api',
|
|
66
|
-
* }),
|
|
67
|
-
* ],
|
|
68
|
-
* })
|
|
69
|
-
* ```
|
|
70
|
-
*
|
|
71
|
-
* File structure:
|
|
72
|
-
* ```
|
|
73
|
-
* dist/
|
|
74
|
-
* client/ ← SPA build output
|
|
75
|
-
* index.html
|
|
76
|
-
* assets/
|
|
77
|
-
* app.js
|
|
78
|
-
* style.css
|
|
79
|
-
* server/ ← KickJS server
|
|
80
|
-
* ```
|
|
81
|
-
*/
|
|
82
|
-
declare class SpaAdapter implements AppAdapter {
|
|
83
|
-
private options;
|
|
84
|
-
name: string;
|
|
85
|
-
private clientDir;
|
|
86
|
-
private apiPrefixes;
|
|
87
|
-
private excludePaths;
|
|
88
|
-
private cacheControl;
|
|
89
|
-
private indexCacheControl;
|
|
90
|
-
private indexHtml;
|
|
91
|
-
constructor(options?: SpaAdapterOptions);
|
|
92
|
-
beforeMount({ app }: AdapterContext): void;
|
|
93
|
-
beforeStart({ app }: AdapterContext): void;
|
|
94
|
-
}
|
|
95
|
-
//#endregion
|
|
96
|
-
export { SpaAdapterOptions as n, SpaAdapter as t };
|
|
97
|
-
//# sourceMappingURL=spa-CCi-hC2M.d.mts.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"spa-CCi-hC2M.d.mts","names":[],"sources":["../src/http/middleware/spa.ts"],"mappings":";;;UAMiB;;;;;;;;;;;;;;EAcf;;;;;;;;;;;EAYA;;;;;;;;;;EAWA;;;;;EAMA;;;;;EAMA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;cAkCW,sBAAsB;UASb;EARpB;UACQ;UACA;UACA;UACA;UACA;UACA;EAER,YAAoB,UAAS;EAU7B,cAAc,OAAO;EAyCrB,cAAc,OAAO"}
|
package/dist/views-3TYTcdyF.mjs
DELETED
|
@@ -1,12 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* @forinda/kickjs v6.7.0
|
|
3
|
-
*
|
|
4
|
-
* Copyright (c) Felix Orinda
|
|
5
|
-
*
|
|
6
|
-
* This source code is licensed under the MIT license found in the
|
|
7
|
-
* LICENSE file in the root directory of this source tree.
|
|
8
|
-
*
|
|
9
|
-
* @license MIT
|
|
10
|
-
*/
|
|
11
|
-
import{Logger}from"./core/logger.mjs";import"./core-DW5uoNhO.mjs";import{resolve}from"node:path";const mergeConfig=(defaults={},overrides={})=>({...defaults,...overrides}),composeName=(base,scope)=>`${base}:${scope}`;function defineAdapter(options){let buildSync=(instanceName,scoped,overrides)=>{let config=mergeConfig(options.defaults,overrides),built=options.build(config,{name:instanceName,scoped});return built.name=instanceName,built},buildAsync=(instanceName,opts)=>{let inner;return{name:instanceName,async beforeStart(ctx){let deps=(opts.inject??[]).map(tok=>ctx.container.resolve(tok)),config=await opts.useFactory(...deps);inner=buildSync(instanceName,!1,config),await inner.beforeStart?.(ctx)},async afterStart(ctx){await inner?.afterStart?.(ctx)},async shutdown(){await inner?.shutdown?.()},async onHealthCheck(){return await inner?.onHealthCheck?.()??{name:instanceName,status:`up`}}}},factory=(config=>buildSync(options.name,!1,config));return factory.scoped=(scopeName,config)=>buildSync(composeName(options.name,scopeName),!0,config),factory.async=opts=>buildAsync(options.name,opts),Object.defineProperty(factory,"definition",{value:Object.freeze({...options})}),factory}const log=Logger.for(`ViewEngine`),ViewAdapter=defineAdapter({name:`ViewAdapter`,build:options=>({beforeMount({app}){let{engine,ext,viewsDir=`src/views`}=options;engine.__express?app.engine(ext,engine.__express):typeof engine.renderFile==`function`?app.engine(ext,(path,opts,callback)=>{engine.renderFile(path,opts,callback)}):(typeof engine==`function`||log.warn(`Engine for .${ext} does not have __express or renderFile. Trying as-is.`),app.engine(ext,engine)),app.set(`view engine`,ext),app.set(`views`,resolve(viewsDir)),log.debug(`View engine: ${ext} (${resolve(viewsDir)})`)}})});export{defineAdapter as n,ViewAdapter as t};
|
|
12
|
-
//# sourceMappingURL=views-3TYTcdyF.mjs.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"views-3TYTcdyF.mjs","names":[],"sources":["../src/core/define-adapter.ts","../src/http/middleware/views.ts"],"sourcesContent":["import type { AppAdapter, AdapterContext } from './adapter'\nimport type { BuildContext } from './define-plugin'\n\n/**\n * Options passed to {@link defineAdapter}. Mirrors {@link DefinePluginOptions}\n * exactly — see `architecture.md` §21.3.4 for the definePlugin/defineAdapter\n * symmetry rationale.\n *\n * The optional `TExtra` generic lets an adapter ship public methods\n * beyond the standard {@link AppAdapter} contract — they're preserved\n * on the returned adapter instance so external callers (tests, peer\n * adapters) can invoke them directly. See `OtelAdapter.applyRedaction`\n * for the canonical use case.\n */\nexport interface DefineAdapterOptions<TConfig, TExtra = unknown> {\n /**\n * Stable identity used for logging, `dependsOn` lookups, and `.scoped()`\n * namespacing. Required for adapters that participate in `dependsOn`\n * sort — error messages reference adapters by name.\n */\n name: string\n version?: string\n requires?: { kickjs?: string }\n defaults?: Partial<TConfig>\n build(config: TConfig, ctx: BuildContext): Omit<AppAdapter, 'name'> & TExtra\n}\n\n/**\n * Async-config form of an adapter. Identical shape to `PluginAsyncOptions`\n * but resolved during `beforeStart` (the earliest async hook in\n * `AppAdapter`) — meaning `middleware()` and `contributors()` from the inner\n * adapter are **not** picked up. Use the bare/`.scoped()` form when you need\n * those.\n */\nexport interface AdapterAsyncOptions<TConfig> {\n inject?: ReadonlyArray<unknown>\n useFactory(...deps: any[]): TConfig | Promise<TConfig>\n}\n\n/**\n * Factory returned by {@link defineAdapter}. Same surface as\n * {@link PluginFactory} (call / `.scoped()` / `.async()`) so adopters learn\n * one mental model for both primitives. Returned instances carry both\n * the standard {@link AppAdapter} contract and any `TExtra` extension\n * methods the `build` function exposed.\n */\nexport interface AdapterFactory<TConfig, TExtra = unknown> {\n (config?: Partial<TConfig>): AppAdapter & TExtra\n scoped(scopeName: string, config?: Partial<TConfig>): AppAdapter & TExtra\n async(opts: AdapterAsyncOptions<TConfig>): AppAdapter\n readonly definition: Readonly<DefineAdapterOptions<TConfig, TExtra>>\n}\n\nconst mergeConfig = <TConfig>(\n defaults: Partial<TConfig> = {},\n overrides: Partial<TConfig> = {},\n): TConfig => ({ ...defaults, ...overrides }) as TConfig\n\nconst composeName = (base: string, scope: string): string => `${base}:${scope}`\n\n/**\n * Build an {@link AppAdapter} factory from a typed definition. See\n * `architecture.md` §21.3.4 for migration guidance — most first-party\n * adapter packages collapse to a single `defineAdapter()` call after this\n * lands.\n *\n * @example\n * ```ts\n * const TenantAdapter = defineAdapter<TenantConfig>({\n * name: 'TenantAdapter',\n * defaults: { strategy: 'header', required: true },\n * build: (config) => ({\n * middleware: () => [tenantResolverMiddleware(config)],\n * beforeStart: ({ container }) => registerTenantFactory(container, config),\n * }),\n * })\n *\n * bootstrap({\n * adapters: [\n * TenantAdapter({ strategy: 'subdomain' }),\n * TenantAdapter.scoped('shard-eu', { headerName: 'x-eu-tenant' }),\n * ],\n * })\n * ```\n */\nexport function defineAdapter<TConfig = Record<string, unknown>, TExtra = unknown>(\n options: DefineAdapterOptions<TConfig, TExtra>,\n): AdapterFactory<TConfig, TExtra> {\n const buildSync = (\n instanceName: string,\n scoped: boolean,\n overrides?: Partial<TConfig>,\n ): AppAdapter & TExtra => {\n const config = mergeConfig(options.defaults, overrides)\n // Mutate `name` on the build result instead of spreading — spread\n // strips prototype methods when `build()` returns a class instance.\n // Extension methods declared by the build function (`TExtra`) survive\n // the mutation since they're own properties on the build result.\n const built = options.build(config, { name: instanceName, scoped }) as AppAdapter & TExtra\n ;(built as AppAdapter).name = instanceName\n return built\n }\n\n const buildAsync = (instanceName: string, opts: AdapterAsyncOptions<TConfig>): AppAdapter => {\n let inner: AppAdapter | undefined\n\n return {\n name: instanceName,\n async beforeStart(ctx: AdapterContext) {\n const deps = (opts.inject ?? []).map((tok) => ctx.container.resolve(tok as never))\n const config = await opts.useFactory(...deps)\n inner = buildSync(instanceName, false, config as Partial<TConfig>)\n await inner.beforeStart?.(ctx)\n },\n async afterStart(ctx: AdapterContext) {\n await inner?.afterStart?.(ctx)\n },\n async shutdown() {\n await inner?.shutdown?.()\n },\n async onHealthCheck() {\n return (await inner?.onHealthCheck?.()) ?? { name: instanceName, status: 'up' }\n },\n }\n }\n\n const factory = ((config?: Partial<TConfig>) =>\n buildSync(options.name, false, config)) as AdapterFactory<TConfig, TExtra>\n\n factory.scoped = (scopeName: string, config?: Partial<TConfig>) =>\n buildSync(composeName(options.name, scopeName), true, config)\n\n factory.async = (opts: AdapterAsyncOptions<TConfig>) => buildAsync(options.name, opts)\n\n Object.defineProperty(factory, 'definition', { value: Object.freeze({ ...options }) })\n\n return factory\n}\n","import { resolve } from 'node:path'\nimport { Logger, defineAdapter } from '../../core'\n\nconst log = Logger.for('ViewEngine')\n\nexport interface ViewAdapterOptions {\n /**\n * Template engine — pass the engine module or a render function.\n * Supported engines: ejs, pug, handlebars, nunjucks, or any\n * Express-compatible engine with a __express property.\n *\n * @example\n * ```ts\n * import ejs from 'ejs'\n * ViewAdapter({ engine: ejs, ext: 'ejs' })\n *\n * import pug from 'pug'\n * ViewAdapter({ engine: pug, ext: 'pug' })\n * ```\n */\n engine: any\n\n /** File extension for templates (e.g., 'ejs', 'pug', 'hbs') */\n ext: string\n\n /** Directory containing template files (default: 'src/views') */\n viewsDir?: string\n\n /** Default layout template (optional — depends on engine) */\n layout?: string\n}\n\n/**\n * View/template adapter — pluggable template engine support for KickJS.\n *\n * Registers an Express view engine and sets the views directory.\n * Use `ctx.render()` in controllers to render templates.\n *\n * Migrated to the `defineAdapter()` factory in v4 — call without `new`.\n * The pre-v4 `new ViewAdapter({...})` form is gone; see\n * `docs/guide/migration-v3-to-v4.md` for the rename.\n *\n * @example\n * ```ts\n * import ejs from 'ejs'\n * import { ViewAdapter } from '@forinda/kickjs'\n *\n * bootstrap({\n * modules,\n * adapters: [\n * ViewAdapter({ engine: ejs, ext: 'ejs', viewsDir: 'src/views' }),\n * ],\n * })\n *\n * // In a controller:\n * @Get('/dashboard')\n * async dashboard(ctx: RequestContext) {\n * ctx.render('dashboard', { user: currentUser, title: 'Dashboard' })\n * }\n * ```\n */\nexport const ViewAdapter = defineAdapter<ViewAdapterOptions>({\n name: 'ViewAdapter',\n build: (options) => ({\n beforeMount({ app }) {\n const { engine, ext, viewsDir = 'src/views' } = options\n\n // Register the engine. Three resolution paths cover every\n // mainstream template engine + a fall-through for custom ones.\n if (engine.__express) {\n // EJS, Pug — have __express method\n app.engine(ext, engine.__express)\n } else if (typeof engine.renderFile === 'function') {\n // Engines with renderFile (nunjucks-style)\n app.engine(\n ext,\n (path: string, opts: any, callback: (err: Error | null, html?: string) => void) => {\n engine.renderFile(path, opts, callback)\n },\n )\n } else if (typeof engine === 'function') {\n // Custom render function: (path, options, callback) => void\n app.engine(ext, engine)\n } else {\n log.warn(`Engine for .${ext} does not have __express or renderFile. Trying as-is.`)\n app.engine(ext, engine)\n }\n\n app.set('view engine', ext)\n app.set('views', resolve(viewsDir))\n\n log.debug(`View engine: ${ext} (${resolve(viewsDir)})`)\n },\n }),\n})\n"],"mappings":";;;;;;;;;;iGAqDA,MAAM,aACJ,SAA6B,CAAC,EAC9B,UAA8B,CAAC,KAClB,CAAE,GAAG,SAAU,GAAG,SAAU,GAErC,aAAe,KAAc,QAA0B,GAAG,KAAK,GAAG,QA2BxE,SAAgB,cACd,QACiC,CACjC,IAAM,WACJ,aACA,OACA,YACwB,CACxB,IAAM,OAAS,YAAY,QAAQ,SAAU,SAAS,EAKhD,MAAQ,QAAQ,MAAM,OAAQ,CAAE,KAAM,aAAc,MAAO,CAAC,EAElE,MADC,OAAsB,KAAO,aACvB,KACT,EAEM,YAAc,aAAsB,OAAmD,CAC3F,IAAI,MAEJ,MAAO,CACL,KAAM,aACN,MAAM,YAAY,IAAqB,CACrC,IAAM,MAAQ,KAAK,QAAU,CAAC,EAAA,CAAG,IAAK,KAAQ,IAAI,UAAU,QAAQ,GAAY,CAAC,EAC3E,OAAS,MAAM,KAAK,WAAW,GAAG,IAAI,EAC5C,MAAQ,UAAU,aAAc,GAAO,MAA0B,EACjE,MAAM,MAAM,cAAc,GAAG,CAC/B,EACA,MAAM,WAAW,IAAqB,CACpC,MAAM,OAAO,aAAa,GAAG,CAC/B,EACA,MAAM,UAAW,CACf,MAAM,OAAO,WAAW,CAC1B,EACA,MAAM,eAAgB,CACpB,OAAQ,MAAM,OAAO,gBAAgB,GAAM,CAAE,KAAM,aAAc,OAAQ,IAAK,CAChF,CACF,CACF,EAEM,SAAY,QAChB,UAAU,QAAQ,KAAM,GAAO,MAAM,GASvC,MAPA,SAAQ,QAAU,UAAmB,SACnC,UAAU,YAAY,QAAQ,KAAM,SAAS,EAAG,GAAM,MAAM,EAE9D,QAAQ,MAAS,MAAuC,WAAW,QAAQ,KAAM,IAAI,EAErF,OAAO,eAAe,QAAS,aAAc,CAAE,MAAO,OAAO,OAAO,CAAE,GAAG,OAAQ,CAAC,CAAE,CAAC,EAE9E,OACT,CCtIA,MAAM,IAAM,OAAO,IAAI,YAAY,EA0DtB,YAAc,cAAkC,CAC3D,KAAM,cACN,MAAQ,UAAa,CACnB,YAAY,CAAE,KAAO,CACnB,GAAM,CAAE,OAAQ,IAAK,SAAW,aAAgB,QAI5C,OAAO,UAET,IAAI,OAAO,IAAK,OAAO,SAAS,EACvB,OAAO,OAAO,YAAe,WAEtC,IAAI,OACF,KACC,KAAc,KAAW,WAAyD,CACjF,OAAO,WAAW,KAAM,KAAM,QAAQ,CACxC,CACF,GACS,OAAO,QAAW,YAI3B,IAAI,KAAK,eAAe,IAAI,sDAAsD,EAFlF,IAAI,OAAO,IAAK,MAAM,GAMxB,IAAI,IAAI,cAAe,GAAG,EAC1B,IAAI,IAAI,QAAS,QAAQ,QAAQ,CAAC,EAElC,IAAI,MAAM,gBAAgB,IAAI,IAAI,QAAQ,QAAQ,EAAE,EAAE,CACxD,CACF,EACF,CAAC"}
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"views-BBY9_PUV.d.mts","names":[],"sources":["../src/core/disposables.ts","../src/core/kick-error.ts","../src/core/circuit-breaker.ts","../src/core/context-errors.ts","../src/core/mount-sort.ts","../src/core/asset-keys.ts","../src/http/cluster.ts","../src/http/define-http-context-decorator.ts","../src/http/runtimes/express.ts","../src/http/request-store.ts","../src/http/middleware/request-scope.ts","../src/http/middleware/trace-context.ts","../src/http/middleware/views.ts"],"mappings":"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"}
|