Solomon Lee

Solomon Lee

Founder & Chief Software Architect of Tekhx

Tech stack

What I reach for, and where it is running

59 technologies

Architecture patterns

The shapes underneath the systems, and the failure each one prevents

Layered modules

Route, DTO, service, repository, schema — one folder per table, always the same five files.

Business rules never touch HTTP or SQL, so a module is testable with no server and no database, and a new developer can guess where anything lives.

  1. Route
  2. DTO
  3. Service
  4. Repository
  5. Postgres

Domain-driven design

The model speaks the business’s language, and invariants live with the aggregate that owns them.

When a rule changes, it changes in one place. Scattered validation is how two endpoints end up disagreeing about what a valid order is.

  1. Domain model
  2. Aggregate
  3. Invariant
  4. Service

Manifest-driven generation

A module is declared once in a manifest; routes, menus, permissions, schema, and CRUD are generated from it.

Hand-writing the same eight files per table is where drift enters. Generate them and every module is identical by construction.

  1. Manifest
  2. Seeds
  3. Generator
  4. Module + tests

Master-detail transactions

Header and lines update together: existing rows update by id, new rows insert, removed rows soft-delete, totals recompute.

The naive version deletes everything and re-inserts, which throws away ids, history, and anything that referenced them. Reconciling is the only version that survives an audit.

  1. Header
  2. Lines
  3. Reconcile
  4. Recompute stock

Event-driven messaging

Services publish what happened; whoever cares subscribes. No service calls another to tell it to update.

Adding a consumer never means redeploying the producer, and a slow downstream cannot stall the write that triggered it.

  1. Producer
  2. Kafka topic
  3. Consumer
  4. Projection

Background jobs

Anything slow — exports, PDFs, SMS batches, imports — leaves the request through a Postgres-backed queue.

The request returns in milliseconds and the work still happens, with retries and a record of every attempt. No extra broker to keep alive.

  1. API
  2. Queue
  3. Worker
  4. Retry / record

Optimistic locking

A read hands back the row’s version; the update sends it back, and a stale one is refused with a 409.

Two people editing the same record no longer means the second save silently erases the first. The version travels as a header, so no update schema changes.

  1. Read
  2. Version token
  3. Update
  4. 409 if stale

Append-only history

Every create, update, and delete writes one structured diff — field, old value, new value — never prose.

The sentence is rendered at read time, so relabelling a field or fixing wording reaches rows written years ago. Frozen prose could never be corrected.

  1. Mutation
  2. Structured diff
  3. Append row
  4. Render on read

RBAC and row scoping

Roles grant endpoints; scope narrows rows. A franchisee sees their branch, not a filtered copy of everyone’s.

Filtering in the dashboard is not access control — it is a UI convenience that a direct API call walks straight past.

  1. Role
  2. Endpoint grant
  3. Row scope
  4. Result

Caching and pooling

Redis in front for reads that repeat, PgBouncer in front of Postgres so connections are borrowed, not opened.

A fleet of services each opening their own pool will exhaust a database long before traffic does.

  1. Request
  2. Redis
  3. PgBouncer
  4. Postgres

Guardrails in CI

Static and live checks that each make a whole class of bug impossible to merge, wired into the pre-push hook.

A convention nobody can violate beats a convention written in a README. Every guardrail exists because that bug shipped once.

  1. Push
  2. Typecheck
  3. Guardrails
  4. Integration
  5. Deploy

Self-hosted topology

Cloudflare Tunnel to Caddy to PM2-managed services, with no inbound port open on the host.

The origin has no public attack surface at all, and TLS renews itself. Thirty-five services, one predictable shape.

  1. Cloudflare Tunnel
  2. Caddy
  3. PM2
  4. Service