mdbook-lint-core 0.13.1

Core linting engine for mdbook-lint - library for markdown linting with mdBook support
Documentation

Core linting engine for mdbook-lint

This crate provides the foundational infrastructure for markdown linting with mdBook support. It defines the core abstractions and engine that powers mdbook-lint's rule-based linting system.

Overview

The mdbook-lint-core crate provides:

  • Plugin-based architecture for extensible rule sets
  • AST and text-based linting with efficient document processing
  • Violation reporting with detailed position tracking and severity levels
  • Automatic fix infrastructure for correctable violations
  • Configuration system for customizing rule behavior
  • Document abstraction with markdown parsing via comrak

Architecture

The core follows a plugin-based architecture where rules are provided by external crates:

┌─────────────────┐
│   Application   │
└────────┬────────┘
         │
┌────────▼────────┐
│  PluginRegistry │ ◄─── Registers rule providers
└────────┬────────┘
         │
┌────────▼────────┐
│   LintEngine    │ ◄─── Orchestrates linting
└────────┬────────┘
         │
┌────────▼────────┐
│     Rules       │ ◄─── Individual rule implementations
└─────────────────┘

Basic Usage

Creating a Lint Engine

use mdbook_lint_core::{PluginRegistry, Document};
use std::path::PathBuf;

// Create an empty engine (no rules registered)
let registry = PluginRegistry::new();
let engine = registry.create_engine()?;

// Lint a document
let document = Document::new("# Hello\n\nWorld".to_string(), PathBuf::from("test.md"))?;
let violations = engine.lint_document(&document)?;

// No violations since no rules are registered
assert_eq!(violations.len(), 0);
# Ok::<(), Box<dyn std::error::Error>>(())

With Rule Providers

use mdbook_lint_core::{PluginRegistry, Document};
// Assumes mdbook-lint-rulesets is available
// use mdbook_lint_rulesets::{StandardRuleProvider, MdBookRuleProvider};
use std::path::PathBuf;

let mut registry = PluginRegistry::new();

// Register rule providers
// registry.register_provider(Box::new(StandardRuleProvider))?;
// registry.register_provider(Box::new(MdBookRuleProvider))?;

// Create engine with registered rules
let engine = registry.create_engine()?;

// Lint a document
let content = "# Title\n\n\n\nToo many blank lines";
let document = Document::new(content.to_string(), PathBuf::from("test.md"))?;
let violations = engine.lint_document(&document)?;

// Process violations
for violation in violations {
    println!("{}:{} - {}", violation.rule_id, violation.line, violation.message);
}
# Ok::<(), Box<dyn std::error::Error>>(())

Key Types

Document

Represents a markdown file with its content and metadata:

use mdbook_lint_core::Document;
use std::path::PathBuf;
use comrak::Arena;

let doc = Document::new(
    "# My Document\n\nContent here".to_string(),
    PathBuf::from("doc.md")
)?;

// Parse AST with comrak Arena
let arena = Arena::new();
let ast = doc.parse_ast(&arena);

// Get document lines
let lines = &doc.lines;
# Ok::<(), Box<dyn std::error::Error>>(())

Violation

Represents a linting violation with location and optional fix:

use mdbook_lint_core::violation::{Violation, Severity, Fix, Position};

let violation = Violation {
    rule_id: "MD001".to_string(),
    rule_name: "heading-increment".to_string(),
    message: "Heading levels should increment by one".to_string(),
    line: 5,
    column: 1,
    severity: Severity::Warning,
    fix: Some(Fix {
        description: "Change heading level".to_string(),
        replacement: Some("## Correct Level".to_string()),
        start: Position { line: 5, column: 1 },
        end: Position { line: 5, column: 20 },
    }),
};

Rule Traits

Rules can be implemented using different traits based on their needs:

  • Rule - Base trait for all rules
  • AstRule - For rules that analyze the markdown AST
  • TextRule - For rules that analyze raw text
  • RuleWithConfig - For rules that support configuration

Configuration

Rules can be configured through TOML configuration files:

# .mdbook-lint.toml
[rules.MD013]
line_length = 120
code_blocks = false

[rules.MD009]
br_spaces = 2

# Disable specific rules
[rules]
MD002 = false
MD041 = false

Features

This crate has no optional features. All functionality is included by default.