Sign in

Architecture overview

Updated Jul 3, 2026

Devani is plain PHP and vanilla JavaScript with no database and no build step. If you can read PHP, you can read all of Devani — the whole application ships as source in every release zip.

The core idea: the filesystem is the data model

A Devani site is a directory tree. Content lives in per-page folders, application state lives in JSON files, and rendering is a template wrapped around a content file. There is nothing else — no ORM, no migrations, no connection pool.

Request flow

  1. A request hits the web server (nginx in the standard install) and routes to PHP.
  2. devani/page-render.php runs: first devani_check_redirects() (consults the redirect table and 301s before any rendering), then a setup check (a site with no users redirects to the setup wizard), then the page renders — the shared template (header, navigation, footer, global styles) around the page's content.html.
  3. Output is clean, semantic HTML. It's dynamic PHP per request, but with no queries and no heavy work, so it's fast bare and caches perfectly behind any CDN.

Application state: JsonStore

devani/JsonStore.php implements the storage layer the rest of the code calls through DevaniDB — a database-shaped API over JSON files in devani/data/storage/. It provides table-like structures with autoincrement ids (users, orders, reviews, MCP API keys, email logs), a settings key/value table, and file locking around writes. seedDefaults() runs on every construct and idempotently back-fills any missing default settings — which is how new settings appear on existing installs after an update.

Storage files are self-defending

Data files are stored with a .php guard (e.g. settings.json.php beginning with an exit sentinel), so a misconfigured server that executes them returns nothing instead of leaking contents. Direct HTTP access to content internals (content.html, meta.json, featured-image.txt) is additionally denied at the web-server level in the standard install.

Why no database is a feature

  • Security: no SQL injection surface, no DB credentials to steal.
  • Ops: backup = copy the directory; migrate = rsync it somewhere else.
  • Portability: no hardcoded paths — everything resolves relative to the install (__DIR__-based), so a site can move between servers and users freely.
  • Performance: reading a file the OS has cached beats a query, every time.

Next: Content storage layout.

Was this helpful?

Related articles

Powered by Subido