March 10, 2026?10 min

Building Seven CMS: Architecture Decisions

Why I wrote a CMS from scratch instead of extending WordPress. Module system, security hardening, and Vue.js frontend.

PHPSeven CMSArchitecture

Building Seven CMS: Architecture Decisions

When I decided to build a CMS, everyone asked: "Why not fork WordPress?"

Here's why I didn't.

The WordPress Problem

WordPress's codebase dates to 2003. It's accumulated 20 years of backwards compatibility hacks, global state, and security patches on top of security patches. Extending it means inheriting all of that.

I wanted something I could reason about completely — where every line of code exists for a reason.

Architecture Decisions

Modular by Default

Each feature is an independent module: Blog, Pages, Media, E-commerce, Users. Modules register themselves at boot. You can install or remove a module without touching the core.

// Module registration
ModuleRegistry::register('blog', BlogModule::class);

Security First

Every security decision was explicit:

  • CSP nonce on every inline script — no wildcard unsafe-inline
  • CSRF tokens on all state-changing forms
  • Rate limiting on auth endpoints (Redis-backed)
  • SVG sanitization on upload — SVGs can contain scripts
  • Trusted proxy validation — proper IP resolution behind Nginx

Vue.js Admin Panel

The admin is a Vue 3 SPA communicating with the PHP REST API. Clean separation: PHP handles data, Vue handles UI.

Build with Vite, served as static assets — the PHP app doesn't need to know about frontend tooling.

What I'd Do Differently

Add a proper event system from the start. Right now inter-module communication is direct method calls. An event bus would make modules more independent.

Open source release is planned once the documentation is complete.