Skip to content
Back to blog
Part 8 of 10 in series
Building a Production-Grade Blog

A curated collection of articles exploring this topic in depth.

3 min read

Testing Content is Not Overkill

Why automated guardrails for your writing prevent silent rot and free you to focus on the craft of thinking.


Testing is frequently perceived as a practice reserved for application logic. However, in this system the content pipeline is as critical as the code that renders it. Without automated checks, the site could become prone to silent rot: broken links, missing metadata, or inconsistent taxonomy.

Testing content is not about proofreading for typos (although that is important); it is about ensuring the integrity of the data layer.

Schema validation as a hard gate#

As discussed earlier in this series, treating content as data requires a formal contract. This contract is enforced by a schema validation script that runs before every build.

The specifics below reflect my own implementation, but the pattern is what matters: validation ensures that every entry adheres to the system's requirements before it is processed.

// web/scripts/validate-content.ts
const result = postSchema.safeParse(data);
if (!result.success) {
  const msg = result.error.issues.map(e => `${e.path.join('.')}: ${e.message}`).join(', ');
  errors.push(`${relativePath}: ${msg}`);
}

This script ensures that every post has a valid date, a summary within the character limit, and the necessary series metadata. If the contract is violated, the build fails. This prevents a malformed post from ever reaching production.

Build verification: Trusting the output#

A successful build does not always guarantee a correct site. A configuration change or a dependency update can lead to an empty RSS feed, a broken search index, or missing pages.

To prevent these silent failures, the pipeline includes a post-build validation step. This script inspects the output directory after the export is complete, verifying the existence of critical artifacts.

// web/scripts/validate-build.ts
const criticalPaths = [
  'index.html',
  'rss.xml',
  'sitemap.xml',
  'search-index.json'
];
 
criticalPaths.forEach(p => {
  if (!fs.existsSync(path.join(outDir, p))) {
    errors.push(`Missing critical build artifact: ${p}`);
  }
});

By verifying the output directly, we gain confidence that the site's essential features are intact before deployment.

Guardrails for thinking#

The primary value of these tests is not just the prevention of errors; it is the psychological safety they provide. When the system handles the validation of technical details, I am free to focus on the writing itself.

Automated guardrails reduce the cognitive load of maintenance. If I decide to refactor the taxonomy or restructure the series logic, I do not have to manually check every post for regressions. The test suite provides immediate, deterministic feedback.

Maintenance vs creation#

Engineering a personal blog with this level of rigour might seem like a distraction from the act of writing. In practice, it is what makes long-term writing sustainable. By investing in the content pipeline, I ensure that the site remains easy to maintain as it grows.

In the next post, we will look at how this structured approach enables long-term growth and discoverability, turning a collection of posts into a coherent archive.