honestjs 0.1.7 → 0.1.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/README.md CHANGED
@@ -61,7 +61,7 @@ ultra-fast performance of Hono, giving you the best of both worlds.
61
61
 
62
62
  > ⚠️ **Documentation is not yet complete** ⚠️
63
63
  >
64
- > If you find any issues or have suggestions for improvements, please open an issue or submit a pull request.
64
+ > If you find any issues or have suggestions for improvements, please open an issue or submit a pull request. See [CONTRIBUTING.md](CONTRIBUTING.md) for how to contribute and [CODE_OF_CONDUCT.md](CODE_OF_CONDUCT.md) for community guidelines.
65
65
 
66
66
  ## Features
67
67
 
@@ -0,0 +1,13 @@
1
+ import type { IApplicationContext } from './interfaces';
2
+ /**
3
+ * Map-backed implementation of the app-level registry.
4
+ * Used by Application so the app (bootstrap, services, any code with `app`) can share pipeline data by key.
5
+ */
6
+ export declare class ApplicationContext implements IApplicationContext {
7
+ private readonly store;
8
+ get<T>(key: string): T | undefined;
9
+ set<T>(key: string, value: T): void;
10
+ has(key: string): boolean;
11
+ delete(key: string): boolean;
12
+ keys(): IterableIterator<string>;
13
+ }
@@ -0,0 +1 @@
1
+ export {};
@@ -1,5 +1,5 @@
1
1
  import { Hono } from 'hono';
2
- import type { HonestOptions, RouteInfo } from './interfaces';
2
+ import type { HonestOptions, IApplicationContext, RouteInfo } from './interfaces';
3
3
  import type { Constructor } from './types';
4
4
  /**
5
5
  * Main application class for the Honest framework
@@ -23,6 +23,7 @@ import type { Constructor } from './types';
23
23
  export declare class Application {
24
24
  private readonly hono;
25
25
  private readonly container;
26
+ private readonly context;
26
27
  private readonly routeManager;
27
28
  private readonly options;
28
29
  /**
@@ -56,6 +57,13 @@ export declare class Application {
56
57
  * @throws {Error} If plugin instantiation fails
57
58
  */
58
59
  private resolvePlugin;
60
+ /**
61
+ * Normalizes a plugin entry to a resolved plugin with pre/post processor arrays.
62
+ * @param entry - Plugin entry (plain plugin or object with plugin and processors)
63
+ * @returns Normalized entry with plugin instance and processor arrays
64
+ * @private
65
+ */
66
+ private normalizePluginEntry;
59
67
  /**
60
68
  * Registers a module with the application
61
69
  * Processes the module's metadata and registers its controllers
@@ -109,6 +117,18 @@ export declare class Application {
109
117
  * ```
110
118
  */
111
119
  getApp(): Hono;
