https://github.com/aminya/mikro-typebox
Generate validation schemas from Mikro-ORM entities. Supports TypeBox, Zod, Valibot, ArkType, Effect, io-ts, Yup, and more.
https://github.com/aminya/mikro-typebox
db json-schema mikro mikro-orm schema ts-to-zod typebox typescript valibot validation yup zod
Last synced: 28 days ago
JSON representation
Generate validation schemas from Mikro-ORM entities. Supports TypeBox, Zod, Valibot, ArkType, Effect, io-ts, Yup, and more.
- Host: GitHub
- URL: https://github.com/aminya/mikro-typebox
- Owner: aminya
- License: apache-2.0
- Created: 2025-09-14T22:36:45.000Z (9 months ago)
- Default Branch: main
- Last Pushed: 2025-10-26T21:38:34.000Z (7 months ago)
- Last Synced: 2025-12-01T01:50:41.091Z (6 months ago)
- Topics: db, json-schema, mikro, mikro-orm, schema, ts-to-zod, typebox, typescript, valibot, validation, yup, zod
- Language: TypeScript
- Homepage: https://www.npmjs.com/package/mikro-typebox
- Size: 103 KB
- Stars: 1
- Watchers: 0
- Forks: 0
- Open Issues: 0
-
Metadata Files:
- Readme: README.md
- License: License.txt
Awesome Lists containing this project
README
# mikro-typebox
Generate validation schemas from Mikro-ORM entities. Supports TypeBox, Zod, Valibot, ArkType, Effect, io-ts, Yup, and more.
## Features
- 🏗️ **Entity Type Generation**: Converts Mikro-ORM entity classes to TypeScript types
- 🔄 **Multiple Validation Libraries**: Supports TypeBox, Zod, Valibot, ArkType, Effect, io-ts, Yup, and more
- 🎯 **Smart Type Resolution**: Automatically resolves entity references depending on the relation graph between entities and sorts them by dependency order
- 🔄 **Circular Reference Handling**: Automatically breaks circular references to avoid infinite recursion
- 🔄 **Partial Types**: Generates partial types for entities with optional properties
- 📦 **Collection Handling**: Handles `Collection` and `Array` with proper type mapping
## Installation
```shell
npm install --save-dev mikro-typebox
```
## CLI Usage
The package includes a command-line interface for easy usage:
Generate typebox schema from `./src/entities` to `./src/entity-validators.ts`
```shell
npx mikro-typebox generate
```
Generate Zod schema from `./src/entities` to `./src/entity-validators.ts`
```shell
npx mikro-typebox generate --target zod
```
Generate Valibot schema from `./src/models` to `./src/validators.ts`
```shell
npx mikro-typebox generate --target valibot --entities ./src/models --output ./src/validators.ts
```
### CLI Options
#### `generate` command
- `-e, --entities `: Directory containing entity files (default: `./src/entities`)
- `-o, --output `: Output file path (default: `./src/entity-validators.ts`)
- `--no-write`: Print the code to the console instead of writing to a file (default: writes to a file)
- `-t, --target `: Target validation library (default: `typebox`)
- `--partials`, `--no-partials`: Generate partial types instead of inline primary key references (default: `true` for `typebox`)
### Supported Validation Libraries
- `typebox` - TypeBox (default)
- `zod` - Zod
- `valibot` - Valibot
- `arktype` - ArkType
- `effect` - Effect
- `io-ts` - io-ts
- `yup` - Yup
- `json-schema` - JSON Schema
- `javascript` - JavaScript
- `typescript` - TypeScript
- `value` - Value
## Programmatic Usage
You can also use the API to generate validation schemas programmatically.
### `generateEntityValidator(options)`
Generates validation schemas from Mikro-ORM entities.
#### Parameters
- `options.entitiesDir` (optional): Directory containing the entity files (default: `"./src/entities"`)
- `options.outputFile` (optional): File path to write the generated code (default: `"./src/entity-validators.ts"`)
- `options.write` (optional): Whether to write the code to a file (default: `true`)
- `options.targetValidationLibrary` (optional): Target validation library (default: `"typebox"`)
- `options.partials` (optional): Whether to generate partial types instead of inline primary key references (default: `true` for `typebox`)
### `generateEntityTypes(code, entityIdTypes)`
Converts Mikro-ORM entity code to TypeScript types.
#### Parameters
- `code`: The entity code as a string
- `entityIdTypes` (optional): Map of entity names to their ID types
### `generateEntityFileTypes(fileContents)`
Processes multiple entity files and generates types with proper entity ID replacement.
#### Parameters
- `fileContents`: Array of entity file contents as strings
## Usage Examples
```typescript
import { generateEntityValidator } from "mikro-typebox";
// Generate for TypeBox
await generateEntityValidator({
entitiesDir: "./src/entities",
outputFile: "./src/validators.ts",
write: true,
partials: true,
});
// Generate for Zod
const zodCode = await generateEntityValidator({
entitiesDir: "./src/entities",
targetValidationLibrary: "zod",
outputFile: "./src/zod-validators.ts",
write: true,
});
// Generate for Valibot
const valibotCode = await generateEntityValidator({
entitiesDir: "./src/entities",
targetValidationLibrary: "valibot",
outputFile: "./src/valibot-validators.ts",
write: true,
});
```
### Working with Entity Files
Given a Mikro-ORM entity file like this:
```typescript
// src/entities/User.ts
import {
Entity,
PrimaryKey,
Property,
Collection,
OneToMany,
} from "@mikro-orm/core";
import { Book } from "./Book";
@Entity()
export class User {
@PrimaryKey()
id!: number;
@Property()
name!: string;
@Property()
email!: string;
@OneToMany(() => Book, (book) => book.author)
books = new Collection(this);
constructor({ name, email }: User) {
this.name = name;
this.email = email;
}
}
// src/entities/Book.ts
import { Entity, PrimaryKey, Property, ManyToOne } from "@mikro-orm/core";
import { User } from "./User";
@Entity()
export class Book {
@PrimaryKey()
id!: number;
@Property()
title!: string;
@ManyToOne(() => User)
author!: User;
constructor({ title, author }: Book) {
this.title = title;
this.author = author;
}
}
```
And then generate validation schemas (e.g., with TypeBox):
```typescript
import { Type, Static, TSchema } from "@sinclair/typebox";
export namespace schema {
export type Collection = Static<
ReturnType>
>;
export const Collection = (T: T) =>
Type.Object(
{},
{
additionalProperties: T,
},
);
export type Book = Static;
export const Book = Type.Object({
id: Type.Number(),
title: Type.String(),
author: schema.PartialUser,
});
export type PartialBook = Static;
export const PartialBook = Type.Object({
id: Type.Number(),
title: Type.Optional(Type.String()),
author: Type.Optional(schema.PartialUser),
});
export type User = Static;
export const User = Type.Object({
id: Type.Number(),
name: Type.String(),
email: Type.String(),
books: Type.Union([
Collection(
Type.Object({
id: Type.Number(),
}),
),
Type.Array(
Type.Object({
id: Type.Number(),
}),
),
]),
});
export type PartialUser = Static;
export const PartialUser = Type.Object({
id: Type.Number(),
name: Type.Optional(Type.String()),
email: Type.Optional(Type.String()),
books: Type.Optional(
Type.Union([
Collection(
Type.Object({
id: Type.Number(),
}),
),
Type.Array(
Type.Object({
id: Type.Number(),
}),
),
]),
),
});
}
```
or for Zod
```typescript
import { z } from "zod";
export type schema_Book = z.infer;
export const schema_Book = z.object({
id: z.number(),
title: z.string(),
author: z.object({
id: z.number(),
}),
});
export type schema_User = z.infer;
export const schema_User = z.object({
id: z.number(),
name: z.string(),
email: z.string(),
books: z.union([
z.object({}),
z.array(
z.object({
id: z.number(),
}),
),
]),
});
```
### Programmatic Usage
```typescript
import { generateEntityTypes, generateEntityFileTypes } from "mikro-typebox";
// Process a single entity file
const entityCode = `
import { Entity, PrimaryKey, Property } from '@mikro-orm/core';
@Entity()
export class Product {
@PrimaryKey()
id!: number;
@Property()
name!: string;
}
`;
const types = generateEntityTypes(entityCode);
console.log(types);
// Output: export type Product = { id: number; name: string; };
// Process multiple entity files
const fileContents = [entityCode, anotherEntityCode];
const allTypes = generateEntityFileTypes(fileContents);
```
## How It Works
1. **Entity Discovery**: Scans entity files for classes decorated with `@Entity()`
2. **Type Extraction**: Extracts property types and relationships from entity classes
3. **ID Type Resolution**: Replaces entity references with their primary key types
4. **Collection Conversion**: Converts `Collection` to `Array` with proper type mapping
5. **Code Cleanup**: Removes Mikro-ORM specific imports, decorators, and method calls
6. **Schema Generation**: Converts TypeScript types to validation schemas using the target library
## License
Apache-2.0, Copyright (c) 2025 Amin Yara