UNPKG

@mobtakronio/schemakit-elysia

Version:

Elysia adapter for SchemaKit with auto-generated REST endpoints

2 lines 7.34 kB
'use strict';Object.defineProperty(exports,'__esModule',{value:true});var elysia=require('elysia'),swagger=require('@elysiajs/swagger');function E(n,a){return {success:true,data:n,message:a,timestamp:new Date().toISOString()}}function h(n,a){return {success:false,error:n instanceof Error?n.message:n,message:a||"Operation failed",timestamp:new Date().toISOString()}}function C(n,a,t,s,y){let g=Math.ceil(s/t),w={page:a,limit:t,total:s,totalPages:g,hasNext:a<g,hasPrev:a>1};return {success:true,data:n,meta:w,message:y,timestamp:new Date().toISOString()}}function O(n){let a=Math.max(1,parseInt(n.page)||1),t=Math.min(100,Math.max(1,parseInt(n.limit)||10)),s={},y=n.sort?{field:n.sort,order:n.order||"asc"}:void 0,g=new Set(["page","limit","sort","order","search"]),w=/^[A-Za-z_][A-Za-z0-9_]*$/;for(let[o,i]of Object.entries(n))g.has(o)||i===void 0||i===""||w.test(o)&&(s[o]=i);return n.search&&(s._search=n.search),{pagination:{page:a,limit:t},filters:s,sort:y}}function A(n,a,t){if(t)return t(n);let s=n.headers;return {tenantId:a,user:{id:s.get("x-user-id")||"anonymous",role:s.get("x-user-role")||"user"},request:{ip:s.get("x-forwarded-for")||s.get("x-real-ip")||"unknown",userAgent:s.get("user-agent")||"unknown"}}}function x(n,a){if(a.excludeEntities){for(let t of a.excludeEntities)if(t instanceof RegExp?t.test(n):t===n)return false}if(a.includeEntities){for(let t of a.includeEntities)if(t instanceof RegExp?t.test(n):t===n)return true;return false}return true}function K(n){return n.toLowerCase().replace(/[^a-z0-9-_]/g,"-")}async function R(n,a,t){try{return {success:!0,data:await n()}}catch(s){return {success:false,error:s instanceof Error?s:new Error(String(s))}}}function T(n,a={}){let t={basePath:"/api",tenantId:"default",enableDocs:true,docsPath:"/docs",enableCors:true,...a},s=new elysia.Elysia({name:"schemakit"});t.enableCors&&s.use(new elysia.Elysia().all("*",({set:o})=>{o.headers["Access-Control-Allow-Origin"]="*",o.headers["Access-Control-Allow-Methods"]="GET, POST, PUT, DELETE, OPTIONS",o.headers["Access-Control-Allow-Headers"]="Content-Type, Authorization, X-User-Id, X-User-Role";})),t.enableDocs&&s.use(swagger.swagger({path:t.docsPath,documentation:{info:{title:"SchemaKit API",description:"Auto-generated REST API for SchemaKit entities",version:"1.0.0"},tags:[{name:"Entities",description:"CRUD operations for dynamic entities"},{name:"Views",description:"View execution endpoints for dynamic entities"}]}}));let y=(o,i,m)=>t.errorHandler?t.errorHandler(o,i,m):(console.error(`SchemaKit Error [${i}:${m}]:`,o),h(o)),g=async o=>await n.entity(o,t.tenantId),w=async o=>{let i=A(o,t.tenantId,t.contextProvider);return i instanceof Promise?await i:i};return s.group(t.basePath,o=>(o.get("/entities",async()=>{try{return E([],"Available entities")}catch(i){return y(i,"system","list-entities")}},{detail:{tags:["Entities"],summary:"List all available entities",description:"Get a list of all entities registered in SchemaKit"}}),o.group("/entity",i=>(i.get("/:entityName",async({params:m,query:p,request:d})=>{let{entityName:r}=m;if(!x(r,t))return h("Entity not accessible","Access denied");let c=await R(async()=>{let u=await g(r),f=await w(d),{pagination:l,filters:b}=O(p),S=await u.get(b,f),P=(l.page-1)*l.limit,N=P+l.limit,I=S.slice(P,N);return C(I,l.page,l.limit,S.length,`Retrieved ${I.length} records`)});return c.success?c.data:y(c.error,r,"list")},{detail:{tags:["Entities"],summary:"List entity records",description:"Get a paginated list of entity records with optional filtering"},query:elysia.t.Object({page:elysia.t.Optional(elysia.t.Number({minimum:1})),limit:elysia.t.Optional(elysia.t.Number({minimum:1,maximum:100})),sort:elysia.t.Optional(elysia.t.String()),order:elysia.t.Optional(elysia.t.Union([elysia.t.Literal("asc"),elysia.t.Literal("desc")])),search:elysia.t.Optional(elysia.t.String())})}),i.post("/:entityName",async({params:m,body:p,request:d})=>{let{entityName:r}=m;if(!x(r,t))return h("Entity not accessible","Access denied");let c=await R(async()=>{let u=await g(r),f=await w(d),l=await u.insert(p,f);return E(l,"Record created successfully")});return c.success?c.data:y(c.error,r,"create")},{detail:{tags:["Entities"],summary:"Create entity record",description:"Create a new entity record"},body:elysia.t.Record(elysia.t.String(),elysia.t.Any())}),i.get("/:entityName/:id",async({params:m,request:p})=>{let{entityName:d,id:r}=m;if(!x(d,t))return h("Entity not accessible","Access denied");let c=await R(async()=>{let u=await g(d),f=await w(p),l=await u.getById(r,f);if(!l)throw new Error(`Record with ID ${r} not found`);return E(l,"Record retrieved")});return c.success?c.data:y(c.error,d,"read")},{detail:{tags:["Entities"],summary:"Get entity record by ID",description:"Retrieve a specific entity record by its ID"},params:elysia.t.Object({entityName:elysia.t.String(),id:elysia.t.Union([elysia.t.String(),elysia.t.Number()])})}),i.get("/:entityName/views/:viewName",async({params:m,query:p,request:d})=>{let{entityName:r,viewName:c}=m;if(!x(r,t))return h("Entity not accessible","Access denied");let u=await R(async()=>{let f=await g(r),l=await w(d),{pagination:b,filters:S}=O(p),P=String(p.stats||"").toLowerCase()==="true",N=await f.view(c,{filters:S,pagination:b,stats:P},l);return E(N,"View executed successfully")});return u.success?u.data:y(u.error,r,"view")},{detail:{tags:["Views"],summary:"Execute view",description:"Execute a named view for the entity with optional pagination and filters"},params:elysia.t.Object({entityName:elysia.t.String(),viewName:elysia.t.String()}),query:elysia.t.Object({page:elysia.t.Optional(elysia.t.Number({minimum:1})),limit:elysia.t.Optional(elysia.t.Number({minimum:1,maximum:100})),stats:elysia.t.Optional(elysia.t.Union([elysia.t.Literal("true"),elysia.t.Literal("false")]))})}),i.put("/:entityName/:id",async({params:m,body:p,request:d})=>{let{entityName:r,id:c}=m;if(!x(r,t))return h("Entity not accessible","Access denied");let u=await R(async()=>{let f=await g(r),l=await w(d),b=await f.update(c,p,l);return E(b,"Record updated successfully")});return u.success?u.data:y(u.error,r,"update")},{detail:{tags:["Entities"],summary:"Update entity record",description:"Update an existing entity record"},params:elysia.t.Object({entityName:elysia.t.String(),id:elysia.t.Union([elysia.t.String(),elysia.t.Number()])}),body:elysia.t.Record(elysia.t.String(),elysia.t.Any())}),i.delete("/:entityName/:id",async({params:m,request:p})=>{let{entityName:d,id:r}=m;if(!x(d,t))return h("Entity not accessible","Access denied");let c=await R(async()=>{let u=await g(d),f=await w(p);if(!await u.delete(r,f))throw new Error(`Failed to delete record with ID ${r}`);return E({id:r,deleted:!0},"Record deleted successfully")});return c.success?c.data:y(c.error,d,"delete")},{detail:{tags:["Entities"],summary:"Delete entity record",description:"Delete an entity record by its ID"},params:elysia.t.Object({entityName:elysia.t.String(),id:elysia.t.Union([elysia.t.String(),elysia.t.Number()])})}),i)),o)),s}exports.createErrorResponse=h;exports.createPaginatedResponse=C;exports.createSuccessResponse=E;exports.default=T;exports.extractContext=A;exports.handleAsync=R;exports.parseListQuery=O;exports.sanitizeEntityName=K;exports.schemaKitElysia=T;exports.shouldIncludeEntity=x;//# sourceMappingURL=index.js.map //# sourceMappingURL=index.js.map