Laizy CMS
Client

Generated Client

Overview of the auto-generated TypeScript client, ManagementClient setup, and how to query content programmatically.

Generated Client

The Laizy CLI generates a fully typed TypeScript client from your schema. This client provides a Prisma-like API for querying content, with full autocomplete and type safety out of the box.

How It Works

When you run pnpm laizy generate, the CLI reads your .laizy schema file and produces three files:

FilePurpose
types.tsTypeScript interfaces for each model (BlogPost, CreateBlogPostInput, etc.)
client.tsRuntime client class with findMany(), findById(), and count() methods
index.tsRe-exports everything for clean imports

These files are written to your configured output directory (default: generated/laizy/).

Setup

The generated LaizyClient requires a ManagementClient instance for making authenticated API calls:

import { LaizyClient } from './generated/laizy';
import { ManagementClient } from '@/lib/management-client';

const managementClient = new ManagementClient({
  baseUrl: process.env.NEXT_PUBLIC_LAIZY_BASE_URL!,
  apiToken: process.env.NEXT_PUBLIC_LAIZY_TOKEN!,
  projectId: 'your-project-id',
});

const client = new LaizyClient(managementClient);

ManagementClient Options

The ManagementClient constructor accepts these options:

interface ManagementClientOptions {
  baseUrl: string;       // Laizy CMS API URL
  apiToken?: string;     // JWT token (admin or frontend)
  projectId?: string;    // Project ID for scoping requests
}
OptionRequiredDescription
baseUrlYesThe URL of your Laizy CMS instance
apiTokenYesA laizy_ prefixed JWT token
projectIdYesThe project to query content from

The ManagementClient automatically sets the Authorization and x-laizy-project headers on every request.

Client Architecture

The generated client follows a simple pattern. Each model in your schema gets its own client class, and the LaizyClient composes them all:

// Each model gets a dedicated client
class BlogPostClient {
  async findMany(options?: FindManyOptions<BlogPost>): Promise<BlogPost[]>
  async findById(id: string): Promise<BlogPost | null>
  async count(): Promise<number>
}

class AuthorClient {
  async findMany(options?: FindManyOptions<Author>): Promise<Author[]>
  async findById(id: string): Promise<Author | null>
  async count(): Promise<number>
}

// The LaizyClient composes all model clients
class LaizyClient {
  blogPost: BlogPostClient
  author: AuthorClient

  constructor(managementClient: ManagementClient)
}

The model property names are the camelCase version of the model names from your schema:

Schema ModelClient Property
BlogPostclient.blogPost
Authorclient.author
HeroSectionclient.heroSection
FooterContentclient.footerContent

Token Types

The ManagementClient works with two token types, each providing different access levels:

Admin Tokens

Full read/write access. Use these in server-side code and the CLI.

const managementClient = new ManagementClient({
  baseUrl: 'https://laizycms.com',
  apiToken: process.env.LAIZY_API_TOKEN!, // admin token
  projectId: 'your-project-id',
});

Frontend Tokens

Read-only access to published content. Safe for client-side use.

const managementClient = new ManagementClient({
  baseUrl: 'https://laizycms.com',
  apiToken: process.env.NEXT_PUBLIC_LAIZY_TOKEN!, // frontend token
  projectId: 'your-project-id',
});

Never expose admin tokens in client-side code. Use frontend tokens (scope: content:read) for any code that runs in the browser. Admin tokens are for server-side code, CLI tools, and API routes only.

Quick Example

import { LaizyClient } from './generated/laizy';
import { ManagementClient } from '@/lib/management-client';

const managementClient = new ManagementClient({
  baseUrl: process.env.NEXT_PUBLIC_LAIZY_BASE_URL!,
  apiToken: process.env.NEXT_PUBLIC_LAIZY_TOKEN!,
  projectId: 'your-project-id',
});

const client = new LaizyClient(managementClient);

// Fetch all blog posts
const posts = await client.blogPost.findMany();

// Fetch a single post by ID
const post = await client.blogPost.findById('abc123');

// Count all authors
const authorCount = await client.author.count();

The ManagementClient Under the Hood

The ManagementClient is a thin wrapper around a tRPC client that:

  1. Sends authenticated requests with the Authorization: Bearer <token> header
  2. Includes the project context via the x-laizy-project header
  3. Uses superjson as the transformer for proper Date serialization
  4. Provides methods for content CRUD, model management, and schema operations

The generated LaizyClient delegates all API calls to the ManagementClient, which handles serialization, authentication, and error handling transparently.

Regenerating

Run pnpm laizy generate whenever you change your schema. The generated files are fully overwritten each time, so do not edit them manually. Instead, extend the LaizyClient in your own code if you need custom behavior.

Next Steps

On this page