Syntax Reference
Complete reference for SchemaLang syntax, types, and modifiers.
Overview
SchemaLang uses a declarative syntax to define data structures. Each definition consists of structs (record types), fields (data members), and optional enums (enumeration types).
Basic Pattern
struct StructName {
type: fieldName: modifiers: description("text");
}
Struct Definition
Basic Struct
struct User {
int64: id: primary_key: required: auto_increment:
description("User ID");
string: username: required:
description("Username");
}
Versioned Struct
Add versioning for migration support:
struct User: version(1.2.0) {
int64: id: primary_key: required: auto_increment:
description("User ID");
string: username: required:
description("Username");
}
Generator-Specific Structs
Control which generators process this struct:
// Only generate for C++ and SQLite
struct InternalData: gens_enabled(Cpp, SQLite) {
string: data: required: description("Internal data");
}
// Exclude from JSON generation
struct SecureData: gens_disabled(Json) {
string: password: required: description("Password");
}
Field Syntax
Field Components
Every field has four required parts:
type: fieldName: modifiers: description("text");
| Component | Description | Required |
|---|---|---|
type |
Data type (primitive, array, enum, or struct) | ✓ |
fieldName |
Identifier for the field | ✓ |
modifiers |
Constraints and attributes (separated by colons) | ✓ (at least one) |
description |
Human-readable documentation | ✓ |
Multi-Line Fields
Long field definitions can span multiple lines:
struct Product {
int64: id: primary_key: required: auto_increment:
description("Product identifier");
string: name: required: unique:
description("Product name, must be unique across catalog");
double: price: required:
description("Price in USD");
}
Data Types
Integer Types
| Type | Size | Range |
|---|---|---|
int8 |
8-bit | -128 to 127 |
int16 |
16-bit | -32,768 to 32,767 |
int32 |
32-bit | -2,147,483,648 to 2,147,483,647 |
int64 |
64-bit | -9,223,372,036,854,775,808 to 9,223,372,036,854,775,807 |
uint8 |
8-bit unsigned | 0 to 255 |
uint16 |
16-bit unsigned | 0 to 65,535 |
uint32 |
32-bit unsigned | 0 to 4,294,967,295 |
uint64 |
64-bit unsigned | 0 to 18,446,744,073,709,551,615 |
Floating Point Types
| Type | Precision | Use Case |
|---|---|---|
float |
Single (32-bit) | General floating-point numbers |
double |
Double (64-bit) | High-precision calculations |
Other Primitive Types
| Type | Description |
|---|---|
bool |
Boolean value (true/false) |
string |
Text string (UTF-8) |
void |
No value (mainly for function returns) |
Complex Types
Arrays
struct Post {
array<string>: tags: optional:
description("Post tags");
array<Comment>: comments: optional:
description("Post comments");
}
References
struct Comment {
int64: postId: required: reference(Post.id):
description("Parent post ID");
}
Custom Types (Other Structs)
struct User {
Profile: profile: required:
description("User profile");
}
Modifiers
Core Modifiers
| Modifier | Description | Example |
|---|---|---|
required |
Field must have a value | string: name: required |
optional |
Field can be null/empty | string: nickname: optional |
unique |
Value must be unique | string: email: unique |
primary_key |
Primary key field | int64: id: primary_key |
auto_increment |
Auto-increment on insert | int64: id: auto_increment |
Relationship Modifiers
| Modifier | Description | Example |
|---|---|---|
reference(Struct.field) |
Foreign key relationship | int64: userId: reference(User.id) |
Array Modifiers
| Modifier | Description | Example |
|---|---|---|
unique_items |
Array elements must be unique | array<string>: tags: unique_items |
min_items(n) |
Minimum array length | array<string>: tags: min_items(1) |
max_items(n) |
Maximum array length | array<string>: tags: max_items(10) |
Generator Control Modifiers
| Modifier | Description | Example |
|---|---|---|
gens_enabled(...) |
Only generate for listed generators | string: data: gens_enabled(Cpp,SQLite) |
gens_disabled(...) |
Exclude from listed generators | string: password: gens_disabled(Json) |
Enumerations
Basic Enum
enum UserRole {
Guest,
User,
Moderator,
Admin
}
Enum with Explicit Values
enum Status {
Inactive = 0,
Active = 1,
Suspended = 2,
Banned = 3
}
Using Enums in Structs
enum UserRole {
Guest,
User,
Admin
}
struct User {
int64: id: primary_key: required: auto_increment:
description("User ID");
string: username: required:
description("Username");
UserRole: role: required:
description("User role");
}
Note: Enums must be defined before they are used in struct definitions.
Include Directives
Split your schema across multiple files:
types.schema
enum UserRole {
Guest,
User,
Admin
}
struct Address {
string: street: required: description("Street address");
string: city: required: description("City");
string: country: required: description("Country");
}
user.schema
include "./types.schema"
struct User {
int64: id: primary_key: required: auto_increment:
description("User ID");
string: username: required:
description("Username");
UserRole: role: required:
description("User role");
Address: address: optional:
description("User address");
}
Included files are merged into the same namespace, allowing you to reference types across files.
Best Practices
- Always include descriptions - They're required and help document your schema
- Use int64 for IDs - Provides sufficient range for most use cases
- Explicitly mark required/optional - Makes intent clear
- Use enums for constrained values - Better than magic numbers or strings
- Version your structs - Enable automatic migration support
- Organize with includes - Split large schemas into logical files