120
+ /**
121
+ * Gets the app-level registry (context) where your app can publish and read pipeline data by key.
122
+ * Use namespaced keys (e.g. 'app.config', 'openapi.spec') and document contracts in your app.
123
+ *
124
+ * @returns The application context instance
125
+ * @example
126
+ * ```ts
127
+ * app.getContext().set('app.config', { env: process.env.NODE_ENV })
128
+ * const config = app.getContext().get<{ env: string }>('app.config')
129
+ * ```
130
+ */
131
+ getContext(): IApplicationContext;
112
132
  /**
113
133
  * Gets information about all registered routes in the application
114
134
  * Useful for documentation and debugging purposes
@@ -0,0 +1 @@
1
+ import 'reflect-metadata';
@@ -0,0 +1 @@
1
+ import 'reflect-metadata';
package/dist/index.d.ts CHANGED
@@ -1,5 +1,6 @@
1
1
  import 'reflect-metadata';
2
2
  export * from './application';
3
+ export * from './application-context';
3
4
  export * from './components';
4
5
  export * from './constants';
5
6
  export * from './decorators';
package/dist/index.js CHANGED
@@ -1,22 +1,22 @@
1
- import"reflect-metadata";import{Hono as o}from"hono";class M{instances=new Map;resolve($,_=new Set){if(this.instances.has($))return this.instances.get($);if(_.has($))throw Error(`Circular dependency detected: ${[..._.keys(),$].map((Q)=>Q.name).join(" -> ")}`);_.add($);let Y=(Reflect.getMetadata("design:paramtypes",$)||[]).map((Q)=>{return this.resolve(Q,new Set(_))}),q=new $(...Y);return this.instances.set($,q),q}register($,_){this.instances.set($,_)}}import{HTTPException as a}from"hono/http-exception";function K($,_,W){let Y=new Date().toISOString(),q=_.get("requestId"),Q=_.req.path;if($ instanceof a)return{response:{status:W?.status||$.status,message:W?.title||$.message,timestamp:Y,path:Q,requestId:q,code:W?.code,details:W?.additionalDetails,...W?.detail&&{detail:W.detail}},status:W?.status||$.status};if($.statusCode||$.status){let z=$.statusCode||$.status,G=W?.status||z;return{response:{status:G,message:W?.title||$.message,timestamp:Y,path:Q,requestId:q,code:W?.code||$.name,details:W?.additionalDetails,...W?.detail&&{detail:W.detail}},status:G}}let J=W?.status||500;return{response:{status:J,message:W?.title||$.message,timestamp:Y,path:Q,requestId:q,code:W?.code||$.name,details:W?.additionalDetails||{stack:$.stack},...W?.detail&&{detail:W.detail}},status:J}}class X{static routes=new Map;static controllers=new Map;static controllerOptions=new Map;static services=new Set;static modules=new Map;static parameters=new Map;static contextIndices=new Map;static global=new Map([["middleware",new Set],["guard",new Set],["pipe",new Set],["filter",new Set]]);static controller=new Map([["middleware",new Map],["guard",new Map],["pipe",new Map],["filter",new Map]]);static handler=new Map([["middleware",new Map],["guard",new Map],["pipe",new Map],["filter",new Map]]);static getRoutes($){return this.routes.get($)||[]}static setRoutes($,_){this.routes.set($,_)}static addRoute($,_){if(!this.routes.has($))this.routes.set($,[]);this.routes.get($).push(_)}static getControllerPath($){return this.controllers.get($)||""}static setControllerPath($,_){this.controllers.set($,_)}static getControllerOptions($){return this.controllerOptions.get($)||{}}static setControllerOptions($,_){this.controllerOptions.set($,_)}static isService($){return this.services.has($)}static addService($){this.services.add($)}static getAllServices(){return this.services}static getModuleOptions($){return this.modules.get($)}static setModuleOptions($,_){this.modules.set($,_)}static getParameters($){return this.parameters.get($)||new Map}static setParameterMap($,_){this.parameters.set($,_)}static getContextIndices($){return this.contextIndices.get($)||new Map}static setContextIndices($,_){this.contextIndices.set($,_)}static registerGlobal($,_){this.global.get($).add(_)}static getGlobal($){return this.global.get($)}static registerController($,_,W){let Y=this.controller.get($);if(!Y.has(_))Y.set(_,[]);Y.get(_).push(W)}static getController($,_){return this.controller.get($).get(_)||[]}static registerHandler($,_,W){let Y=this.handler.get($);if(!Y.has(_))Y.set(_,[]);Y.get(_).push(W)}static getHandler($,_){return this.handler.get($).get(_)||[]}static clear(){this.routes.clear(),this.controllers.clear(),this.controllerOptions.clear(),this.services.clear(),this.modules.clear(),this.parameters.clear(),this.contextIndices.clear();for(let $ of this.global.values())$.clear();for(let $ of this.controller.values())$.clear();for(let $ of this.handler.values())$.clear()}}class S{static routes=[];static registerRoute($){if(!$)throw Error("Route info is required");if(!$.controller)throw Error("Route controller is required");if(!$.handler)throw Error("Route handler is required");if(!$.method)throw Error("Route method is required");if(!$.fullPath)throw Error("Route fullPath is required");this.routes.push($)}static getRoutes(){return this.routes}static getRoutesByController($){return this.routes.filter((_)=>_.controller===$)}static getRoutesByMethod($){return this.routes.filter((_)=>_.method.toUpperCase()===$.toUpperCase())}static getRoutesByPath($){return this.routes.filter((_)=>$.test(_.fullPath))}static clear(){this.routes.length=0}}function b($){return(_="",W={})=>{return(Y,q,Q)=>{let J=Y.constructor;X.addRoute(J,{path:_,method:$,handlerName:q,parameterMetadata:[],version:W.version,prefix:W.prefix})}}}function k($,_){return(W)=>{return(Y,q,Q)=>{let J=Y.constructor;if(!X.getParameters(J).size)X.setParameterMap(J,new Map);let A=X.getParameters(J);if(!A.has(q))A.set(q,[]);let G=Reflect.getMetadata("design:paramtypes",Y,q)?.[Q];if(A.get(q).push({index:Q,name:$,data:W,factory:_,metatype:G}),$==="context"){if(!X.getContextIndices(J).size)X.setContextIndices(J,new Map);X.getContextIndices(J).set(q,Q)}}}}class x{static handle(){return async($,_)=>{let{response:W,status:Y}=K($,_);return _.json(W,Y)}}}class C{static handle(){return async($)=>{return $.json({message:`Not Found - ${$.req.path}`},404)}}}var O$=($)=>typeof $>"u",O=($)=>$===null||typeof $>"u",V=($)=>$!==null&&typeof $==="object",T$=($)=>{if(!V($))return!1;let _=Object.getPrototypeOf($);if(_===null)return!0;let W=Object.prototype.hasOwnProperty.call(_,"constructor")&&_.constructor;return typeof W==="function"&&W instanceof W&&Function.prototype.toString.call(W)===Function.prototype.toString.call(Object)},d=($)=>typeof $==="function",I=($)=>typeof $==="string",S$=($)=>typeof $==="number",N$=($)=>$.length===0,w$=($)=>typeof $==="symbol",P$=($)=>typeof $==="string"?$.charAt(0)!=="/"?"/"+$:$:"",v=($)=>$?$.startsWith("/")?("/"+$.replace(/\/+$/,"")).replace(/\/+/g,"/"):"/"+$.replace(/\/+$/,""):"/",R$=($)=>$.endsWith("/")?$.slice(0,-1):$,c=($)=>{return d($)&&!O($.prototype)&&!d($.prototype)&&Object.getOwnPropertyNames($.prototype).length>1};class Z{static container;static init($){this.container=$}static setupGlobalComponents($){let _=$.components||{};if(_.middleware)this.registerGlobal("middleware",..._.middleware);if(_.guards)this.registerGlobal("guard",..._.guards);if(_.pipes)this.registerGlobal("pipe",..._.pipes);if(_.filters)this.registerGlobal("filter",..._.filters)}static registerGlobal($,..._){_.forEach((W)=>{X.registerGlobal($,W)})}static registerController($,_,...W){W.forEach((Y)=>{X.registerController($,_,Y)})}static registerHandler($,_,W,...Y){let q=`${_.name}:${String(W)}`;Y.forEach((Q)=>{X.registerHandler($,q,Q)})}static getComponents($,_,W){let Y=`${_.name}:${String(W)}`,q=X.getHandler($,Y),Q=X.getController($,_);return[...Array.from(X.getGlobal($)),...Q,...q]}static resolveMiddleware($){return $.map((_)=>{if(V(_)&&"use"in _)return _.use.bind(_);let W=this.container.resolve(_);return W.use.bind(W)})}static getHandlerMiddleware($,_){let W=this.getComponents("middleware",$,_);return this.resolveMiddleware(W)}static getGlobalMiddleware(){let $=Array.from(X.getGlobal("middleware"));return this.resolveMiddleware($)}static resolveGuards($){return $.map((_)=>{if(V(_)&&"canActivate"in _)return _;return this.container.resolve(_)})}static getHandlerGuards($,_){let W=this.getComponents("guard",$,_);return this.resolveGuards(W)}static resolvePipes($){return $.map((_)=>{if(V(_)&&"transform"in _)return _;return this.container.resolve(_)})}static getHandlerPipes($,_){let W=this.getComponents("pipe",$,_);return this.resolvePipes(W)}static async executePipes($,_,W){let Y=$;for(let q of W)Y=await q.transform(Y,_);return Y}static async handleException($,_){let W=_.get("controllerClass"),Y=_.get("handlerName");if(W&&Y){let A=X.getHandler("filter",`${W.name}:${Y}`);if(A.length>0){let z=await this.executeFilters(A,$,_);if(z)return z}}if(W){let A=X.getController("filter",W);if(A.length>0){let z=await this.executeFilters(A,$,_);if(z)return z}}let q=Array.from(X.getGlobal("filter"));if(q.length>0){let A=await this.executeFilters(q,$,_);if(A)return A}let{response:Q,status:J}=K($,_);return _.json(Q,J)}static async executeFilters($,_,W){for(let Y of $){let q;if(V(Y)&&"catch"in Y)q=Y;else q=this.container.resolve(Y);try{let Q=await q.catch(_,W);if(Q!==void 0)return Q}catch(Q){console.error("Error in exception filter:",Q)}}return}static async registerModule($,_){let W=X.getModuleOptions($);if(!W)throw Error(`Module ${$.name} is not properly decorated with @Module()`);let Y=[];if(W.imports&&W.imports.length>0)for(let q of W.imports){let Q=await this.registerModule(q,_);Y.push(...Q)}if(W.services&&W.services.length>0)for(let q of W.services)_.resolve(q);if(W.controllers&&W.controllers.length>0)Y.push(...W.controllers);return Y}}import{HTTPException as r}from"hono/http-exception";var y=Symbol("VERSION_NEUTRAL");class h{hono;container;globalPrefix;globalVersion;constructor($,_,W={}){this.hono=$,this.container=_,this.globalPrefix=W.prefix!==void 0?this.normalizePath(W.prefix):void 0,this.globalVersion=W.version,this.applyGlobalMiddleware()}applyGlobalMiddleware(){let $=Z.getGlobalMiddleware();for(let _ of $)this.hono.use("*",_)}normalizePath($){if(I($))return v($);return $?`/${$}`:""}registerRouteHandler($,_,W,Y){if(W.length>0)this.hono.on($.toUpperCase(),_,...W,Y);else this.hono.on($.toUpperCase(),_,Y)}buildRoutePath($,_,W,Y){return v(`${$}${_}${W}${Y}`)}formatVersionSegment($){if(O($))return"";return $===y?"":`/v${String($)}`}async registerController($){let _=X.getControllerPath($)||"",W=X.getControllerOptions($)||{},Y=X.getRoutes($)||[],q=X.getParameters($)||new Map,Q=X.getContextIndices($)||new Map,J=this.normalizePath(_),A=this.container.resolve($),z=W.prefix!==void 0?W.prefix:this.globalPrefix,G=W.version!==void 0?W.version:this.globalVersion;for(let U of Y){let{path:T,method:E,handlerName:f,version:N,prefix:w}=U,P=w!==void 0?w:z,D=!O(P)?this.normalizePath(P):"",L=N!==void 0?N:G,F=this.normalizePath(T);if(O(L)){this.registerRoute(A,U,q,Q,$,D,"",J,F,E);continue}if(L===y){this.registerRoute(A,U,q,Q,$,D,"",J,F,E),this.registerRoute(A,U,q,Q,$,D,"/:version{v[0-9]+}",J,F,E);continue}if(Array.isArray(L)){for(let H of L){let j=this.formatVersionSegment(H);this.registerRoute(A,U,q,Q,$,D,j,J,F,E)}continue}let R=this.formatVersionSegment(L);this.registerRoute(A,U,q,Q,$,D,R,J,F,E)}}registerRoute($,_,W,Y,q,Q,J,A,z,G){let{handlerName:U}=_,T=this.buildRoutePath(Q,J,A,z),E=$[U].bind($),f=W.get(U)||[],N=Y.get(U),w=Z.getHandlerMiddleware(q,U),P=Z.getHandlerPipes(q,U);S.registerRoute({controller:q.name,handler:U,method:G,prefix:Q,version:J,route:A,path:z,fullPath:T,parameters:f});let D=async(L)=>{try{L.set("controllerClass",q),L.set("handlerName",String(U));let F=Z.getHandlerGuards(q,U);for(let j of F)if(!await j.canActivate(L))throw new r(403,{message:"Forbidden"});let R=Array(E.length);for(let j of f){let m=j.factory(j.data,L),n=await Z.executePipes(m,{type:j.name,metatype:j.metatype,data:j.data},P);R[j.index]=n}let H=await E(...R);if(N!==void 0)return H;if(O(H))return L.json(null);if(I(H))return L.text(H);return L.json(H)}catch(F){return Z.handleException(F,L)}};this.registerRouteHandler(G,T,w,D)}}class i{hono;container;routeManager;options;constructor($={}){this.options=V($)?$:{},this.hono=new o(this.options.hono),this.container=this.options.container||new M,this.setupComponents(),this.setupErrorHandlers(),this.routeManager=new h(this.hono,this.container,{prefix:this.options.routing?.prefix,version:this.options.routing?.version})}setupComponents(){Z.init(this.container),Z.setupGlobalComponents(this.options)}setupErrorHandlers(){this.hono.notFound(this.options.notFound||C.handle()),this.hono.onError(this.options.onError||x.handle())}resolvePlugin($){if(c($))return new $;return $}async register($){let _=await Z.registerModule($,this.container);for(let W of _)await this.routeManager.registerController(W);return this}static async create($,_={}){let W=new i(_),Y=(_.plugins||[]).map((q)=>W.resolvePlugin(q));for(let q of Y)if(q.beforeModulesRegistered)await q.beforeModulesRegistered(W,W.hono);await W.register($);for(let q of Y)if(q.afterModulesRegistered)await q.afterModulesRegistered(W,W.hono);return{app:W,hono:W.getApp()}}getApp(){return this.hono}getRoutes(){return S.getRoutes()}}import{html as B,raw as g}from"hono/html";var t={type:"website",locale:"en_US"},u=($)=>{if(!$)return"";return Object.entries($).map(([_,W])=>{if(typeof W==="boolean")return W?_:"";let Y=String(W).replace(/"/g,"&quot;");return`${_}="${Y}"`}).filter(Boolean).join(" ")},Y_=($)=>{let _={...t,...$};return B`
1
+ import"reflect-metadata";import{Hono as t}from"hono";class M{store=new Map;get($){return this.store.get($)}set($,_){this.store.set($,_)}has($){return this.store.has($)}delete($){return this.store.delete($)}keys(){return this.store.keys()}}class C{instances=new Map;resolve($,_=new Set){if(this.instances.has($))return this.instances.get($);if(_.has($))throw Error(`Circular dependency detected: ${[..._.keys(),$].map((Q)=>Q.name).join(" -> ")}`);_.add($);let Y=(Reflect.getMetadata("design:paramtypes",$)||[]).map((Q)=>{return this.resolve(Q,new Set(_))}),q=new $(...Y);return this.instances.set($,q),q}register($,_){this.instances.set($,_)}}import{HTTPException as r}from"hono/http-exception";function K($,_,W){let Y=new Date().toISOString(),q=_.get("requestId"),Q=_.req.path;if($ instanceof r)return{response:{status:W?.status||$.status,message:W?.title||$.message,timestamp:Y,path:Q,requestId:q,code:W?.code,details:W?.additionalDetails,...W?.detail&&{detail:W.detail}},status:W?.status||$.status};if($.statusCode||$.status){let L=$.statusCode||$.status,E=W?.status||L;return{response:{status:E,message:W?.title||$.message,timestamp:Y,path:Q,requestId:q,code:W?.code||$.name,details:W?.additionalDetails,...W?.detail&&{detail:W.detail}},status:E}}let Z=W?.status||500;return{response:{status:Z,message:W?.title||$.message,timestamp:Y,path:Q,requestId:q,code:W?.code||$.name,details:W?.additionalDetails||{stack:$.stack},...W?.detail&&{detail:W.detail}},status:Z}}class X{static routes=new Map;static controllers=new Map;static controllerOptions=new Map;static services=new Set;static modules=new Map;static parameters=new Map;static contextIndices=new Map;static global=new Map([["middleware",new Set],["guard",new Set],["pipe",new Set],["filter",new Set]]);static controller=new Map([["middleware",new Map],["guard",new Map],["pipe",new Map],["filter",new Map]]);static handler=new Map([["middleware",new Map],["guard",new Map],["pipe",new Map],["filter",new Map]]);static getRoutes($){return this.routes.get($)||[]}static setRoutes($,_){this.routes.set($,_)}static addRoute($,_){if(!this.routes.has($))this.routes.set($,[]);this.routes.get($).push(_)}static getControllerPath($){return this.controllers.get($)||""}static setControllerPath($,_){this.controllers.set($,_)}static getControllerOptions($){return this.controllerOptions.get($)||{}}static setControllerOptions($,_){this.controllerOptions.set($,_)}static isService($){return this.services.has($)}static addService($){this.services.add($)}static getAllServices(){return this.services}static getModuleOptions($){return this.modules.get($)}static setModuleOptions($,_){this.modules.set($,_)}static getParameters($){return this.parameters.get($)||new Map}static setParameterMap($,_){this.parameters.set($,_)}static getContextIndices($){return this.contextIndices.get($)||new Map}static setContextIndices($,_){this.contextIndices.set($,_)}static registerGlobal($,_){this.global.get($).add(_)}static getGlobal($){return this.global.get($)}static registerController($,_,W){let Y=this.controller.get($);if(!Y.has(_))Y.set(_,[]);Y.get(_).push(W)}static getController($,_){return this.controller.get($).get(_)||[]}static registerHandler($,_,W){let Y=this.handler.get($);if(!Y.has(_))Y.set(_,[]);Y.get(_).push(W)}static getHandler($,_){return this.handler.get($).get(_)||[]}static clear(){this.routes.clear(),this.controllers.clear(),this.controllerOptions.clear(),this.services.clear(),this.modules.clear(),this.parameters.clear(),this.contextIndices.clear();for(let $ of this.global.values())$.clear();for(let $ of this.controller.values())$.clear();for(let $ of this.handler.values())$.clear()}}class S{static routes=[];static registerRoute($){if(!$)throw Error("Route info is required");if(!$.controller)throw Error("Route controller is required");if(!$.handler)throw Error("Route handler is required");if(!$.method)throw Error("Route method is required");if(!$.fullPath)throw Error("Route fullPath is required");this.routes.push($)}static getRoutes(){return this.routes}static getRoutesByController($){return this.routes.filter((_)=>_.controller===$)}static getRoutesByMethod($){return this.routes.filter((_)=>_.method.toUpperCase()===$.toUpperCase())}static getRoutesByPath($){return this.routes.filter((_)=>$.test(_.fullPath))}static clear(){this.routes.length=0}}function k($){return(_="",W={})=>{return(Y,q,Q)=>{let Z=Y.constructor;X.addRoute(Z,{path:_,method:$,handlerName:q,parameterMetadata:[],version:W.version,prefix:W.prefix})}}}function G($,_){return(W)=>{return(Y,q,Q)=>{let Z=Y.constructor;if(!X.getParameters(Z).size)X.setParameterMap(Z,new Map);let B=X.getParameters(Z);if(!B.has(q))B.set(q,[]);let E=Reflect.getMetadata("design:paramtypes",Y,q)?.[Q];if(B.get(q).push({index:Q,name:$,data:W,factory:_,metatype:E}),$==="context"){if(!X.getContextIndices(Z).size)X.setContextIndices(Z,new Map);X.getContextIndices(Z).set(q,Q)}}}}class x{static handle(){return async($,_)=>{let{response:W,status:Y}=K($,_);return _.json(W,Y)}}}class I{static handle(){return async($)=>{return $.json({message:`Not Found - ${$.req.path}`},404)}}}var S$=($)=>typeof $>"u",b=($)=>$===null||typeof $>"u",D=($)=>$!==null&&typeof $==="object",N$=($)=>{if(!D($))return!1;let _=Object.getPrototypeOf($);if(_===null)return!0;let W=Object.prototype.hasOwnProperty.call(_,"constructor")&&_.constructor;return typeof W==="function"&&W instanceof W&&Function.prototype.toString.call(W)===Function.prototype.toString.call(Object)},i=($)=>typeof $==="function",v=($)=>typeof $==="string",w$=($)=>typeof $==="number",P$=($)=>$.length===0,R$=($)=>typeof $==="symbol",K$=($)=>typeof $==="string"?$.charAt(0)!=="/"?"/"+$:$:"",y=($)=>$?$.startsWith("/")?("/"+$.replace(/\/+$/,"")).replace(/\/+/g,"/"):"/"+$.replace(/\/+$/,""):"/",f$=($)=>$.endsWith("/")?$.slice(0,-1):$,c=($)=>{return i($)&&!b($.prototype)&&!i($.prototype)&&Object.getOwnPropertyNames($.prototype).length>=1};class J{static container;static init($){this.container=$}static setupGlobalComponents($){let _=$.components||{};if(_.middleware)this.registerGlobal("middleware",..._.middleware);if(_.guards)this.registerGlobal("guard",..._.guards);if(_.pipes)this.registerGlobal("pipe",..._.pipes);if(_.filters)this.registerGlobal("filter",..._.filters)}static registerGlobal($,..._){_.forEach((W)=>{X.registerGlobal($,W)})}static registerController($,_,...W){W.forEach((Y)=>{X.registerController($,_,Y)})}static registerHandler($,_,W,...Y){let q=`${_.name}:${String(W)}`;Y.forEach((Q)=>{X.registerHandler($,q,Q)})}static getComponents($,_,W){let Y=`${_.name}:${String(W)}`,q=X.getHandler($,Y),Q=X.getController($,_);return[...Array.from(X.getGlobal($)),...Q,...q]}static resolveMiddleware($){return $.map((_)=>{if(D(_)&&"use"in _)return _.use.bind(_);let W=this.container.resolve(_);return W.use.bind(W)})}static getHandlerMiddleware($,_){let W=this.getComponents("middleware",$,_);return this.resolveMiddleware(W)}static getGlobalMiddleware(){let $=Array.from(X.getGlobal("middleware"));return this.resolveMiddleware($)}static resolveGuards($){return $.map((_)=>{if(D(_)&&"canActivate"in _)return _;return this.container.resolve(_)})}static getHandlerGuards($,_){let W=this.getComponents("guard",$,_);return this.resolveGuards(W)}static resolvePipes($){return $.map((_)=>{if(D(_)&&"transform"in _)return _;return this.container.resolve(_)})}static getHandlerPipes($,_){let W=this.getComponents("pipe",$,_);return this.resolvePipes(W)}static async executePipes($,_,W){let Y=$;for(let q of W)Y=await q.transform(Y,_);return Y}static async handleException($,_){let W=_.get("controllerClass"),Y=_.get("handlerName");if(W&&Y){let B=X.getHandler("filter",`${W.name}:${Y}`);if(B.length>0){let L=await this.executeFilters(B,$,_);if(L)return L}}if(W){let B=X.getController("filter",W);if(B.length>0){let L=await this.executeFilters(B,$,_);if(L)return L}}let q=Array.from(X.getGlobal("filter"));if(q.length>0){let B=await this.executeFilters(q,$,_);if(B)return B}let{response:Q,status:Z}=K($,_);return _.json(Q,Z)}static async executeFilters($,_,W){for(let Y of $){let q;if(D(Y)&&"catch"in Y)q=Y;else q=this.container.resolve(Y);try{let Q=await q.catch(_,W);if(Q!==void 0)return Q}catch(Q){console.error("Error in exception filter:",Q)}}return}static async registerModule($,_){let W=X.getModuleOptions($);if(!W)throw Error(`Module ${$.name} is not properly decorated with @Module()`);let Y=[];if(W.imports&&W.imports.length>0)for(let q of W.imports){let Q=await this.registerModule(q,_);Y.push(...Q)}if(W.services&&W.services.length>0)for(let q of W.services)_.resolve(q);if(W.controllers&&W.controllers.length>0)Y.push(...W.controllers);return Y}}import{HTTPException as o}from"hono/http-exception";var g=Symbol("VERSION_NEUTRAL");class h{hono;container;globalPrefix;globalVersion;constructor($,_,W={}){this.hono=$,this.container=_,this.globalPrefix=W.prefix!==void 0?this.normalizePath(W.prefix):void 0,this.globalVersion=W.version,this.applyGlobalMiddleware()}applyGlobalMiddleware(){let $=J.getGlobalMiddleware();for(let _ of $)this.hono.use("*",_)}normalizePath($){if(v($))return y($);return $?`/${$}`:""}registerRouteHandler($,_,W,Y){if(W.length>0)this.hono.on($.toUpperCase(),_,...W,Y);else this.hono.on($.toUpperCase(),_,Y)}buildRoutePath($,_,W,Y){return y(`${$}${_}${W}${Y}`)}formatVersionSegment($){if(b($))return"";return $===g?"":`/v${String($)}`}async registerController($){let _=X.getControllerPath($)||"",W=X.getControllerOptions($)||{},Y=X.getRoutes($)||[],q=X.getParameters($)||new Map,Q=X.getContextIndices($)||new Map,Z=this.normalizePath(_),B=this.container.resolve($),L=W.prefix!==void 0?W.prefix:this.globalPrefix,E=W.version!==void 0?W.version:this.globalVersion;for(let A of Y){let{path:T,method:V,handlerName:f,version:N,prefix:w}=A,P=w!==void 0?w:L,H=!b(P)?this.normalizePath(P):"",U=N!==void 0?N:E,j=this.normalizePath(T);if(b(U)){this.registerRoute(B,A,q,Q,$,H,"",Z,j,V);continue}if(U===g){this.registerRoute(B,A,q,Q,$,H,"",Z,j,V),this.registerRoute(B,A,q,Q,$,H,"/:version{v[0-9]+}",Z,j,V);continue}if(Array.isArray(U)){for(let O of U){let F=this.formatVersionSegment(O);this.registerRoute(B,A,q,Q,$,H,F,Z,j,V)}continue}let R=this.formatVersionSegment(U);this.registerRoute(B,A,q,Q,$,H,R,Z,j,V)}}registerRoute($,_,W,Y,q,Q,Z,B,L,E){let{handlerName:A}=_,T=this.buildRoutePath(Q,Z,B,L),V=$[A].bind($),f=W.get(A)||[],N=Y.get(A),w=J.getHandlerMiddleware(q,A),P=J.getHandlerPipes(q,A);S.registerRoute({controller:q.name,handler:A,method:E,prefix:Q,version:Z,route:B,path:L,fullPath:T,parameters:f});let H=async(U)=>{try{U.set("controllerClass",q),U.set("handlerName",String(A));let j=J.getHandlerGuards(q,A);for(let F of j)if(!await F.canActivate(U))throw new o(403,{message:"Forbidden"});let R=Array(V.length);for(let F of f){let d=F.factory(F.data,U),a=await J.executePipes(d,{type:F.name,metatype:F.metatype,data:F.data},P);R[F.index]=a}let O=await V(...R);if(N!==void 0)return O;if(b(O))return U.json(null);if(v(O))return U.text(O);return U.json(O)}catch(j){return J.handleException(j,U)}};this.registerRouteHandler(E,T,w,H)}}class p{hono;container;context;routeManager;options;constructor($={}){this.options=D($)?$:{},this.hono=new t(this.options.hono),this.container=this.options.container||new C,this.context=new M,this.setupComponents(),this.setupErrorHandlers(),this.routeManager=new h(this.hono,this.container,{prefix:this.options.routing?.prefix,version:this.options.routing?.version})}setupComponents(){J.init(this.container),J.setupGlobalComponents(this.options)}setupErrorHandlers(){this.hono.notFound(this.options.notFound||I.handle()),this.hono.onError(this.options.onError||x.handle())}resolvePlugin($){if(c($))return new $;return $}normalizePluginEntry($){if($&&typeof $==="object"&&"plugin"in $){let _=$;return{plugin:this.resolvePlugin(_.plugin),preProcessors:_.preProcessors??[],postProcessors:_.postProcessors??[]}}return{plugin:this.resolvePlugin($),preProcessors:[],postProcessors:[]}}async register($){let _=await J.registerModule($,this.container);for(let W of _)await this.routeManager.registerController(W);return this}static async create($,_={}){let W=new p(_),Y=(_.plugins||[]).map((Q)=>W.normalizePluginEntry(Q)),q=W.getContext();for(let{plugin:Q,preProcessors:Z}of Y){for(let B of Z)await B(W,W.hono,q);if(Q.beforeModulesRegistered)await Q.beforeModulesRegistered(W,W.hono)}await W.register($);for(let{plugin:Q,postProcessors:Z}of Y){if(Q.afterModulesRegistered)await Q.afterModulesRegistered(W,W.hono);for(let B of Z)await B(W,W.hono,q)}return{app:W,hono:W.getApp()}}getApp(){return this.hono}getContext(){return this.context}getRoutes(){return S.getRoutes()}}import{html as z,raw as u}from"hono/html";var e={type:"website",locale:"en_US"},m=($)=>{if(!$)return"";return Object.entries($).map(([_,W])=>{if(typeof W==="boolean")return W?_:"";let Y=String(W).replace(/"/g,"&quot;");return`${_}="${Y}"`}).filter(Boolean).join(" ")},X_=($)=>{let _={...e,...$};return z`
2
2
  <!DOCTYPE html>
3
- <html lang="${_.locale?.split("_")[0]||"en"}" ${g(u(_.htmlAttributes))}>
4
- <head ${g(u(_.headAttributes))}>
3
+ <html lang="${_.locale?.split("_")[0]||"en"}" ${u(m(_.htmlAttributes))}>
4
+ <head ${u(m(_.headAttributes))}>
5
5
  <meta charset="UTF-8" />
6
6
  <meta name="viewport" content="width=device-width, initial-scale=1.0" />
7
- ${_.csp?B`<meta http-equiv="Content-Security-Policy" content="${_.csp}" />`:""}
7
+ ${_.csp?z`<meta http-equiv="Content-Security-Policy" content="${_.csp}" />`:""}
8
8
  <title>${_.title}</title>
9
- ${_.description?B`<meta name="description" content="${_.description}" />`:""}
9
+ ${_.description?z`<meta name="description" content="${_.description}" />`:""}
10
10
 
11
11
  <!-- Open Graph / Facebook -->
12
12
  <meta prefix="og: http://ogp.me/ns#" />
13
13
  <meta property="og:title" content="${_.title}" />
14
- ${_.description?B`<meta property="og:description" content="${_.description}" />`:""}
15
- ${_.image?B`<meta property="og:image" content="${_.image}" />`:""}
16
- ${_.url?B`<meta property="og:url" content="${_.url}" />`:""}
17
- ${_.locale?B`<meta property="og:locale" content="${_.locale}" />`:""}
18
- ${_.type?B`<meta property="og:type" content="${_.type}" />`:""}
19
- ${_.siteName?B`<meta property="og:site_name" content="${_.siteName}" />`:""}
14
+ ${_.description?z`<meta property="og:description" content="${_.description}" />`:""}
15
+ ${_.image?z`<meta property="og:image" content="${_.image}" />`:""}
16
+ ${_.url?z`<meta property="og:url" content="${_.url}" />`:""}
17
+ ${_.locale?z`<meta property="og:locale" content="${_.locale}" />`:""}
18
+ ${_.type?z`<meta property="og:type" content="${_.type}" />`:""}
19
+ ${_.siteName?z`<meta property="og:site_name" content="${_.siteName}" />`:""}
20
20
 
21
21
  <!-- Twitter -->
22
22
  <meta
@@ -24,23 +24,23 @@ import"reflect-metadata";import{Hono as o}from"hono";class M{instances=new Map;r
24
24
  content="${_.twitterCard||(_.image?"summary_large_image":"summary")}"
25
25
  />
26
26
  <meta name="twitter:title" content="${_.title}" />
27
- ${_.description?B`<meta name="twitter:description" content="${_.description}" />`:""}
28
- ${_.image?B`<meta name="twitter:image" content="${_.image}" />`:""}
27
+ ${_.description?z`<meta name="twitter:description" content="${_.description}" />`:""}
28
+ ${_.image?z`<meta name="twitter:image" content="${_.image}" />`:""}
29
29
 
30
30
  <!-- Custom Meta Tags -->
31
- ${_.customMeta?_.customMeta.map((W)=>{let Y=W.name?`name="${W.name}"`:"",q=W.property?`property="${W.property}"`:"";return B`<meta ${Y} ${q} content="${W.content}" />`}):""}
31
+ ${_.customMeta?_.customMeta.map((W)=>{let Y=W.name?`name="${W.name}"`:"",q=W.property?`property="${W.property}"`:"";return z`<meta ${Y} ${q} content="${W.content}" />`}):""}
32
32
 
33
33
  <!-- Favicon -->
34
- ${_.favicon?B`<link rel="icon" href="${_.favicon}" />`:""}
34
+ ${_.favicon?z`<link rel="icon" href="${_.favicon}" />`:""}
35
35
 
36
36
  <!-- Stylesheets -->
37
- ${_.stylesheets?_.stylesheets.map((W)=>B`<link rel="stylesheet" href="${W}" />`):""}
37
+ ${_.stylesheets?_.stylesheets.map((W)=>z`<link rel="stylesheet" href="${W}" />`):""}
38
38
 
39
39
  <!-- Scripts -->
40
- ${_.scripts?_.scripts.map((W)=>{if(typeof W==="string")return B`<script src="${W}"></script>`;let{src:Y,async:q,defer:Q}=W;if(q&&Q)return B`<script src="${Y}" async defer></script>`;if(q)return B`<script src="${Y}" async></script>`;if(Q)return B`<script src="${Y}" defer></script>`;return B`<script src="${Y}"></script>`}):""}
40
+ ${_.scripts?_.scripts.map((W)=>{if(typeof W==="string")return z`<script src="${W}"></script>`;let{src:Y,async:q,defer:Q}=W;if(q&&Q)return z`<script src="${Y}" async defer></script>`;if(q)return z`<script src="${Y}" async></script>`;if(Q)return z`<script src="${Y}" defer></script>`;return z`<script src="${Y}"></script>`}):""}
41
41
  </head>
42
- <body ${g(u(_.bodyAttributes))}>
42
+ <body ${u(m(_.bodyAttributes))}>
43
43
  ${_.children}
44
44
  </body>
45
45
  </html>
46
- `};function p($="",_={}){return(W)=>{X.setControllerPath(W,$),X.setControllerOptions(W,_)}}var s=b("get"),B_=b("post"),U_=b("put"),z_=b("delete"),L_=b("patch"),k_=b("options"),j_=b("all");function l($={}){return(_)=>{X.setModuleOptions(_,$)}}function H_($="",_={prefix:null,version:null}){return p($,_)}var O_=s;function T_($={}){return l({imports:$.imports,services:$.services,controllers:($.views||[]).concat($.controllers||[])})}var w_=k("body",async($,_)=>{let W=await _.req.json();return $?W[$]:W}),P_=k("param",($,_)=>{return $?_.req.param($):_.req.param()}),R_=k("query",($,_)=>{return $?_.req.query($):_.req.query()}),K_=k("header",($,_)=>{return $?_.req.header($):_.req.header()}),f_=k("request",($,_)=>_.req),M_=k("request",($,_)=>_.req),x_=k("response",($,_)=>_.res),C_=k("response",($,_)=>_.res),I_=k("context",($,_)=>_),v_=k("context",($,_)=>_),y_=k("variable",($,_)=>_.get($)),h_=k("variable",($,_)=>_.get($));function m_(){return($)=>{X.addService($)}}function i_($,..._){return(W,Y)=>{if(Y){let q=W.constructor;Z.registerHandler($,q,Y,..._)}else Z.registerController($,W,..._)}}function l_(...$){return(_,W)=>{if(W){let Y=_.constructor;Z.registerHandler("filter",Y,W,...$)}else Z.registerController("filter",_,...$)}}function r_(...$){return(_,W)=>{if(W){let Y=_.constructor;Z.registerHandler("guard",Y,W,...$)}else Z.registerController("guard",_,...$)}}function e_(...$){return(_,W)=>{if(W){let Y=_.constructor;Z.registerHandler("middleware",Y,W,...$)}else Z.registerController("middleware",_,...$)}}function WW(...$){return(_,W)=>{if(W){let Y=_.constructor;Z.registerHandler("pipe",Y,W,...$)}else Z.registerController("pipe",_,...$)}}export{R$ as stripEndSlash,v as normalizePath,O$ as isUndefined,w$ as isSymbol,I as isString,T$ as isPlainObject,V as isObject,S$ as isNumber,O as isNil,d as isFunction,N$ as isEmpty,c as isConstructor,k as createParamDecorator,b as createHttpMethodDecorator,K as createErrorResponse,P$ as addLeadingSlash,H_ as View,h_ as Variable,y_ as Var,y as VERSION_NEUTRAL,WW as UsePipes,e_ as UseMiddleware,r_ as UseGuards,l_ as UseFilters,i_ as UseComponent,m_ as Service,S as RouteRegistry,h as RouteManager,C_ as Response,x_ as Res,M_ as Request,f_ as Req,R_ as Query,U_ as Put,B_ as Post,L_ as Patch,P_ as Param,O_ as Page,k_ as Options,C as NotFoundHandler,T_ as MvcModule,l as Module,X as MetadataRegistry,Y_ as Layout,K_ as Header,s as Get,x as ErrorHandler,z_ as Delete,I_ as Ctx,p as Controller,v_ as Context,M as Container,Z as ComponentManager,w_ as Body,i as Application,j_ as All};
46
+ `};function s($="",_={}){return(W)=>{X.setControllerPath(W,$),X.setControllerOptions(W,_)}}var l=k("get"),U_=k("post"),G_=k("put"),F_=k("delete"),E_=k("patch"),j_=k("options"),V_=k("all");function n($={}){return(_)=>{X.setModuleOptions(_,$)}}function S_($="",_={prefix:null,version:null}){return s($,_)}var N_=l;function w_($={}){return n({imports:$.imports,services:$.services,controllers:($.views||[]).concat($.controllers||[])})}var K_=G("body",async($,_)=>{let W=await _.req.json();return $?W[$]:W}),f_=G("param",($,_)=>{return $?_.req.param($):_.req.param()}),M_=G("query",($,_)=>{return $?_.req.query($):_.req.query()}),C_=G("header",($,_)=>{return $?_.req.header($):_.req.header()}),x_=G("request",($,_)=>_.req),I_=G("request",($,_)=>_.req),v_=G("response",($,_)=>_.res),y_=G("response",($,_)=>_.res),g_=G("context",($,_)=>_),h_=G("context",($,_)=>_),u_=G("variable",($,_)=>_.get($)),m_=G("variable",($,_)=>_.get($));function c_(){return($)=>{X.addService($)}}function l_($,..._){return(W,Y)=>{if(Y){let q=W.constructor;J.registerHandler($,q,Y,..._)}else J.registerController($,W,..._)}}function r_(...$){return(_,W)=>{if(W){let Y=_.constructor;J.registerHandler("filter",Y,W,...$)}else J.registerController("filter",_,...$)}}function e_(...$){return(_,W)=>{if(W){let Y=_.constructor;J.registerHandler("guard",Y,W,...$)}else J.registerController("guard",_,...$)}}function WW(...$){return(_,W)=>{if(W){let Y=_.constructor;J.registerHandler("middleware",Y,W,...$)}else J.registerController("middleware",_,...$)}}function QW(...$){return(_,W)=>{if(W){let Y=_.constructor;J.registerHandler("pipe",Y,W,...$)}else J.registerController("pipe",_,...$)}}export{f$ as stripEndSlash,y as normalizePath,S$ as isUndefined,R$ as isSymbol,v as isString,N$ as isPlainObject,D as isObject,w$ as isNumber,b as isNil,i as isFunction,P$ as isEmpty,c as isConstructor,G as createParamDecorator,k as createHttpMethodDecorator,K as createErrorResponse,K$ as addLeadingSlash,S_ as View,m_ as Variable,u_ as Var,g as VERSION_NEUTRAL,QW as UsePipes,WW as UseMiddleware,e_ as UseGuards,r_ as UseFilters,l_ as UseComponent,c_ as Service,S as RouteRegistry,h as RouteManager,y_ as Response,v_ as Res,I_ as Request,x_ as Req,M_ as Query,G_ as Put,U_ as Post,E_ as Patch,f_ as Param,N_ as Page,j_ as Options,I as NotFoundHandler,w_ as MvcModule,n as Module,X as MetadataRegistry,X_ as Layout,C_ as Header,l as Get,x as ErrorHandler,F_ as Delete,g_ as Ctx,s as Controller,h_ as Context,C as Container,J as ComponentManager,K_ as Body,M as ApplicationContext,p as Application,V_ as All};
@@ -0,0 +1,35 @@
1
+ /**
2
+ * App-level registry where your application can publish and read pipeline data by key.
3
+ * Available to bootstrap code, services, and any code with access to `app`.
4
+ * Enables composition without hard coupling: producers and consumers use namespaced keys.
5
+ */
6
+ export interface IApplicationContext {
7
+ /**
8
+ * Get a value by key. Caller provides type for type safety.
9
+ * @param key - Namespaced registry key (e.g. 'app.config', 'openapi.spec')
10
+ * @returns The value or undefined if not set
11
+ */
12
+ get<T>(key: string): T | undefined;
13
+ /**
14
+ * Set a value by key.
15
+ * @param key - Namespaced registry key
16
+ * @param value - Value to store
17
+ */
18
+ set<T>(key: string, value: T): void;
19
+ /**
20
+ * Check if a key is present.
21
+ * @param key - Registry key
22
+ * @returns true if the key exists
23
+ */
24
+ has(key: string): boolean;
25
+ /**
26
+ * Remove a key and its value.
27
+ * @param key - Registry key
28
+ * @returns true if the key existed and was removed
29
+ */
30
+ delete(key: string): boolean;
31
+ /**
32
+ * Iterate over all registered keys.
33
+ */
34
+ keys(): IterableIterator<string>;
35
+ }
@@ -1,6 +1,6 @@
1
1
  import type { Context } from 'hono';
