or run

npx @tessl/cli init
Log in

Version

Tile

Overview

Evals

Files

docs

configuration.mdcontext.mdi18n.mdindex.mdplugin-system.mdrouting.mdswizzling.md
tile.json

routing.mddocs/

Routing System

Route definition, metadata, modules, and chunk management for client-side navigation and code splitting.

Capabilities

RouteConfig

Core route configuration structure for defining pages and their properties.

/**
 * Route configuration for a single page or layout
 */
interface RouteConfig {
  /** Route path with leading slash. Trailing slash normalized by config. */
  path: string;
  
  /** Component path that the bundler can require to render this route */
  component: string;
  
  /** Props modules - each entry maps prop name to module path */
  modules?: RouteModules;
  
  /** Route context data available via useRouteContext hook */
  context?: RouteModules;
  
  /** Nested routes for layout components with subroutes */
  routes?: RouteConfig[];
  
  /** Exact routes don't match subroutes (React Router option) */
  exact?: boolean;
  
  /** Strict routes are sensitive to trailing slash (React Router option) */
  strict?: boolean;
  
  /** Route priority for matching order (higher priority matched first) */
  priority?: number;
  
  /** Optional metadata for the route */
  metadata?: RouteMetadata;
  
  /** Direct props object (converted to module internally) */
  props?: {[propName: string]: unknown};
  
  /** Additional route attributes available on client */
  [attributeName: string]: unknown;
}

PluginRouteConfig

Route configuration with plugin identification for tracking route ownership.

/**
 * Route configuration with plugin identifier
 */
interface PluginRouteConfig extends RouteConfig {
  /** Plugin that created this route */
  plugin: PluginIdentifier;
}

Route Metadata

Optional metadata that plugins can attach to routes.

/**
 * Optional metadata for routes (Node.js side only)
 */
interface RouteMetadata {
  /** Source file path that created this route (relative to site directory) */
  sourceFilePath?: string;
  
  /** 
   * Last updated timestamp for this route
   * - undefined: not computed
   * - null: computed but no value found (untracked files)
   * - number: timestamp in milliseconds
   */
  lastUpdatedAt?: number | null;
}

Module System

Module system for code splitting and lazy loading of route data.

/**
 * A serialized data module for client-side import
 */
type Module =
  | {
      /** Import marker to distinguish from nested objects */
      __import?: boolean;
      /** File path for bundler to require */
      path: string;
      /** Query parameters for the import */
      query?: ParsedUrlQueryInput;
    }
  | string; // Simple file path

/**
 * Nested structure of modules for route data
 */
interface RouteModules {
  [propName: string]: Module | RouteModules | RouteModules[];
}

Usage Example:

import type { RouteConfig, RouteModules } from "@docusaurus/types";

// Simple route with component only
const simpleRoute: RouteConfig = {
  path: '/about',
  component: '@site/src/pages/About.tsx'
};

// Route with modules for props
const blogRoute: RouteConfig = {
  path: '/blog',
  component: '@theme/BlogListPage',
  modules: {
    // Props will be injected from these modules
    posts: '@generated/blog-posts.json',
    metadata: {
      path: '@generated/blog-metadata.json',
      query: { version: '1.0' }
    }
  }
};

// Layout route with nested routes
const docsLayout: RouteConfig = {
  path: '/docs',
  component: '@theme/DocsRoot',
  routes: [
    {
      path: '/docs/intro',
      component: '@theme/DocPage',
      exact: true
    }
  ]
};

Route Context

Runtime context available to route components via hooks.

/**
 * Base route context with plugin-specific data
 */
interface RouteContext {
  /** Plugin-specific context data */
  data?: {[key: string]: unknown};
}

/**
 * Route context for plugin-created routes with plugin information
 */
interface PluginRouteContext extends RouteContext {
  /** Information about the plugin that created this route */
  plugin: {
    id: string;
    name: string;
  };
}

Code Splitting System

Types for managing code splitting and chunk loading.

/**
 * Chunk names structure mirroring RouteModules
 */
interface ChunkNames {
  [propName: string]: string | ChunkNames | ChunkNames[];
}

/**
 * Mapping from route paths (with hash) to chunk names
 */
interface RouteChunkNames {
  [routePathHashed: string]: ChunkNames;
}

/**
 * Registry for react-loadable with module loading information
 */
interface Registry {
  readonly [chunkName: string]: [
    Loader: () => Promise<any>,
    ModuleName: string,
    ResolvedModuleName: string,
  ];
}

Usage Example:

// Example of how chunks are organized
const exampleChunkNames: ChunkNames = {
  content: "blog-post-123",
  metadata: "blog-metadata-456",
  sidebar: {
    items: "sidebar-items-789",
    config: "sidebar-config-101"
  }
};

// Route chunk names map routes to their chunks
const routeChunkNames: RouteChunkNames = {
  "/blog/my-post-abcd1234": {
    content: "content-chunk-123",
    props: "props-chunk-456"
  }
};

Route Creation Workflow

Here's how routes are typically created by plugins:

import type { Plugin } from "@docusaurus/types";

const myPlugin: Plugin = {
  name: 'my-plugin',
  
  async contentLoaded({ content, actions }) {
    const { addRoute, createData } = actions;
    
    // Create data files for props
    const propsPath = await createData(
      'my-data.json', 
      JSON.stringify({ title: 'My Page' })
    );
    
    // Add route with the data module
    addRoute({
      path: '/my-page',
      component: '@site/src/components/MyPage.tsx',
      modules: {
        props: propsPath
      },
      exact: true,
      metadata: {
        sourceFilePath: 'src/content/my-page.md'
      }
    });
  }
};

Client-Side Route Usage

On the client side, route data is accessible through hooks:

import { useRouteContext } from '@docusaurus/router';
import type { PluginRouteContext } from '@docusaurus/types';

function MyComponent() {
  const context = useRouteContext() as PluginRouteContext;
  
  // Access plugin information
  console.log(context.plugin.name); // 'my-plugin'
  console.log(context.plugin.id);   // 'default'
  
  // Access custom context data
  const customData = context.data?.customField;
  
  return <div>Content here</div>;
}