LoopBack 4's architecture. Hono's speed.
Documentation • Quickstart • Core API • Examples • Changelog
Enterprise TypeScript server infrastructure: decorator-driven dependency injection, the repository pattern, and a component system - running on Hono at ~140k req/s with Drizzle's type-safe SQL.
You write controllers, services, and repositories. IGNIS wires them, validates every request against Zod, and generates the OpenAPI spec from the same schemas.
bun add @venizia/ignis @venizia/ignis-helpers hono @hono/zod-openapi drizzle-orm pg
bun add -d typescript tsc-alias @venizia/dev-configs @types/bunImportant
experimentalDecorators and emitDecoratorMetadata must be true in your tsconfig.json, declared
inline - Bun does not resolve them through extends, and @inject is silently dropped without them.
Copy them from @venizia/dev-configs/tsconfig.common.json.
import { z } from '@hono/zod-openapi';
import {
ApiReferenceComponent, BaseApplication, BaseRestController,
controller, get, IApplicationInfo, jsonContent,
} from '@venizia/ignis';
import { HTTP } from '@venizia/ignis-helpers';
import { Context } from 'hono';
@controller({ path: '/hello' })
class HelloController extends BaseRestController {
constructor() {
super({ scope: 'HelloController', path: '/hello' });
}
override binding() {}
@get({
configs: {
path: '/',
responses: {
[HTTP.ResultCodes.RS_2.Ok]: jsonContent({
description: 'Says hello',
schema: z.object({ message: z.string() }),
}),
},
},
})
sayHello(c: Context) {
return c.json({ message: 'Hello from IGNIS!' }, HTTP.ResultCodes.RS_2.Ok);
}
}
class App extends BaseApplication {
getAppInfo(): IApplicationInfo {
return { name: 'my-app', version: '1.0.0', description: 'My first IGNIS app' };
}
staticConfigure() {}
postConfigure() {}
setupMiddlewares() {}
preConfigure() {
this.component(ApiReferenceComponent); // interactive docs at /doc/explorer
this.controller(HelloController);
}
}
new App({
scope: 'App',
config: { host: '0.0.0.0', port: 3000, path: { base: '/api', isStrict: false } },
})
.start()
.catch((error: unknown) => {
console.error('[main] Application start failed | Error:', error);
process.exit(1);
});bun run src/index.ts
curl http://localhost:3000/api/hello # {"message":"Hello from IGNIS!"}Full walkthrough: 5-minute quickstart - then build a CRUD API.
| Layered architecture | Controller -> Service -> Repository -> DataSource, each a DI binding |
| Dependency injection | ~350-line IoC container; @inject by namespaced key, tags for discovery |
| Type-safe data access | Drizzle + PostgreSQL, inferred types, transactions, relations, soft delete |
| Validation & OpenAPI | One Zod schema validates the request and generates the spec |
| Convention boot | Auto-discovers *.controller.ts, *.service.ts, *.repository.ts, *.datasource.ts |
| Components | Auth (JWT/Basic), Casbin RBAC, API reference, health, mail, storage, Socket.IO, gRPC |
| Production helpers | Logger, Redis, BullMQ, MinIO/S3, crypto, cron, Snowflake UID, TCP/UDP |
| Multi-runtime | Bun first (Bun.serve), Node.js 18+ supported via @hono/node-server |
Core API • Components & helpers • Best practices
Each builds on the one above it - a change in inversion reaches everything.
| Package | Role |
|---|---|
@venizia/ignis |
The framework: application, controllers, repositories, models, components |
@venizia/ignis-boot |
Convention-based discovery and bootstrapping |
@venizia/ignis-helpers |
Logger, Redis, queues, storage, crypto, network, UID |
@venizia/ignis-inversion |
Standalone IoC container and decorators |
@venizia/dev-configs |
Shared ESLint, Prettier, TypeScript configs |
@venizia/ignis-docs |
Documentation site and MCP server |
Yes if you are building a growing API - 10+ endpoints, real auth, several models - and want the structure to hold up as the team grows.
Probably not for a webhook receiver, a prototype, or a 3-endpoint service. Plain Hono is lighter.
| Hono / Express | NestJS / LoopBack 4 | IGNIS | |
|---|---|---|---|
| Throughput | ~150k req/s | ~25k req/s | ~140k req/s |
| Structure | do it yourself | strict | guided |
| DI | manual | built-in, heavy | built-in, ~350 lines |
| ORM | bring your own | TypeORM / Prisma | Drizzle |
| OpenAPI | manual | module | from your Zod schemas |
Longer comparison with real code: Philosophy.
Note
IGNIS is 0.x: minor versions can break. It runs in production at VENIZIA AI, and the core patterns are stable - pin exact versions and read the changelog before upgrading.
| Example | What it shows |
|---|---|
| 5-mins-qs | The single-file hello world above |
| vert | Production reference: CRUD, auth, RBAC, transactions, relations |
| typesense-search | Search connector alongside PostgreSQL |
| supabase | Supabase driver and RLS auth context |
| rpc-api-server + rpc-client-app | gRPC server with a React frontend |
| socket-io-test / websocket-test | Real-time transports |
cd examples/vert
cp .env.example .env.development # add your PostgreSQL credentials
bun install && bun run migrate:dev && bun run server:devgit clone https://github.com/venizia-ai/ignis.git && cd ignis
bun install
make build # or: make core - builds it and everything it depends on
make lint-allConventional Commits (feat:, fix:, docs:, ...), branches feature/* / fix/*, and PRs target
develop. Bun only - never npm, yarn, or pnpm. See CONTRIBUTING.md,
CODE_OF_CONDUCT.md, and SECURITY.md.
Standing on LoopBack 4 (patterns), Hono (speed), Drizzle (type-safe SQL), plus ideas from NestJS and Spring Boot.
MIT licensed - see LICENSE.md. Questions: GitHub Issues • developer@venizia.ai