2
2
  import type { VERSION_NEUTRAL } from '../constants';
3
- import type { FilterType, GuardType, MiddlewareType, PipeType, PluginType } from '../interfaces';
3
+ import type { FilterType, GuardType, MiddlewareType, PipeType, PluginEntry } from '../interfaces';
4
4
  import type { DiContainer } from './di-container.interface';
5
5
  /**
6
6
  * Options for configuring the Honest application
@@ -64,9 +64,10 @@ export interface HonestOptions {
64
64
  filters?: FilterType[];
65
65
  };
66
66
  /**
67
- * Plugins for extending the application functionality
67
+ * Plugins for extending the application functionality.
68
+ * Each entry can be a plain plugin or an object with plugin and optional pre/post processors.
68
69
  */
69
- plugins?: PluginType[];
70
+ plugins?: PluginEntry[];
70
71
  /**
71
72
  * Default exception handler to use when no filter matches
72
73
  */
@@ -1,3 +1,4 @@
1
+ export * from './application-context.interface';
1
2
  export * from './controller-options.interface';
2
3
  export * from './di-container.interface';
3
4
  export * from './error-response.interface';
@@ -1,6 +1,21 @@
1
1
  import type { Hono } from 'hono';
2
2
  import type { Application } from '../application';
3
+ import type { IApplicationContext } from './application-context.interface';
3
4
  import type { Constructor } from '../types';
