Comparing version 0.4.9 to 0.5.0-exp-230422.2036
@@ -10,1 +10,2 @@ import { Elysia } from '.'; | ||
}) => any; | ||
export declare const composeGeneralHandler: (app: Elysia<any>) => any; |
@@ -1,2 +0,2 @@ | ||
import{parse as e}from"fast-querystring";import{mapEarlyResponse as r,mapResponse as t}from"./handler";import{createValidationError as a}from"./utils";import{mapErrorCode as s}from"./error";let n="AsyncFunction",o=e=>e.constructor.name===n;export const composeHandler=({method:c,hooks:l,validator:d,handler:i,handleError:f})=>{let p="try {\n",u="GET"!==c||i.constructor.name===n||l.parse.length||l.afterHandle.find(o)||l.beforeHandle.find(o)||l.transform.find(o);if(u){if(p+=` | ||
import{parse as e}from"fast-querystring";import{mapEarlyResponse as r,mapResponse as t}from"./handler";import{createValidationError as a,mapPathnameAndQueryRegEx as s}from"./utils";import{mapErrorCode as n}from"./error";let o="AsyncFunction",c=e=>e.constructor.name===o;export const composeHandler=({method:s,hooks:l,validator:d,handler:i,handleError:u})=>{let p="try {\n",f="GET"!==s||i.constructor.name===o||l.parse.length||l.afterHandle.find(c)||l.beforeHandle.find(c)||l.transform.find(c);if(f){if(p+=` | ||
let contentType = c.request.headers.get('content-type'); | ||
@@ -44,3 +44,3 @@ | ||
`.replace(/\t/g,"")+`}} | ||
`}if(l?.transform)for(let e=0;e<l.transform.length;e++)p+=l.transform[e].constructor.name===n?`await transform[${e}](c);`:`transform[${e}](c);`;if(d&&(d.headers&&(p+=` | ||
`}if(l?.transform)for(let e=0;e<l.transform.length;e++)p+=l.transform[e].constructor.name===o?`await transform[${e}](c);`:`transform[${e}](c);`;if(d&&(d.headers&&(p+=` | ||
const _header = {} | ||
@@ -57,6 +57,6 @@ for (const key of c.request.headers.keys()) | ||
} | ||
`.replace(/\t/g,"")),d.params&&(p+="if(params.Check(c.params) === false) { throw createValidationError('params', params, c.params) }"),d.query&&(p+="if(query.Check(c.query) === false) { throw createValidationError('params', query, c.query) }"),d.body&&(p+="if(body.Check(c.body) === false) { throw createValidationError('body', body, c.body) }")),l?.beforeHandle)for(let e=0;e<l.beforeHandle.length;e++){let r=`be${e}`;if(p+=(l.beforeHandle[e].constructor.name===n?`let ${r} = await beforeHandle[${e}](c); | ||
`.replace(/\t/g,"")),d.params&&(p+="if(params.Check(c.params) === false) { throw createValidationError('params', params, c.params) }"),d.query&&(p+="if(query.Check(c.query) === false) { throw createValidationError('params', query, c.query) }"),d.body&&(p+="if(body.Check(c.body) === false) { throw createValidationError('body', body, c.body) }")),l?.beforeHandle)for(let e=0;e<l.beforeHandle.length;e++){let r=`be${e}`;if(p+=(l.beforeHandle[e].constructor.name===o?`let ${r} = await beforeHandle[${e}](c); | ||
`:`let ${r} = beforeHandle[${e}](c); | ||
`)+`if(${r} !== undefined) { | ||
`,l?.afterHandle)for(let e=0;e<l.afterHandle.length;e++){let t=`af${e}`;p+=(l.afterHandle[e].constructor.name===n?`const ${t} = await afterHandle[${e}](c, ${r}); | ||
`,l?.afterHandle)for(let e=0;e<l.afterHandle.length;e++){let t=`af${e}`;p+=(l.afterHandle[e].constructor.name===o?`const ${t} = await afterHandle[${e}](c, ${r}); | ||
`:`const ${t} = afterHandle[${e}](c, ${r}); | ||
@@ -66,5 +66,5 @@ `)+`if(${t} !== undefined) { ${r} = ${t} } | ||
`),p+=`return mapEarlyResponse(${r}, c.set)} | ||
`}if(l?.afterHandle.length){p+=i.constructor.name===n?`let r = await handler(c); | ||
`}if(l?.afterHandle.length){p+=i.constructor.name===o?`let r = await handler(c); | ||
`:`let r = handler(c); | ||
`;for(let e=0;e<l.afterHandle.length;e++){let r=`af${e}`;p+=l.afterHandle[e].constructor.name===n?`let ${r} = await afterHandle[${e}](c, r) | ||
`;for(let e=0;e<l.afterHandle.length;e++){let r=`af${e}`;p+=l.afterHandle[e].constructor.name===o?`let ${r} = await afterHandle[${e}](c, r) | ||
`:`let ${r} = afterHandle[${e}](c, r) | ||
@@ -77,8 +77,8 @@ `,d.response?p+=`if(response[c.set.status]?.Check(${r}) === false) { throw createValidationError('response', response[c.set.status], ${r}) } | ||
`),p+=`return mapResponse(r, c.set); | ||
`}else d.response?p+=(i.constructor.name===n?`const r = await handler(c); | ||
`}else d.response?p+=(i.constructor.name===o?`const r = await handler(c); | ||
`:`const r = handler(c); | ||
`)+`if(response[c.set.status]?.Check(r) === false) { throw createValidationError('response', response[c.set.status], r) } | ||
`+"return mapResponse(r, c.set);":p+=i.constructor.name===n?"return mapResponse(await handler(c), c.set);":"return mapResponse(handler(c), c.set);";p+=` | ||
`+"return mapResponse(r, c.set);":p+=i.constructor.name===o?"return mapResponse(await handler(c), c.set);":"return mapResponse(handler(c), c.set);";p+=` | ||
} catch(error) { | ||
${u?"":"return (async () => {"} | ||
${f?"":"return (async () => {"} | ||
const set = c.set | ||
@@ -106,3 +106,3 @@ | ||
return handleError(c.request, error, set) | ||
${u?"":"})()"} | ||
${f?"":"})()"} | ||
}`,p=`const { | ||
@@ -134,2 +134,69 @@ handler, | ||
return ${u?"async":""} function(c) {${p}}`.replace(/\t/g,"");let h=Function("hooks",p);return h({handler:i,hooks:l,validator:d,handleError:f,utils:{createValidationError:a,mapResponse:t,mapEarlyResponse:r,mapErrorCode:s,parseQuery:e}})}; | ||
return ${f?"async":""} function(c) {${p}}`.replace(/\t/g,"");let h=Function("hooks",p);return h({handler:i,hooks:l,validator:d,handleError:u,utils:{createValidationError:a,mapResponse:t,mapEarlyResponse:r,mapErrorCode:n,parseQuery:e}})};export const composeGeneralHandler=t=>{let a=Object.keys(t.decorators).length>0;return Function("data",`const { | ||
app, | ||
parseQuery, | ||
mapPathnameAndQueryRegEx: map, | ||
mapEarlyResponse | ||
} = data | ||
// staticRouter | ||
const _static = app._s | ||
// Raikiri | ||
const router = app.router | ||
const ctx = ${a?"app.decorators":`{ | ||
set: { | ||
headers: {}, | ||
status: 200 | ||
}, | ||
params: {}, | ||
query: {} | ||
}`} | ||
return (request) => { | ||
${a?` | ||
ctx.set = { | ||
headers: {}, | ||
status: 200 | ||
}`:""} | ||
ctx.request = request | ||
${t.event.request.length?` | ||
try { | ||
for (let i = 0; i < app.event.request.length; i++) { | ||
const response = mapEarlyResponse( | ||
app.event.request[i](ctx), | ||
ctx.set | ||
) | ||
if (response) return response | ||
} | ||
} catch (error) { | ||
return app.handleError(request, error, ctx.set) | ||
}`:""} | ||
const fracture = map.exec(request.url) | ||
if (fracture[2]) ctx.query = parseQuery(fracture[2]) | ||
${a?"else ctx.query = {}":""} | ||
const handle = _static.get(request.method + fracture[1]) | ||
if (handle) { | ||
${a?"ctx.params = {}":""} | ||
return handle(ctx) | ||
} else { | ||
const route = router._m(request.method, fracture[1]) ?? router._m('ALL', fracture[1]) | ||
if (!route) | ||
return app.handleError( | ||
request, | ||
new Error('NOT_FOUND'), | ||
ctx.set | ||
) | ||
ctx.params = route.params | ||
return route.store(ctx) | ||
} | ||
}`)({app:t,parseQuery:e,mapPathnameAndQueryRegEx:s,mapEarlyResponse:r})}; |
@@ -364,3 +364,3 @@ /// <reference types="bun-types" /> | ||
handle: (request: Request) => Promise<Response>; | ||
innerHandle: (request: Request) => MaybePromise<Response>; | ||
innerHandle(request: Request): MaybePromise<Response>; | ||
handleError: (request: Request, error: Error, set?: Context['set']) => Promise<Response>; | ||
@@ -367,0 +367,0 @@ listen: (options: string | number | Partial<Serve>, callback?: ListenCallback) => this; |
@@ -1,1 +0,1 @@ | ||
import{nanoid as e}from"nanoid";import{Raikiri as t}from"raikiri";import{parse as r}from"fast-querystring";import{mapResponse as s,mapEarlyResponse as a}from"./handler";import{SCHEMA as i,EXPOSED as o,DEFS as n,clone as h,mergeHook as u,getSchemaValidator as d,getResponseSchemaValidator as l,mapPathnameAndQueryRegEx as c,mergeDeep as m}from"./utils";import{registerSchemaPath as p}from"./schema";import{mapErrorCode as f,mapErrorStatus as v}from"./error";import{composeHandler as y}from"./compose";import{ws as g}from"./ws";export default class b{config;store={};meta={[i]:Object.create(null),[n]:Object.create(null),[o]:Object.create(null)};decorators={[i]:this.meta[i],[n]:this.meta[n],store:this.store};event={start:[],request:[],parse:[],transform:[],beforeHandle:[],afterHandle:[],error:[],stop:[]};server=null;$schema=null;router=new t;routes=[];_s=new Map;wsRouter;lazyLoadModules=[];constructor(e){this.config={fn:"/~fn",...e}}_addHandler(e,t,r,s){t=t.startsWith("/")?t:`/${t}`,this.routes.push({method:e,path:t,handler:r,hooks:u({...this.event},s)});let a=this.meta[n],o=d(s?.schema?.body??this.$schema?.body,a),c=d(s?.schema?.headers??this.$schema?.headers,a,!0),m=d(s?.schema?.params??this.$schema?.params,a),f=d(s?.schema?.query??this.$schema?.query,a),v=l(s?.schema?.response??this.$schema?.response,a);p({schema:this.meta[i],contentType:s?.schema?.contentType,hook:s,method:e,path:t,models:this.meta[n]});let g=u(h(this.event),s),b=y({method:e,hooks:g,validator:{body:o,headers:c,params:m,query:f,response:v},handler:r,handleError:this.handleError});t.includes("/:")||t.includes("/*")||this._s.set(e+t,b),this.router.add(e,t,b)}onStart(e){return this.event.start.push(e),this}onRequest(e){return this.event.request.push(e),this}onParse(e){return this.event.parse.splice(this.event.parse.length-1,0,e),this}onTransform(e){return this.event.transform.push(e),this}onBeforeHandle(e){return this.event.beforeHandle.push(e),this}onAfterHandle(e){return this.event.afterHandle.push(e),this}onError(e){return this.event.error.push(e),this}onStop(e){return this.event.stop.push(e),this}on(e,t){switch(e){case"start":this.event.start.push(t);break;case"request":this.event.request.push(t);break;case"parse":this.event.parse.push(t);break;case"transform":this.event.transform.push(t);break;case"beforeHandle":this.event.beforeHandle.push(t);break;case"afterHandle":this.event.afterHandle.push(t);break;case"error":this.event.error.push(t);break;case"stop":this.event.stop.push(t)}return this}group(e,t){let r=new b;r.store=this.store,this.wsRouter&&r.use(g());let s=t(r);return this.decorators=m(this.decorators,r.decorators),s.event.request.length&&(this.event.request=[...this.event.request,...s.event.request]),this.setModel(s.meta[n]),Object.values(r.routes).forEach(({method:t,path:a,handler:i,hooks:o})=>{let n="/"===a?e:`${e}${a}`,h=r.wsRouter?.match("subscribe",n);if(h){let e=r.wsRouter.history.find(([e,t])=>a===t);if(!e)return;return this.ws(n,e[2])}this._addHandler(t,n,i,u(o,{error:s.event.error}))}),r.wsRouter&&this.wsRouter&&r.wsRouter.history.forEach(([t,r,s])=>{"/"===r?this.wsRouter?.add(t,e,s):this.wsRouter?.add(t,`${e}${r}`,s)}),this}guard(e,t){let r=new b;r.store=this.store,this.wsRouter&&r.use(g());let s=t(r);return this.decorators=m(this.decorators,r.decorators),s.event.request.length&&(this.event.request=[...this.event.request,...s.event.request]),this.setModel(s.meta[n]),Object.values(r.routes).forEach(({method:t,path:a,handler:i,hooks:o})=>{let n=r.wsRouter?.match("subscribe",a);if(n){let e=r.wsRouter.history.find(([e,t])=>a===t);if(!e)return;return this.ws(a,e[2])}this._addHandler(t,a,i,u(e,{...o,error:o.error?Array.isArray(o.error)?[...o.error,...s.event.error]:[o.error,...s.event.error]:s.event.error}))}),r.wsRouter&&this.wsRouter&&r.wsRouter.history.forEach(([e,t,r])=>{this.wsRouter?.add(e,t,r)}),this}use(e){if(e instanceof Promise)return this.lazyLoadModules.push(e.then(e=>"function"==typeof e?e(this):e.default(this))),this;let t=e(this);return t instanceof Promise?(this.lazyLoadModules.push(t),this):t}if(e,t){return e?this.use(t):this}get(e,t,r){return this._addHandler("GET",e,t,r),this}post(e,t,r){return this._addHandler("POST",e,t,r),this}put(e,t,r){return this._addHandler("PUT",e,t,r),this}patch(e,t,r){return this._addHandler("PATCH",e,t,r),this}delete(e,t,r){return this._addHandler("DELETE",e,t,r),this}options(e,t,r){return this._addHandler("OPTIONS",e,t,r),this}all(e,t,r){return this._addHandler("ALL",e,t,r),this}head(e,t,r){return this._addHandler("HEAD",e,t,r),this}trace(e,t,r){return this._addHandler("TRACE",e,t,r),this}connect(e,t,r){return this._addHandler("CONNECT",e,t,r),this}ws(t,r){if(!this.wsRouter)throw Error("Can't find WebSocket. Please register WebSocket plugin first by importing 'elysia/ws'");return this.wsRouter.add("subscribe",t,r),this.get(t,t=>{if(!this.server?.upgrade(t.request,{headers:"function"==typeof r.headers?r.headers(t):r.headers,data:{...t,id:e(),message:d(r.schema?.body,this.meta[n]),transformMessage:r.transform?Array.isArray(r.transformMessage)?r.transformMessage:[r.transformMessage]:[]}}))return t.set.status=400,"Expected a websocket connection"},{parse:r.parse,beforeHandle:r.beforeHandle,transform:r.transform,schema:{headers:r.schema?.headers,params:r.schema?.params,query:r.schema?.query}}),this}route(e,t,r,s){return this._addHandler(e,t,r,s),this}state(e,t){return e in this.store||(this.store[e]=t),this}decorate(e,t){return e in this.decorators||(this.decorators[e]=t),this}derive(e){return"AsyncFunction"===e.constructor.name?this.onTransform(async t=>{Object.assign(t,await e(t))}):this.onTransform(t=>{Object.assign(t,e(t))})}fn(e){return this.use(async()=>{let{fn:t}=await import("@elysiajs/fn");return t({app:this,value:e,path:this.config.fn})})}schema(e){let t=this.meta[n];return this.$schema={body:d(e.body,t),headers:d(e?.headers,t,!0),params:d(e?.params,t),query:d(e?.query,t),response:d(e?.response,t)},this}handle=async e=>this.innerHandle(e);innerHandle=e=>{let t=this.decorators;if(t.request=e,t.set={headers:{},status:200},this.event.request.length)try{for(let e=0;e<this.event.request.length;e++){let r=a(this.event.request[e](t),t.set);if(r)return r}}catch(r){return this.handleError(e,r,t.set)}let s=c.exec(e.url);s[2]?t.query=r(s[2]):t.query={};let i=this._s.get(e.method+s[1]);if(i)return t.params={},i(t);{let r=this.router._m(e.method,s[1])??this.router._m("ALL",s[1]);return r?(t.params=r.params,r.store(t)):this.handleError(e,Error("NOT_FOUND"),t.set)}};handleError=async(e,t,r={headers:{}})=>{for(let a=0;a<this.event.error.length;a++){let i=this.event.error[a]({request:e,code:f(t.message),error:t,set:r});if(i instanceof Promise&&(i=await i),null!=i)return s(i,r)}return new Response("string"==typeof t.cause?t.cause:t.message,{headers:r.headers,status:v(f(t.message))})};listen=(e,t)=>{if(!Bun)throw Error("Bun to run");if("string"==typeof e&&Number.isNaN(e=+e))throw Error("Port must be a numeric value");let r=this.innerHandle,s="object"==typeof e?{...this.config.serve,...e,fetch:r}:{...this.config.serve,port:e,fetch:r},a=`$$Elysia:${s.port}`;globalThis[a]?(this.server=globalThis[a],this.server.reload(s)):globalThis[a]=this.server=Bun.serve(s);for(let e=0;e<this.event.start.length;e++)this.event.start[e](this);return t&&t(this.server),Promise.all(this.lazyLoadModules).then(()=>{this.server.pendingRequests||Bun.gc(!0)}),this};stop=async()=>{if(!this.server)throw Error("Elysia isn't running. Call `app.listen` to start the server.");this.server.stop();for(let e=0;e<this.event.stop.length;e++)await this.event.stop[e](this)};get modules(){return Promise.all(this.lazyLoadModules)}setModel(e){return Object.entries(e).forEach(([e,t])=>{e in this.meta[n]||(this.meta[n][e]=t)}),this}}export{t}from"./custom-types";export{ws}from"./ws";export{SCHEMA,DEFS,EXPOSED,createValidationError,getSchemaValidator,mergeDeep,mergeHook,mergeObjectArray,mapPathnameAndQueryRegEx}from"./utils";export{ElysiaError,ValidationError}from"./validation";export{b as Elysia}; | ||
import{nanoid as e}from"nanoid";import{Raikiri as t}from"raikiri";import{mapResponse as r}from"./handler";import{SCHEMA as s,EXPOSED as a,DEFS as i,mergeHook as o,getSchemaValidator as n,getResponseSchemaValidator as h,mergeDeep as u}from"./utils";import{registerSchemaPath as d}from"./schema";import{mapErrorCode as l,mapErrorStatus as c}from"./error";import{composeGeneralHandler as m,composeHandler as p}from"./compose";import{ws as f}from"./ws";export default class v{config;store={};meta={[s]:Object.create(null),[i]:Object.create(null),[a]:Object.create(null)};decorators={[s]:this.meta[s],[i]:this.meta[i],store:this.store};event={start:[],request:[],parse:[],transform:[],beforeHandle:[],afterHandle:[],error:[],stop:[]};server=null;$schema=null;router=new t;routes=[];_s=new Map;wsRouter;lazyLoadModules=[];constructor(e){this.config={fn:"/~fn",...e},this.innerHandle=m(this)}_addHandler(e,t,r,a){t=t.startsWith("/")?t:`/${t}`,this.routes.push({method:e,path:t,handler:r,hooks:o({...this.event},a)});let u=this.meta[i];d({schema:this.meta[s],contentType:a?.schema?.contentType,hook:a,method:e,path:t,models:this.meta[i]});let l={body:n(a?.schema?.body??this.$schema?.body,u),headers:n(a?.schema?.headers??this.$schema?.headers,u,!0),params:n(a?.schema?.params??this.$schema?.params,u),query:n(a?.schema?.query??this.$schema?.query,u),response:h(a?.schema?.response??this.$schema?.response,u)},c=o(this.event,a),f=p({method:e,hooks:c,validator:l,handler:r,handleError:this.handleError});-1===t.indexOf(":")&&-1===t.indexOf("*")&&this._s.set(e+t,f),this.router.add(e,t,f),this.innerHandle=m(this)}onStart(e){return this.event.start.push(e),this}onRequest(e){return this.event.request.push(e),this}onParse(e){return this.event.parse.splice(this.event.parse.length-1,0,e),this}onTransform(e){return this.event.transform.push(e),this}onBeforeHandle(e){return this.event.beforeHandle.push(e),this}onAfterHandle(e){return this.event.afterHandle.push(e),this}onError(e){return this.event.error.push(e),this}onStop(e){return this.event.stop.push(e),this}on(e,t){switch(e){case"start":this.event.start.push(t);break;case"request":this.event.request.push(t);break;case"parse":this.event.parse.push(t);break;case"transform":this.event.transform.push(t);break;case"beforeHandle":this.event.beforeHandle.push(t);break;case"afterHandle":this.event.afterHandle.push(t);break;case"error":this.event.error.push(t);break;case"stop":this.event.stop.push(t)}return this}group(e,t){let r=new v;r.store=this.store,this.wsRouter&&r.use(f());let s=t(r);return this.decorators=u(this.decorators,r.decorators),s.event.request.length&&(this.event.request=[...this.event.request,...s.event.request]),this.setModel(s.meta[i]),Object.values(r.routes).forEach(({method:t,path:a,handler:i,hooks:n})=>{let h="/"===a?e:`${e}${a}`,u=r.wsRouter?.match("subscribe",h);if(u){let e=r.wsRouter.history.find(([e,t])=>a===t);if(!e)return;return this.ws(h,e[2])}this._addHandler(t,h,i,o(n,{error:s.event.error}))}),r.wsRouter&&this.wsRouter&&r.wsRouter.history.forEach(([t,r,s])=>{"/"===r?this.wsRouter?.add(t,e,s):this.wsRouter?.add(t,`${e}${r}`,s)}),this}guard(e,t){let r=new v;r.store=this.store,this.wsRouter&&r.use(f());let s=t(r);return this.decorators=u(this.decorators,r.decorators),s.event.request.length&&(this.event.request=[...this.event.request,...s.event.request]),this.setModel(s.meta[i]),Object.values(r.routes).forEach(({method:t,path:a,handler:i,hooks:n})=>{let h=r.wsRouter?.match("subscribe",a);if(h){let e=r.wsRouter.history.find(([e,t])=>a===t);if(!e)return;return this.ws(a,e[2])}this._addHandler(t,a,i,o(e,{...n,error:n.error?Array.isArray(n.error)?[...n.error,...s.event.error]:[n.error,...s.event.error]:s.event.error}))}),r.wsRouter&&this.wsRouter&&r.wsRouter.history.forEach(([e,t,r])=>{this.wsRouter?.add(e,t,r)}),this}use(e){if(e instanceof Promise)return this.lazyLoadModules.push(e.then(e=>"function"==typeof e?e(this):e.default(this))),this;let t=e(this);return t instanceof Promise?(this.lazyLoadModules.push(t),this):t}if(e,t){return e?this.use(t):this}get(e,t,r){return this._addHandler("GET",e,t,r),this}post(e,t,r){return this._addHandler("POST",e,t,r),this}put(e,t,r){return this._addHandler("PUT",e,t,r),this}patch(e,t,r){return this._addHandler("PATCH",e,t,r),this}delete(e,t,r){return this._addHandler("DELETE",e,t,r),this}options(e,t,r){return this._addHandler("OPTIONS",e,t,r),this}all(e,t,r){return this._addHandler("ALL",e,t,r),this}head(e,t,r){return this._addHandler("HEAD",e,t,r),this}trace(e,t,r){return this._addHandler("TRACE",e,t,r),this}connect(e,t,r){return this._addHandler("CONNECT",e,t,r),this}ws(t,r){if(!this.wsRouter)throw Error("Can't find WebSocket. Please register WebSocket plugin first by importing 'elysia/ws'");return this.wsRouter.add("subscribe",t,r),this.get(t,t=>{if(!this.server?.upgrade(t.request,{headers:"function"==typeof r.headers?r.headers(t):r.headers,data:{...t,id:e(),message:n(r.schema?.body,this.meta[i]),transformMessage:r.transform?Array.isArray(r.transformMessage)?r.transformMessage:[r.transformMessage]:[]}}))return t.set.status=400,"Expected a websocket connection"},{parse:r.parse,beforeHandle:r.beforeHandle,transform:r.transform,schema:{headers:r.schema?.headers,params:r.schema?.params,query:r.schema?.query}}),this}route(e,t,r,s){return this._addHandler(e,t,r,s),this}state(e,t){return e in this.store||(this.store[e]=t),this}decorate(e,t){return e in this.decorators||(this.decorators[e]=t),this}derive(e){return"AsyncFunction"===e.constructor.name?this.onTransform(async t=>{Object.assign(t,await e(t))}):this.onTransform(t=>{Object.assign(t,e(t))})}fn(e){return this.use(async()=>{let{fn:t}=await import("@elysiajs/fn");return t({app:this,value:e,path:this.config.fn})})}schema(e){let t=this.meta[i];return this.$schema={body:n(e.body,t),headers:n(e?.headers,t,!0),params:n(e?.params,t),query:n(e?.query,t),response:n(e?.response,t)},this}handle=async e=>this.innerHandle(e);handleError=async(e,t,s={headers:{}})=>{for(let a=0;a<this.event.error.length;a++){let i=this.event.error[a]({request:e,code:l(t.message),error:t,set:s});if(i instanceof Promise&&(i=await i),null!=i)return r(i,s)}return new Response("string"==typeof t.cause?t.cause:t.message,{headers:s.headers,status:c(l(t.message))})};listen=(e,t)=>{if(!Bun)throw Error("Bun to run");if("string"==typeof e&&Number.isNaN(e=+e))throw Error("Port must be a numeric value");let r=this.innerHandle,s="object"==typeof e?{...this.config.serve,...e,fetch:r}:{...this.config.serve,port:e,fetch:r},a=`$$Elysia:${s.port}`;globalThis[a]?(this.server=globalThis[a],this.server.reload(s)):globalThis[a]=this.server=Bun.serve(s);for(let e=0;e<this.event.start.length;e++)this.event.start[e](this);return t&&t(this.server),Promise.all(this.lazyLoadModules).then(()=>{this.server.pendingRequests||Bun.gc(!0)}),this};stop=async()=>{if(!this.server)throw Error("Elysia isn't running. Call `app.listen` to start the server.");this.server.stop();for(let e=0;e<this.event.stop.length;e++)await this.event.stop[e](this)};get modules(){return Promise.all(this.lazyLoadModules)}setModel(e){return Object.entries(e).forEach(([e,t])=>{e in this.meta[i]||(this.meta[i][e]=t)}),this}}export{t}from"./custom-types";export{ws}from"./ws";export{SCHEMA,DEFS,EXPOSED,createValidationError,getSchemaValidator,mergeDeep,mergeHook,mergeObjectArray,mapPathnameAndQueryRegEx}from"./utils";export{ElysiaError,ValidationError}from"./validation";export{v as Elysia}; |
{ | ||
"name": "elysia", | ||
"description": "Fast, and friendly Bun web framework", | ||
"version": "0.4.9", | ||
"version": "0.5.0-exp-230422.2036", | ||
"author": { | ||
@@ -6,0 +6,0 @@ "name": "saltyAom", |
@@ -6,3 +6,3 @@ import { Elysia } from '.' | ||
import { mapEarlyResponse, mapResponse } from './handler' | ||
import { createValidationError } from './utils' | ||
import { createValidationError, mapPathnameAndQueryRegEx } from './utils' | ||
import { mapErrorCode } from './error' | ||
@@ -289,9 +289,94 @@ | ||
// const createTypeboxAot = (a: TypeCheck<any> | undefined) => { | ||
// if (!a) return | ||
export const composeGeneralHandler = (app: Elysia<any>) => { | ||
// @ts-ignore | ||
const hasDecorators = Object.keys(app.decorators).length > 0 | ||
// const fnLiteral = a.Code() | ||
return Function( | ||
'data', | ||
`const { | ||
app, | ||
parseQuery, | ||
mapPathnameAndQueryRegEx: map, | ||
mapEarlyResponse | ||
} = data | ||
// if (fnLiteral.includes('custom(')) return (param: any) => a.Check(param) | ||
// return new Function(a.Code())() | ||
// } | ||
// staticRouter | ||
const _static = app._s | ||
// Raikiri | ||
const router = app.router | ||
const ctx = ${ | ||
hasDecorators | ||
? `app.decorators` | ||
: `{ | ||
set: { | ||
headers: {}, | ||
status: 200 | ||
}, | ||
params: {}, | ||
query: {} | ||
}` | ||
} | ||
return (request) => { | ||
${ | ||
hasDecorators | ||
? ` | ||
ctx.set = { | ||
headers: {}, | ||
status: 200 | ||
}` | ||
: '' | ||
} | ||
ctx.request = request | ||
${ | ||
app.event.request.length | ||
? ` | ||
try { | ||
for (let i = 0; i < app.event.request.length; i++) { | ||
const response = mapEarlyResponse( | ||
app.event.request[i](ctx), | ||
ctx.set | ||
) | ||
if (response) return response | ||
} | ||
} catch (error) { | ||
return app.handleError(request, error, ctx.set) | ||
}` | ||
: '' | ||
} | ||
const fracture = map.exec(request.url) | ||
if (fracture[2]) ctx.query = parseQuery(fracture[2]) | ||
${hasDecorators ? `else ctx.query = {}` : ''} | ||
const handle = _static.get(request.method + fracture[1]) | ||
if (handle) { | ||
${hasDecorators ? `ctx.params = {}` : ''} | ||
return handle(ctx) | ||
} else { | ||
const route = router._m(request.method, fracture[1]) ?? router._m('ALL', fracture[1]) | ||
if (!route) | ||
return app.handleError( | ||
request, | ||
new Error('NOT_FOUND'), | ||
ctx.set | ||
) | ||
ctx.params = route.params | ||
return route.store(ctx) | ||
} | ||
}` | ||
)({ | ||
app, | ||
parseQuery, | ||
mapPathnameAndQueryRegEx, | ||
mapEarlyResponse | ||
}) | ||
} |
115
src/index.ts
@@ -5,5 +5,4 @@ import type { Serve, Server } from 'bun' | ||
import { Raikiri } from 'raikiri' | ||
import { parse as parseQuery } from 'fast-querystring' | ||
import { mapResponse, mapEarlyResponse } from './handler' | ||
import { mapResponse } from './handler' | ||
import { | ||
@@ -13,7 +12,5 @@ SCHEMA, | ||
DEFS, | ||
clone, | ||
mergeHook, | ||
getSchemaValidator, | ||
getResponseSchemaValidator, | ||
mapPathnameAndQueryRegEx, | ||
mergeDeep | ||
@@ -25,3 +22,3 @@ } from './utils' | ||
import { composeHandler } from './compose' | ||
import { composeGeneralHandler, composeHandler } from './compose' | ||
@@ -126,2 +123,4 @@ import { ws } from './ws' | ||
} | ||
this.innerHandle = composeGeneralHandler(this) | ||
} | ||
@@ -149,24 +148,2 @@ | ||
const body = getSchemaValidator( | ||
hook?.schema?.body ?? (this.$schema?.body as any), | ||
defs | ||
) | ||
const headers = getSchemaValidator( | ||
hook?.schema?.headers ?? (this.$schema?.headers as any), | ||
defs, | ||
true | ||
) | ||
const params = getSchemaValidator( | ||
hook?.schema?.params ?? (this.$schema?.params as any), | ||
defs | ||
) | ||
const query = getSchemaValidator( | ||
hook?.schema?.query ?? (this.$schema?.query as any), | ||
defs | ||
) | ||
const response = getResponseSchemaValidator( | ||
hook?.schema?.response ?? (this.$schema?.response as any), | ||
defs | ||
) | ||
registerSchemaPath({ | ||
@@ -182,10 +159,26 @@ schema: this.meta[SCHEMA], | ||
const validator = { | ||
body, | ||
headers, | ||
params, | ||
query, | ||
response | ||
body: getSchemaValidator( | ||
hook?.schema?.body ?? (this.$schema?.body as any), | ||
defs | ||
), | ||
headers: getSchemaValidator( | ||
hook?.schema?.headers ?? (this.$schema?.headers as any), | ||
defs, | ||
true | ||
), | ||
params: getSchemaValidator( | ||
hook?.schema?.params ?? (this.$schema?.params as any), | ||
defs | ||
), | ||
query: getSchemaValidator( | ||
hook?.schema?.query ?? (this.$schema?.query as any), | ||
defs | ||
), | ||
response: getResponseSchemaValidator( | ||
hook?.schema?.response ?? (this.$schema?.response as any), | ||
defs | ||
) | ||
} | ||
const hooks = mergeHook(clone(this.event), hook as RegisteredHook) | ||
const hooks = mergeHook(this.event, hook as RegisteredHook) | ||
@@ -200,6 +193,8 @@ const mainHandler = composeHandler({ | ||
if (!path.includes('/:') && !path.includes('/*')) | ||
if (path.indexOf(':') === -1 && path.indexOf('*') === -1) | ||
this._s.set(method + path, mainHandler) | ||
this.router.add(method, path, mainHandler as any) | ||
this.innerHandle = composeGeneralHandler(this) | ||
} | ||
@@ -2192,53 +2187,5 @@ | ||
*/ | ||
innerHandle = (request: Request): MaybePromise<Response> => { | ||
const context: Context = this.decorators as any as Context | ||
context.request = request | ||
context.set = { | ||
headers: {}, | ||
status: 200 | ||
} | ||
// @ts-ignore | ||
innerHandle(request: Request): MaybePromise<Response> | ||
if (this.event.request.length) | ||
try { | ||
for (let i = 0; i < this.event.request.length; i++) { | ||
const response = mapEarlyResponse( | ||
this.event.request[i](context), | ||
context.set | ||
) | ||
if (response) return response | ||
} | ||
} catch (error) { | ||
return this.handleError(request, error as Error, context.set) | ||
} | ||
const fracture = mapPathnameAndQueryRegEx.exec(request.url)! | ||
if (fracture[2]) context.query = parseQuery(fracture[2]) | ||
else context.query = {} | ||
const handle = this._s.get(request.method + fracture[1]) | ||
if (handle) { | ||
context.params = {} | ||
return handle(context) | ||
} else { | ||
const route = | ||
// @ts-ignore | ||
this.router._m(request.method, fracture[1]) ?? | ||
// @ts-ignore | ||
this.router._m('ALL', fracture[1]) | ||
if (!route) | ||
return this.handleError( | ||
request, | ||
new Error('NOT_FOUND'), | ||
context.set | ||
) | ||
context.params = route.params | ||
return route.store(context) | ||
} | ||
} | ||
handleError = async ( | ||
@@ -2245,0 +2192,0 @@ request: Request, |
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
Uses eval
Supply chain riskPackage uses dynamic code execution (e.g., eval()), which is a dangerous practice. This can prevent the code from running in certain environments and increases the risk that the code may contain exploits or malicious behavior.
Found 1 instance in 1 package
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
203572
5305
2