DEV Community

Cover image for Forget MVC. The New Era Is PSR (Project Stack Resource)
tdk-cli
tdk-cli

Posted on

Forget MVC. The New Era Is PSR (Project Stack Resource)

You’re still thinking in MVC.

Controllers, models, views, “where does this function live?”, “which file owns the routing?” — that mental model made sense when the unit of work was a single application. It starts falling apart the moment you have more than a handful of services that need to run together locally.

The useful unit of work is no longer a function or a controller. It’s a resource that belongs to a stack inside a project.

The Old Era vs the New One

Era Mental model What you maintain by hand What breaks at scale
MVC Controllers / Models / Views Routes, services, wiring inside one app Multi-service local reality
Manual microservices Dockerfiles + Compose + scripts Everything surrounding the code Consistency, onboarding, drift
PSR Project → Stack → Resource service.json + app code Almost nothing local

If you’re still spending afternoons reading or rewriting Dockerfiles, Tiltfiles, nginx configs, Vite configs, and health-check plumbing, you’re operating in the previous era.

Project → Stack → Resource

flowchart LR
    P["Project<br/>.tdk/project.json"] --> S1["Stack: shop"]
    P --> S2["Stack: billing"]
    S1 --> R1["orders-api<br/>backend"]
    S1 --> R2["storefront-web<br/>frontend"]
    S2 --> R3["checkout-api<br/>backend"]
  • Project owns the overall landscape and phases.
  • Stack is a business slice you can start on its own (tdk up shop).
  • Resource is one service (backend, frontend, worker, migrator, etc.).

You declare the resource once:

{
  "$schema": "https://tdk-landscape.github.io/schema.service.json",
  "schemaVersion": 1,
  "appName": "orders-api",
  "appType": "backend",
  "stack": "shop",
  "port": 4000,
  "healthCheckPath": "/health",
  "dependsOn": []
}
Enter fullscreen mode Exit fullscreen mode

Everything else is derived.

You Don’t Need to Read the Functions Anymore

This is the part that feels wrong at first if you grew up in the MVC era.

In the old model you had to read the functions because the functions were the system. The routing, the dependency wiring, the startup order, the config — all of it lived in code you were expected to understand line by line.

In the PSR model the local infrastructure is a generated artifact. TDK produces the Dockerfile, the Tiltfile, the Traefik routes, the live-update rules, the nginx/Vite/tsconfig/env files, the API client, the health probes, and the Postgres wiring from the contract. You stop treating those files as something you carefully author and constantly re-read.

flowchart TD
    A["Write service.json<br/>+ app code"] --> B["tdk up"]
    B --> C{"Drift check"}
    C -->|Clean| D["Tilt + Docker<br/>Hot reload"]
    C -->|Hand edit detected| E["Exit 2<br/>List files"]
    E --> F["tdk config regenerate"]
    E --> G["--ignore-drift"]

Hand-edits are not silently overwritten. tdk up exits with code 2 and tells you exactly which generated files drifted. You either regenerate from the contract or explicitly keep the customization. The source of truth stays the small declarative file and your application code.

Why This Is the Actual Upgrade

AI made writing application code cheap. It did not make multi-service local infrastructure consistent. Generators that treat their output as derived artifacts (and refuse to quietly wipe your changes) close that gap.

You’re falling behind if:

  • You still hand-maintain a docker-compose.yml for more than a couple of services.
  • You treat the Tiltfile as source instead of generated.
  • You spend time reading generated nginx, Vite, or Dockerfile logic instead of changing the contract.
  • Your “local setup” is a wiki page instead of tdk doctor + tdk up.

The MVC era taught us to organize code inside one process. The PSR era organizes resources that can be started, stopped, and hot-reloaded as slices of a larger system — without forcing you to re-read the plumbing every time the generator improves.

The functions still exist. You just stop needing to live inside them for the local infrastructure layer.

Getting Started

npm install -g @tdk-landscape/tdk-cli-core
tdk doctor
tdk project --yes
tdk resource orders-api --type backend --stack shop --yes
tdk up shop
Enter fullscreen mode Exit fullscreen mode

MVC got you this far.

Project → Stack → Resource is how you stop maintaining the local stack by hand.

Top comments (1)

Collapse
 
tdk-cli profile image
tdk-cli •

nice!