5
+ /**
6
+ * Processor callback for plugin pre/post hooks.
7
+ * Receives app, hono, and the application context (registry) for sharing pipeline data.
8
+ */
9
+ export type PluginProcessor = (app: Application, hono: Hono, ctx: IApplicationContext) => void | Promise<void>;
10
+ /**
11
+ * Object form of a plugin entry with optional pre/post processors.
12
+ * Processors run before (pre) or after (post) the plugin's lifecycle hooks.
13
+ */
14
+ export interface PluginEntryObject {
15
+ plugin: IPlugin | Constructor<IPlugin>;
16
+ preProcessors?: PluginProcessor[];
17
+ postProcessors?: PluginProcessor[];
18
+ }
4
19
  /**
5
20
  * Interface for Honest framework plugins
6
21
  * Plugins can extend the framework's functionality by hooking into
@@ -29,3 +44,9 @@ export interface IPlugin {
29
44
  * Can be either a class implementing IPlugin or an instance of IPlugin
30
45
  */
31
46
  export type PluginType = Constructor<IPlugin> | IPlugin;
47
+ /**
48
+ * Plugin entry: either a plain plugin or an object wrapping a plugin with optional processors.
49
+ * Use the object form to attach preProcessors (run before lifecycle hooks) and postProcessors
50
+ * (run after). Processors receive (app, hono, ctx) where ctx is the application context.
51
+ */
52
+ export type PluginEntry = PluginType | PluginEntryObject;
@@ -0,0 +1 @@
1
+ export {};
@@ -98,11 +98,12 @@ export declare const normalizePath: (path?: string) => string;
98
98
  */
