Skip to content

Deploy SQL Server, PostgreSQL & MySQL as one

You’re running three database engines. Not because someone made a bad call — because each service picked the engine that fits it best. And now you’ve got three different mental models, three different toolchains, and three different answers every time someone asks “did that schema change land everywhere?”

Hey folks. I’m Forge Barrett, master of the Content Forge here at SchemaSmith.

This course is about closing that gap. Three engines, one consistent workflow, and every service independently deployable. Native packages — one per engine, each in its own metal — and the same deploy command that reads identical on all three. You don’t get a lowest-common-denominator abstraction. You get full native fidelity and a rhythm you only have to learn once.

That’s what the next five modules are going to prove.

The course builds on a fictional commerce platform — Northwind Commerce — split across three backend services. Each one picked its engine for real reasons.

Orders — SQL Server. The transactional system of record. Brackets, NVARCHAR, schema-qualified names, FK integrity across a graph of orders, customers, and line items. SQL Server earns its place when auditability and relational discipline matter most. This is the engine you reach for when “the data has to be right” is non-negotiable.

Catalog — PostgreSQL. Rich types, lowercase identifiers, and text columns where the width isn’t a constraint. PostgreSQL earns its spot when the data model needs to be expressive and the query layer needs room to breathe. Catalog owns the canonical product and reference data the other services pull from.

Sessions — MySQL. High-volume, write-heavy event tracking. Backtick-quoted identifiers, InnoDB, utf8mb4 — tuned for throughput at the edge. Sessions is where every page view, add-to-cart, and checkout event lands, at volume, continuously.

If Sessions ran on MariaDB instead, nothing about this course would change shape — you’d select Platform: MariaDb and get a native MariaDB package. Same family as MySQL, its own platform selection. What you would not do is point the MySQL package at MariaDB; each engine gets its own native package, always.

Three different strengths. Three different native conventions. All three real reasons, not accidents.

One consistent workflow — native packages per engine, always separate

Section titled “One consistent workflow — native packages per engine, always separate”

Here’s what SchemaSmith gives you across all three: the same package layout, the same deploy command, and the same convergence guarantee. Declare your schema in JSON, run schemaquench, done. The DDL looks different per engine — brackets vs lowercase vs backticks, NVARCHAR vs text vs varchar — but the workflow doesn’t. That consistency is the whole value.

What you do NOT get is a single package that targets all three engines. That’s not how SchemaSmith works, and it’s not how production services work. One package per engine. Always. Each service has its own native package. Orders is a SQL Server package. Catalog is a PostgreSQL package. Sessions is a MySQL package. They each generate native DDL for their engine, run independently, and deploy on their own schedule.

The consistency is in the tooling and the workflow. The DDL stays native. Those two things are not in tension — they’re the design.

Every service deploys on its own timeline. The Orders team can ship a column change on Tuesday without coordinating with the Catalog team’s Friday release. Sessions can deploy three times a day while Orders is mid-sprint. Nothing about deploying one service triggers or blocks the others. Each package targets one connection string, runs one deploy, produces one exit code.

That independence is the production norm. In a real polyglot setup, each service is its own repo — its own quench.settings.json, its own deploy pipeline, its own secrets rotation. The lab co-locates all three services under one folder because that’s how lab bundles ship. Don’t read that as a recommendation for how to organize production. Polyrepo is the norm. Co-location is a lab convenience.

Contrast with Course 7 — Fleet vs Polyglot

Section titled “Contrast with Course 7 — Fleet vs Polyglot”

If you came through Course 7, the distinction is worth naming. Fleet management (Course 7) was one schema, many databases — same engine, same package, fanned out across a fleet of targets. Every database got the same DDL, which meant one package could drive all of them.

This is different. Polyglot management is many engines, each with its own native package. The consistency isn’t “every database gets the same DDL.” It’s “every engine runs the same workflow.” Same shape, different metal. Fleet scales out across databases. Polyglot manages across engines. Both use SchemaSmith. The packages look different because the job is different.

The arc — five modules, one complete picture

Section titled “The arc — five modules, one complete picture”

Module 1 — Same change, three engines. Prove the workflow is identical. One class of change — nullable column, index, seeded reference table — applied to all three services independently. You’ll feel the rhythm before you think about the differences.

Module 2 — Where native fidelity diverges. Slow down on why the DDL looks different per engine. Brackets vs lowercase vs backticks aren’t cosmetic. NVARCHAR and text and varchar aren’t interchangeable. This module explains why that native fidelity is a feature, not a problem to abstract away.

Module 3 — Organizing polyglot services. Per-service subfolders, Core/Reference structure, and file-less credential injection via SmithySettings_ environment variables. The mechanics that make a multi-engine setup manageable by a real team and ready for CI.

Module 4 — Each service, its own pipeline. Wire three independent CI/CD pipelines — one per service — path-filtered, WhatIf-gated on every PR, credentials from secrets. No combined pipeline. No lockstep. Each service releases on its own cadence.

Module 5 — Capstone: an independent release done right. The hardest problem in multi-service schema work: shared reference data across independent services. Expand / contract across all three — Catalog owns the canonical table, Orders and Sessions each carry their own synced copy. No coordination window. No combined deployment. Just three independent deploys that land in the right order, by design.

Five modules. One complete picture of a polyglot fleet run the way production expects.

Before Module 1: stand up the three services

Section titled “Before Module 1: stand up the three services”

The setup lab is the prerequisite for everything that follows. Run it before Module 1. It stands up the three service databases — Orders, Catalog, Sessions — and gives you live targets to deploy against for the rest of the course.

The lab uses schemaquench built from source, the same as every other lab in this series. If you haven’t run the Course setup yet, do that first. The setup lab brief walks you through it.


Three engines. One workflow. Every service on its own timeline. That’s what a three-headed shop looks like when it’s running well — not one tool per head, but one smithy that knows how to work each metal.

Subscribe and stick around. In Module 1, we’ll kindle the forge and prove the rhythm: one class of change, three native packages, three independent deploys, three exit zeros.

Until then, may each head of your forge find its own steady fire.

— Forge

Check yourself: The course uses three separate SchemaSmith packages — one for Orders (SQL Server), one for Catalog (PostgreSQL), one for Sessions (MySQL). Why is there no single package that targets all three engines?

Because SchemaSmith packages are native per engine — each one targets one engine, generates native DDL for that engine, and deploys to one connection string. A single package spanning all three engines would require a lowest-common-denominator model that sacrifices the native fidelity that makes each engine worth using. In production, each service is its own independent deployment with its own package, its own pipeline, and its own release cadence. Native + separate is not a limitation — it’s the design. The consistency the course delivers is in the workflow and tooling, not in the DDL.

Check yourself: What's the difference between what Course 7 (Fleet) taught and what Course 9 (Polyglot) teaches — and what stays the same across both?

Course 7 was one schema, many databases — same engine, same package, fanned out across a fleet of targets. Every database in the fleet got the same DDL. Course 9 is many engines, each with its own native package — the consistency is in the workflow, not the DDL. Fleet scales out across databases on one engine. Polyglot manages across engines, each in its native form. What stays the same across both: the package layout, the deploy command, and the convergence guarantee. SchemaSmith runs the same workflow regardless of whether you’re targeting ten SQL Server databases or three different engines. The shape of the work is the same. The metal is different.