Fields & Relations
Complete reference for the fields and relations MCP tools — field types, interfaces, and relationship workflows.
Fields Tool
Creating Fields
Critical: data is ALWAYS an array, even for a single field.
Tool: fields
Input: {
"action": "create",
"collection": "posts",
"data": [{
"field": "title",
"type": "string",
"meta": {
"interface": "input",
"note": "Post title",
"required": true
},
"schema": {
"is_nullable": false
}
}]
}
Reading Fields
Tool: fields
Input: { "action": "read", "collection": "posts" }
Or read a specific field:
Tool: fields
Input: { "action": "read", "collection": "posts", "field": "title" }
Deleting Fields
Tool: fields
Input: { "action": "delete", "collection": "posts", "field": "deprecated_field" }
Field Types Reference
| Type | Description | Typical Interface |
|---|---|---|
string |
Short text (max 255) | input |
text |
Long text (unlimited) | input-multiline, input-rich-text-md, input-rich-text-html |
uuid |
UUID identifier | input (auto-generated for PKs) |
hash |
Hashed value | input-hash |
integer |
Whole number | input |
bigInteger |
Large whole number | input |
float |
Floating point | input |
decimal |
Exact decimal | input |
timestamp |
Date + time (with timezone) | datetime |
datetime |
Date + time (no timezone) | datetime |
date |
Date only | datetime |
time |
Time only | datetime |
boolean |
True/false | boolean, toggle |
json |
JSON data | input-code, select-multiple-dropdown |
csv |
Comma-separated values | tags |
alias |
Virtual field (no column) | Used for O2M, M2M, M2A |
Common Interface Mappings
| Use Case | Type | Interface | Meta Options |
|---|---|---|---|
| Short text | string |
input |
— |
| Rich text | text |
input-rich-text-md |
— |
| Dropdown | string |
select-dropdown |
options.choices: [{text, value}] |
| Tags | json |
tags |
— |
| Toggle | boolean |
boolean |
— |
| Number | integer |
input |
— |
| Currency | decimal |
input |
options.prefix: "$" |
| Date picker | datetime |
datetime |
— |
| Color picker | string |
select-color |
— |
| Slug | string |
input |
options.slug: true |
| Image (single) | uuid |
file-image |
special: ["file"] |
| File (single) | uuid |
file |
special: ["file"] |
Relationship Types
M2O (Many-to-One)
Example: Many posts belong to one author.
Step 1: Create the M2O field (uuid type in the "many" collection):
Tool: fields
Input: {
"action": "create",
"collection": "posts",
"data": [{
"field": "author",
"type": "uuid",
"meta": {
"interface": "select-dropdown-m2o",
"special": ["m2o"],
"display": "related-values",
"display_options": { "template": "{{first_name}} {{last_name}}" }
},
"schema": {}
}]
}
Step 2: Create the relation:
Tool: relations
Input: {
"action": "create",
"collection": "posts",
"field": "author",
"data": {
"collection": "posts",
"field": "author",
"related_collection": "authors",
"schema": { "on_delete": "SET NULL" },
"meta": {}
}
}
O2M (One-to-Many)
Example: One author has many posts. This is the reverse side of M2O — an alias field on the "one" collection.
The M2O side must exist first. Then add an alias field to the "one" collection:
Tool: fields
Input: {
"action": "create",
"collection": "authors",
"data": [{
"field": "posts",
"type": "alias",
"meta": {
"interface": "list-o2m",
"special": ["o2m"],
"display": "related-values"
}
}]
}
Then create the relation from the O2M side:
Tool: relations
Input: {
"action": "create",
"collection": "posts",
"field": "author",
"data": {
"collection": "posts",
"field": "author",
"related_collection": "authors",
"schema": { "on_delete": "SET NULL" },
"meta": { "one_field": "posts" }
}
}
M2M (Many-to-Many)
Example: Posts can have many tags, tags can belong to many posts.
Step 1: Create junction collection:
Tool: collections
Input: {
"action": "create",
"data": [{
"collection": "posts_tags",
"schema": {},
"meta": { "hidden": true, "icon": "import_export" }
}]
}
Step 2: Create M2O fields in junction:
Tool: fields
Input: {
"action": "create",
"collection": "posts_tags",
"data": [
{
"field": "posts_id",
"type": "uuid",
"meta": { "hidden": true }
},
{
"field": "tags_id",
"type": "uuid",
"meta": { "hidden": true }
}
]
}
Step 3: Create alias fields on both parent collections:
Tool: fields
Input: {
"action": "create",
"collection": "posts",
"data": [{
"field": "tags",
"type": "alias",
"meta": {
"interface": "list-m2m",
"special": ["m2m"],
"display": "related-values",
"display_options": { "template": "{{tags_id.name}}" }
}
}]
}
Tool: fields
Input: {
"action": "create",
"collection": "tags",
"data": [{
"field": "posts",
"type": "alias",
"meta": {
"interface": "list-m2m",
"special": ["m2m"],
"display": "related-values"
}
}]
}
Step 4: Create relations:
Tool: relations
Input: {
"action": "create",
"collection": "posts_tags",
"field": "posts_id",
"data": {
"collection": "posts_tags",
"field": "posts_id",
"related_collection": "posts",
"schema": { "on_delete": "CASCADE" },
"meta": { "one_field": "tags", "junction_field": "tags_id" }
}
}
Tool: relations
Input: {
"action": "create",
"collection": "posts_tags",
"field": "tags_id",
"data": {
"collection": "posts_tags",
"field": "tags_id",
"related_collection": "tags",
"schema": { "on_delete": "CASCADE" },
"meta": { "one_field": "posts", "junction_field": "posts_id" }
}
}
M2A (Many-to-Any)
Polymorphic relation — items can relate to different collection types. Used for page builders, flexible content blocks.
Step 1: Create junction collection with item (uuid) and collection (string) fields:
Tool: collections
Input: {
"action": "create",
"data": [{
"collection": "page_sections",
"schema": {},
"meta": { "hidden": true }
}]
}
Step 2: Add junction fields:
Tool: fields
Input: {
"action": "create",
"collection": "page_sections",
"data": [
{ "field": "pages_id", "type": "uuid" },
{ "field": "item", "type": "uuid", "meta": { "hidden": true } },
{ "field": "collection", "type": "string", "meta": { "hidden": true } },
{ "field": "sort", "type": "integer", "meta": { "hidden": true } }
]
}
Step 3: Add M2A alias on parent:
Tool: fields
Input: {
"action": "create",
"collection": "pages",
"data": [{
"field": "sections",
"type": "alias",
"meta": {
"interface": "list-m2a",
"special": ["m2a"],
"options": {
"allowedCollections": ["headings", "paragraphs", "images", "cta_blocks"]
}
}
}]
}
File Relation (Single File)
Relate a field to directus_files:
Tool: fields
Input: {
"action": "create",
"collection": "posts",
"data": [{
"field": "featured_image",
"type": "uuid",
"meta": {
"interface": "file-image",
"special": ["file"],
"display": "image"
}
}]
}
Then create the relation to directus_files:
Tool: relations
Input: {
"action": "create",
"collection": "posts",
"field": "featured_image",
"data": {
"collection": "posts",
"field": "featured_image",
"related_collection": "directus_files",
"schema": { "on_delete": "SET NULL" },
"meta": {}
}
}
on_delete Options
| Value | Behavior |
|---|---|
SET NULL |
Set foreign key to null (default, safe) |
CASCADE |
Delete related items (use for junction tables) |
NO ACTION |
Prevent deletion if related items exist |
SET DEFAULT |
Reset to default value |
Common Mistakes
- Wrong type for relation fields — M2O fields must be
uuid, O2M/M2M/M2A fields must bealias - Missing
meta.special— M2O needs["m2o"], O2M needs["o2m"], M2M needs["m2m"], M2A needs["m2a"], files need["file"] - Forgetting junction collection — M2M requires a dedicated junction collection with two M2O fields
- Wrong schema for alias fields — Alias fields (O2M, M2M, M2A) should NOT have a
schemaproperty (or setschema: null) - Creating relations before fields — The field must exist before the relation is created
- Missing
one_fieldin M2M meta — Themeta.one_fieldtells Directus which alias field on the related collection to populate - Forgetting
junction_fieldin M2M meta — Required for M2M relations to know which field in the junction points to the other collection