squidfunk/mkdocs-material · error · PluginError

Error reading metadata of post '{path}' in '{docs}': Expecte

Error message

Error reading metadata of post '{path}' in '{docs}':
Expected metadata to be defined but found nothing

What it means

Blog posts must start with a YAML metadata block delimited by `---` lines, parsed via YAML_RE. If the regex finds no metadata block at the top of the markdown file, the Post constructor raises this PluginError because the plugin expects required metadata (title, date, etc.) to be defined.

Source

Thrown at src/plugins/blog/structure/__init__.py:73

        # Resolve path relative to docs directory
        docs = os.path.relpath(config.docs_dir)
        path = os.path.relpath(file.abs_src_path, docs)

        # Read contents and metadata immediately
        with open(file.abs_src_path, encoding = "utf-8-sig") as f:
            self.markdown = f.read()

            # Sadly, MkDocs swallows any exceptions that occur during parsing.
            # Since we want to provide the best possible user experience, we
            # need to catch errors early and display them nicely. We decided to
            # drop support for MkDocs' MultiMarkdown syntax, because it is not
            # correctly implemented anyway. When using MultiMarkdown syntax, all
            # date formats are returned as strings and list are not properly
            # supported. Thus, we just use the relevants parts of `get_data`.
            match: Match = YAML_RE.match(self.markdown)
            if not match:
                raise PluginError(
                    f"Error reading metadata of post '{path}' in '{docs}':\n"
                    f"Expected metadata to be defined but found nothing"
                )

            # Extract metadata and parse as YAML
            try:
                self.meta = yaml.load(match.group(1), SafeLoader) or {}
                self.markdown = self.markdown[match.end():].lstrip("\n")

            # The post's metadata could not be parsed because of a syntax error,
            # which we display to the author with a nice error message
            except Exception as e:
                raise PluginError(
                    f"Error reading metadata of post '{path}' in '{docs}':\n"
                    f"{e}"
                )

            # Hack: if the meta plugin is registered, we need to move the call

View on GitHub (pinned to e2136532f4)

Solutions

  1. Add a proper metadata block at the very top of the post: first line `---`, metadata, then a closing `---`
  2. Remove or move the file out of the configured `posts_dir` if it is not a blog post
  3. Check for a BOM or stray characters before the opening `---` and remove them

Example fix

# before (posts/my-post.md)
# My Post
Some text

// after
---
title: My Post
date: 2024-01-15
---
# My Post
Some text
Defensive patterns

Strategy: validation

Validate before calling

import pathlib
def has_front_matter(p):
    text = p.read_text(encoding='utf-8-sig')
    return text.startswith('---') and '\n---' in text[3:]
missing = [p for p in pathlib.Path('docs/posts').rglob('*.md') if not has_front_matter(p)]
assert not missing, f"Posts missing front matter: {missing}"

Type guard

def has_valid_front_matter(text):
    stripped = text.lstrip('\ufeff')
    return stripped.startswith('---') and stripped.count('---') >= 2

Try / catch

try:
    mkdocs.commands.build(config)
except PluginError as e:
    if "Expected metadata to be defined" in str(e):
        log.error(f"Add a '--- ... ---' metadata block to: {e}")
    raise

Prevention

When it happens

Trigger: A file inside the blog `posts_dir` has no leading `--- ... ---` metadata block, or the block is malformed such that YAML_RE does not match (e.g. missing opening/closing `---`, BOM, or leading blank/comment lines before the block).

Common situations: Adding a plain markdown note into the posts directory; deleting the metadata while editing; an editor stripping the front-matter; a file with Windows BOM or different fence characters.

Related errors


AI-assisted analysis of squidfunk/mkdocs-material@e2136532f4 (2026-08-29). Data as JSON: /api/errors/64d877fdbd364057. Report an issue: GitHub.