.env file, a first knowledge context registered on the app, and both processes running locally.
Prerequisites
- Completed Setup —
@exulu/backendinstalled, Node.js 22.18.0. - Completed Getting started — you have
src/exulu.ts,src/server.ts, andsrc/worker.tsin some form. - A running Postgres instance and a running Redis instance (see Self-hosting quickstart if you need them locally).
What you will build
A project structured exactly as IMP expects in production: two separate entry points (server and worker), a shared app-initialization module, a firstExuluContext for a generic knowledge collection, and scripts that match the container split used in deployment.
1
Organize the folder layout
The recommended layout mirrors the production container split:Create the
src/contexts directory:2
Configure tsup
tsup compiles TypeScript into two separate output bundles — one for the server and one for the worker — that Node.js can run directly:tsup.config.ts
src/exulu.ts module at build time. tsup bundles each entry independently, so the server bundle and the worker bundle are separate files with no runtime coupling.3
Add package.json scripts
package.json
dev:server and dev:worker use tsx watch for fast iteration — file changes restart the process automatically. start:server and start:worker run the compiled output for production.4
Create the .env file
.env
@exulu/backend auto-loads this file via a dotenv/config import it prepends to every bundle — you do not need to call dotenv yourself.5
Define a first context
Create This context has no data source yet — you will add items manually through the IMP UI or programmatically via
src/contexts/index.ts with a simple knowledge context:src/contexts/index.ts
createItem(). See Defining contexts for a full context with sources and embedder queues.6
Wire everything in exulu.ts
src/exulu.ts
requireSystemDependencies: false lets the server start even if pandoc or soffice are not installed locally. Remove this flag in production or when you need document processing.7
Write server.ts and worker.ts
src/server.ts
src/worker.ts
ready (the unresolved promise) and await it independently. app.express.init() registers routes and starts the LiteLLM proxy supervisor when EXULU_USE_LITELLM=true. app.bullmq.workers.create() connects to Redis and starts consuming all registered queues.8
Run the project
Open two terminals.Terminal 1 — server:On the very first boot you will see:Terminal 2 — worker:The worker connects to Redis and starts processing jobs. With
team_knowledge registered, it will embed any items you add to the context.What you built
- A tsup project with separate server and worker entry points.
- A
.env-driven configuration that the package loads automatically. - A first
ExuluContext(team_knowledge) registered on the app, ready to store items and generate embeddings on insert. - Two development scripts that hot-reload on file change.
Next steps
Defining contexts
Add fields, sources, and embedder queues to build production-ready contexts.
Data sources and sync
Pull data from an external API on a cron schedule.
Queues and workers
Register BullMQ queues and scope your worker process.
Custom tools
Give agents callable functions backed by your own code.