99
99
  export declare const stripEndSlash: (path: string) => string;
100
100
  /**
101
- * Checks if a value is a constructor function
101
+ * Checks if a value is a constructor function (callable with `new`).
102
102
  * A constructor function must:
103
103
  * - Be a function
104
- * - Have a prototype
105
- * - Have prototype properties beyond the default ones
104
+ * - Have a non-null prototype (excludes arrow functions, which have no prototype)
105
+ * - Have a prototype that is not a function (excludes rare edge cases)
106
+ * - Have at least the built-in 'constructor' on prototype (so empty classes are constructors)
106
107
  *
107
108
  * @param val - The value to check
108
109
  * @returns True if the value is a constructor function, false otherwise
@@ -0,0 +1 @@
1
+ export {};
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "honestjs",
3
3
  "description": "HonestJS - a modern web framework built on top of Hono",
4
- "version": "0.1.7",
4
+ "version": "0.1.9",
5
5
  "author": "Orkhan Karimov <karimovok1@gmail.com> (https://github.com/kerimovok)",
6
6
  "repository": {
7
7
  "type": "git",
@@ -51,6 +51,8 @@
51
51
  "scripts": {
52
52
  "clean": "rm -rf dist",
53
53
  "prepare": "husky",
54
+ "test": "bun test",
55
+ "test:watch": "bun test --watch",
54
56
  "build": "bun run clean && bun build ./src/index.ts --outdir=dist --target=node --minify --external hono --external reflect-metadata && bun run build:types",
55
57
  "build:types": "tsc --emitDeclarationOnly --declaration --outDir dist",
56
58
  "lint": "eslint .",