[data-reveal]{opacity:1!important;transform:none!important}
Building

Project setup

Set up a normal AntelopeJS project that loads the DMS as a dependency and registers its own pages.

This is the common case: you build an AntelopeJS application — an admin backend for your product — and you want the DMS to provide the dashboard, auth, and component system while your code defines the pages, data, and business logic. You don't author a distributable DMS module; you build a normal AntelopeJS project that loads the DMS as a dependency and registers its own pages directly.

If instead you package a reusable extension to ship to other projects, see Distributable module. It uses the same page and component APIs — only the packaging differs.

Project layout

A typical project:

my-app/
my-app/
  antelope.config.ts        # THE project: which modules to load (incl. the DMS) and their config
  package.json              # deps: @antelopejs-private/cms + @antelopejs-private/cms-nuxt + the stack
  src/
    index.ts                # your project's module: construct/start/stop lifecycle + AddNuxtLayer
    pages/                  # @RegisterPage classes                         → Pages & components
    data-api/               # DataControllers (TableViews attach on pages)  → Data controller
    data-types/             # custom DataTypes                              → Data types
    permissions/            # RegisterPermission                            → Auth & permissions
    db/                     # @RegisterTable models / schema
    routes/                 # @Controller HTTP routes                       → Pages & components
    services/               # your business logic
  nuxt-layer/               # OPTIONAL — your own frontend layer (custom Vue) → Frontend layer
  package.json

antelope.config.ts — loading the DMS and the stack

The config is the heart of a project: it declares which modules to load (the DMS plus the infrastructure it needs) and their per-module config. Your own code loads as a module with a local source (source.type: "local") — the module key (local below) is just a name; pick any.

antelope.config.ts
import { defineConfig } from "@antelopejs/interface-core/config";

export default defineConfig({
  name: "my-app",
  modules: {
    // 1. Your own project code — a local-source module, built before run.
    local: {
      source: {
        type: "local",
        path: ".",
        watchDir: ["src"],
        installCommand: ["npm install", "npx tsc"], // first install / full build
        reloadCommand: "npx tsc", // recompile on watched-file changes
      },
      config: {
        /* your project's Config — flows to construct(config) in src/index.ts */
      },
    },

    // 2. The DMS itself.
    "@antelopejs-private/cms": {
      source: { type: "package", package: "@antelopejs-private/cms", version: "0.2.0" },
      config: {
        apiBaseUrl: "http://localhost:5010", // where the backend is reachable
        clientBaseUrl: "http://localhost:3001", // where the dashboard frontend is served
      },
    },

    // 3. The infrastructure the DMS and your app need. A typical stack:
    "@antelopejs/api": {
      source: { type: "package", package: "@antelopejs/api", version: "1.2.0" },
      config: {
        servers: [{ protocol: "http", port: "5010" }],
      },
    },
    "@antelopejs/data-api": {
      source: { type: "package", package: "@antelopejs/data-api", version: "1.1.1" },
      config: {},
    },
    "@antelopejs/mongodb": {
      source: { type: "package", package: "@antelopejs/mongodb", version: "1.2.2" },
      config: { url: "mongodb://127.0.0.1:27017", database: "myapp" },
    },
    "@antelopejs/auth-jwt": {
      source: { type: "package", package: "@antelopejs/auth-jwt", version: "1.0.0" },
      config: { secret: "" }, // the auth-jwt module's own signing secret
    },
    "@antelopejs/redis": {
      source: { type: "package", package: "@antelopejs/redis", version: "1.0.1" },
      config: { url: "redis://localhost:6379" },
    },
    // …plus file-storage, payments, email, etc. as your app needs.
  },
});

Key points:

  • The DMS needs an API module (HTTP server), a database (e.g. mongodb), auth-jwt, and usually redis; wire each in modules. Table decorators come from the @antelopejs/interface-database-decorators library — no dedicated module is required.
  • The DMS's own config you touch most: apiBaseUrl, clientBaseUrl, and auth.jwtSecret (the DMS's own session-token signing secret — set a strong value in production). Every key, every default, and the auth/htmlRender/realtime blocks are in Configuration.
  • The DMS auto-registers its base dashboard layer — the core UI (shell, login, component vocabulary) that renders standard pages. A frontend layer is included by its AddNuxtLayer call, not by config (see Frontend layer). A pages-only project needs no layer of its own.

Your project's lifecycle (src/index.ts)

A project is itself a module — the lifecycle (construct, start, …) is a framework concept, covered in Creating a module. The side-effect imports run your @RegisterPage/@RegisterDataType/etc. decorators, and construct(config) receives the local module's config.

src/index.ts
import "./pages"; // @RegisterPage
import "./db"; // models / schema
import "./data-api"; // DataControllers
import "./routes"; // @Controller

export interface Config {
  /* whatever you put under modules.local.config */
}
let globalConfig: Config = {
  /* defaults */
};
export function getConfig(): Config {
  return globalConfig;
}

export function construct(config: Config): void {
  globalConfig = config;
}

A custom frontend layer is optional and attached with AddNuxtLayer from start() — see Frontend layer.

What you register (same APIs as everywhere)

Once the project is wired, building the actual admin is identical to the rest of these docs — none of it is project-specific:

You want to…UseDoc
Add a dashboard screen@RegisterPage + PageController, attached to pagesCategory or a CategoryPages & components
Show a table / CRUDDataController + TableViewRoutes / TableViewData controller, Tables
A custom field/column type@RegisterDataType extending DataTypeData types
Custom actions, cross-component reactivity.action(), .watch(), ActionTargetActions & reactivity
Gate pages/routes, define permissionscms-auth + cms/guards decorators, RegisterPermissionAuth & permissions
Hooks, notifications, job locks, HTML rendercms/hooks, cms-notifications, job-locks, cms-html-renderBackend services
Custom Vue in your dashboardyour nuxt-layer/Frontend layer

Running

Two coupled processes (full detail in Architecture and Frontend layer):

  • Backendajs project dev -w (watch). Most projects also bring up infra (Mongo/Redis) in Docker first, e.g. a dev script of docker-compose up -d && ajs project dev --inspect -w.
  • Frontend — the cms-nuxt loader: acms dev. It auto-discovers the backend, so -b <apiBaseUrl> is optional (see Frontend CLI). Projects conventionally expose this as a frontend:dev npm script.

In production you build both processes once and launch them from their build artifacts, with production secrets and Redis. Deployment covers the build commands, startup order, and the production checklist.