From 2b7fd1d1e7ff59a2c50aed82d79e7923f4874efa Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Wed, 3 Dec 2025 15:12:58 +0000 Subject: [PATCH] Improve field location detection and add comprehensive documentation Co-authored-by: estruyf <2900833+estruyf@users.noreply.github.com> --- src/commands/StatusListener.ts | 20 ++++++++++++--- src/helpers/ContentTypeSchemaGenerator.ts | 30 +++++++++++++++++++++++ src/helpers/FrontMatterValidator.ts | 20 +++++++++++++++ 3 files changed, 66 insertions(+), 4 deletions(-) diff --git a/src/commands/StatusListener.ts b/src/commands/StatusListener.ts index b2327d66..9e1400a4 100644 --- a/src/commands/StatusListener.ts +++ b/src/commands/StatusListener.ts @@ -209,13 +209,25 @@ export class StatusListener { const frontMatterEnd = frontMatterMatch ? frontMatterMatch[0].length : text.length; for (const error of errors) { - // Find the field in the document - const fieldPath = error.field.split('.'); - const fieldName = fieldPath[fieldPath.length - 1]; + // For required field errors, use the missing property name + let fieldName = ''; + if (error.keyword === 'required' && error.params?.missingProperty) { + fieldName = error.params.missingProperty; + } else { + // Find the field in the document + const fieldPath = error.field.split('.'); + fieldName = fieldPath[fieldPath.length - 1]; + } + + if (!fieldName || fieldName === 'root') { + continue; // Skip if we can't determine field name + } // Try to find the field location in the front matter section only + // Note: This is a simple implementation that may match partial strings + // Future improvement: Use YAML AST parsing for exact field locations const searchText = text.substring(0, frontMatterEnd); - const fieldIdx = searchText.indexOf(fieldName); + const fieldIdx = searchText.indexOf(`${fieldName}:`); if (fieldIdx !== -1) { const posStart = editor.document.positionAt(fieldIdx); diff --git a/src/helpers/ContentTypeSchemaGenerator.ts b/src/helpers/ContentTypeSchemaGenerator.ts index 8783d4cd..5f4984b9 100644 --- a/src/helpers/ContentTypeSchemaGenerator.ts +++ b/src/helpers/ContentTypeSchemaGenerator.ts @@ -24,6 +24,36 @@ export interface JSONSchema { /** * Generates JSON Schema from Front Matter Content Type definitions + * + * This utility converts Front Matter content type definitions into JSON Schema format + * which can then be used for validation. It handles all field types supported by + * Front Matter CMS including nested fields, blocks, and field groups. + * + * Field Type Mappings: + * - string, slug, image, file, customField → string + * - number → number (with optional min/max) + * - boolean, draft → boolean + * - datetime → string with date-time format + * - choice → string with enum (or array if multiple) + * - tags, categories, taxonomy, list → array of strings + * - fields → nested object with properties + * - block → array of objects with oneOf for field groups + * - json → any valid JSON type + * - dataFile, contentRelationship → string or array + * + * Features: + * - Required field validation + * - Type validation + * - Enum/choice validation + * - Number range validation (min/max) + * - Nested object support + * - Block field support with multiple field group options + * + * Usage: + * ```typescript + * const schema = ContentTypeSchemaGenerator.generateSchema(contentType); + * // Use schema for validation with AJV or other JSON Schema validators + * ``` */ export class ContentTypeSchemaGenerator { /** diff --git a/src/helpers/FrontMatterValidator.ts b/src/helpers/FrontMatterValidator.ts index 08b05789..505fa9db 100644 --- a/src/helpers/FrontMatterValidator.ts +++ b/src/helpers/FrontMatterValidator.ts @@ -14,6 +14,26 @@ export interface ValidationError { /** * Validates front matter data against content type schemas + * + * This validator uses JSON Schema validation (via AJV) to ensure that front matter + * in markdown files conforms to the structure defined in content types. + * + * Features: + * - Automatic schema generation from content type definitions + * - Type validation (string, number, boolean, datetime, arrays, etc.) + * - Required field validation + * - Enum/choice validation + * - Number range validation (min/max) + * - Nested object validation + * + * Usage: + * ```typescript + * const validator = new FrontMatterValidator(); + * const errors = validator.validate(frontMatterData, contentType); + * if (errors.length > 0) { + * // Handle validation errors + * } + * ``` */ export class FrontMatterValidator { private ajv: Ajv;