| Option | How it works | When to choose it |
|---|---|---|
| **A. Pure-Rust migrations** | Implement `diesel::migration::Migration<DB>` in
a Rust file (`up.rs` / `down.rs`) and compile with both
`features = ["postgres", "sqlite"]`. The query builder emits backend-specific
SQL at runtime. | You prefer the type-checked DSL and can live with slightly
slower compile times. | | **B. Lowest-common-denominator SQL** | Write one
`up.sql`/`down.sql` that *already* works on both engines. This demands avoiding
SERIAL/IDENTITY, JSONB, `TIMESTAMPTZ`, etc. | Simple schemas, embedded use-case
only, you are happy to supply integer primary keys manually. | | **C. Two
separate migration trees** | Maintain `migrations/sqlite` and
`migrations/postgres` directories with identical version numbers. Use
`embed_migrations!("migrations/<backend>")` to compile the right set. | You ship
a single binary with migrations baked in. |
