JSON Type Definition представляет собой стандарт описания структуры JSON-данных, ориентированный на простоту и строгую типизацию. В отличие от JSON Schema, JTD делает акцент на минимальном наборе конструкций, достаточном для описания типов данных, исключая сложные логические выражения и избыточные механизмы валидации.
Библиотека Ajv поддерживает JTD как отдельный режим компиляции схем, обеспечивая быстрые проверки данных и строгую типизацию на основе декларативного описания структуры.
Ключевая особенность JTD заключается в том, что схема описывает не набор ограничений, а тип данных, что делает её ближе к моделям типов в языках программирования.
JTD работает с фиксированным набором типов:
booleanstringfloat32 / float64int8, uint8, int16,
uint16, int32timestampenumpropertiesoptionalPropertiesvalueselementsdiscriminatorКаждый тип описывает конкретную структуру данных без необходимости комбинирования логических операторов.
В JTD отсутствуют конструкции:
oneOfanyOfallOfnotЭто упрощает валидацию и делает схемы более предсказуемыми. Вместо композиции логики используется строгая структура объектов.
Ajv требует явного включения поддержки JTD-режима через дополнительные пакеты или конфигурацию.
import Ajv from "ajv/dist/jtd";
const ajv = new Ajv();
В этом режиме компилятор схем работает исключительно с JTD-структурами, игнорируя JSON Schema.
const schema = {
type: "string"
};
const validate = ajv.compile(schema);
validate("text"); // true
validate(123); // false
const schemaInt = {
type: "int32"
};
const schemaFloat = {
type: "float64"
};
JTD различает типы чисел по диапазону и представлению, что позволяет строго контролировать входные данные.
const schema = {
type: "boolean"
};
Поддерживаются только значения true и
false, любые преобразования отсутствуют.
const schema = {
properties: {
id: { type: "string" },
age: { type: "uint8" }
}
};
Особенность properties заключается в том, что все
указанные поля являются обязательными.
const schema = {
properties: {
id: { type: "string" }
},
optionalProperties: {
nickname: { type: "string" }
}
};
Если nickname отсутствует в объекте, валидация не
проваливается.
JTD не допускает произвольных полей, если они не описаны явно.
const schema = {
properties: {
id: { type: "string" }
}
};
Объекты с дополнительными полями считаются невалидными.
const schema = {
elements: {
type: "string"
}
};
Описывает массив строк.
Пример:
validate(["a", "b", "c"]); // true
validate([1, 2, 3]); // false
const schema = {
enum: ["admin", "user", "guest"]
};
Любое значение вне списка считается невалидным.
const schema = {
properties: {
user: {
properties: {
id: { type: "string" },
roles: {
elements: {
enum: ["admin", "editor", "viewer"]
}
}
}
}
}
};
Такие структуры позволяют строить типизированные модели данных без использования логических операторов.
JTD поддерживает дискриминатор для выбора структуры объекта по значению поля.
const schema = {
discriminator: "type",
mapping: {
admin: {
properties: {
type: { type: "string" },
permissions: {
elements: { type: "string" }
}
}
},
user: {
properties: {
type: { type: "string" },
email: { type: "string" }
}
}
}
};
Поле type определяет, какая схема применяется к объекту.
Это заменяет сложные конструкции условной логики.
validate({
type: "admin",
permissions: ["read", "write"]
}); // true
Ajv компилирует JTD-схему в оптимизированную функцию:
const validate = ajv.compile(schema);
const valid = validate(data);
При ошибке:
validate.errors;
Ошибки содержат информацию о несоответствии типов или структуры.
JTD:
JSON Schema:
JTD в Ajv компилируется в более простые функции, что снижает накладные расходы при валидации.
JTD не позволяет:
minimum/maximumJTD часто используется как источник для генерации TypeScript-типов.
Пример соответствия:
const schema = {
properties: {
id: { type: "string" },
active: { type: "boolean" }
}
};
Эквивалент TypeScript:
type Model = {
id: string;
active: boolean;
};
JTD часто применяется для описания API-контрактов:
const userSchema = {
properties: {
id: { type: "string" },
email: { type: "string" },
age: { type: "uint8" }
},
optionalProperties: {
nickname: { type: "string" }
}
};
const validateUser = ajv.compile(userSchema);
if (!validateUser(request.body)) {
throw new Error("Invalid payload");
}
JTD не предназначен для сложной бизнес-валидации. Его использование эффективно в случаях, когда:
При необходимости расширенной логики предпочтение отдается JSON Schema.
Глубокие структуры снижают читаемость и увеличивают сложность сопровождения.
Отсутствие additionalProperties требует строгого
контроля модели данных.
Полиморфизм через discriminator предпочтительнее
вложенных проверок типов.