Why I Chose the Content Layer Over CMS for This Blog

A practical comparison between local markdown, headless CMSes, and direct content-layer workflows.

I moved through CMS options for a while before choosing local markdown as the source of truth. The short answer: for this project, local files are faster, simpler, and safer.

Local markdown is the right default for a portfolio

The Content Layer in Astro gives me a clean schema, type checking, and first-class compile-time support.
For posts that I want to own directly in git, that matters more than every feature a managed CMS advertises.

CMS can still help, but in the wrong context

If your content changes constantly by non-technical contributors, a CMS is worth the overhead.
For a developer-led portfolio, the overhead can slow releases:

  • extra auth workflows,
  • deployment hooks,
  • content approval loops,
  • harder local diffing for prose edits.

For me, the tradeoff is clear: markdown lowers friction every time I ship.

The build-time benefit

Because content is local, the feed query is deterministic:

const posts = (await getCollection('blog')).sort(
  (a, b) => b.data.pubDate.valueOf() - a.data.pubDate.valueOf()
)

No remote rate limits. No transient authoring outages. No schema drift from external editors.

Where this pattern scales

This approach scales surprisingly well if you keep your frontmatter strict and your templates boring:

  • add one shared PostCard,
  • keep date ordering in page-level queries,
  • enforce image dimensions in schema.

The stack stays fast without being minimal to the point of being plain.