Open Source · PostgreSQL Migration

pgloader

Migrate to PostgreSQL in a single command

pgloader v4 is a full rewrite in Clojure, distributed as one self-contained JAR — download it, run it anywhere a JVM does. Requires Java 21+.

2005maintained since 4live sources, 1 in funding v4Clojure rewrite, drop-in v3 syntax

$ pgloader mysql://app@src/shop pgsql://app@dst/shop
# catalog fetched — 14 tables, 701,433 rows
COPY results         done   26,759 rows   0.55s
COPY laptimes        done  589,081 rows   3.76s
COPY driverstandings done   34,863 rows   0.64s
# building 23 indexes in parallel…
Total import time       701,433 rows   6.49s

One pipeline, five stages

The literal order pgloader executes in — the report at the end times every one of them

  1. 01

    Fetch catalog

    Query the source's live catalogs, or read a file header, into an in-memory schema.

  2. 02

    Prepare target

    Translate the catalog into PostgreSQL's own, applying casting rules as it goes.

  3. 03

    Parallel COPY

    Reader and writer threads per table, batching over the COPY protocol.

  4. 04

    Parallel indexes

    Every index builds once its table's data has landed — primary keys get their own pass.

  5. 05

    Complete schema

    Constraints, comments, and foreign keys install last, as defined in the source.

Same .load file syntax and command-line flags as v3 — existing migration scripts keep working. v4 also accepts plain JDBC connection strings (jdbc:mysql://, jdbc:sqlserver://, etc.) with driver-specific parameters passed through unchanged.

$ curl -L -o pgloader.jar https://github.com/dimitri/pgloader/releases/download/v4-dev/pgloader.jar
$ java -jar pgloader.jar mysql://user@host/dbname postgresql:///dbname

Every source, one tool

Cell size follows how much ground each source actually covers

Live database

MySQL & MariaDB

The flagship path: enum→type translation, TINYINT(1)→boolean, zero-date handling, .my.cnf credential lookup.

pgloader mysql://user@host/db pgsql:///db
Live database

MS SQL Server

Azure AD auth, sequence migration, multi-column foreign keys — sponsored work, still shipping.

File

SQLite

No live connection needed — reads the file directly.

Files

CSV · DBF · Fixed

A retry-wrapper over PostgreSQL's own COPY.

Open for funding

Oracle

Never built. A threshold-funded campaign is open for it.

Fund a Feature

Oracle Support for pgloader v4

Never built — open for funding as a threshold campaign. Below the threshold nothing is charged and nothing starts; above it, work ships continuously, in the open, under the same license as the rest of pgloader.

raisedthreshold

Every run signs its own work

Not a screenshot

pgloader's own default report, unedited — one command against a MariaDB source (the F1DB dataset: Formula 1 results since 1950, 14 tables, 701K rows, ~20MB) loading into PostgreSQL. Row counts, bytes, and timing, per table, every time.

Run it yourself from the pgloader repo with make -C clojure/tests mariadb — that target drives the exact docker-compose stack (MariaDB source, PostgreSQL target) this output came from. Same command, same shape of report — compare the numbers yourself.

migration report · mariadb → postgresql
fetch meta data0.72s
create tables0.21s
f1db.laptimes589,081 rows
f1db.driverstandings34,863 rows
f1db.results26,759 rows
create indexes5.40s
total import time701,433 rows · 6.49s

Migrate without betting everything on one night

Continuous Migration

pgloader exists to make the hardest step of a real migration project fully automated — nightly, re-run, repeatable, not a single big-bang cutover. That method has a name and a free White Paper.

Support pgloader

Open source, not maintained-for-free-forever

If pgloader is part of your production migration, its ongoing maintenance is worth funding. Priority fixes, roadmap input, and reserved capacity — or learn to run the migration yourself with the MySQL course (MS SQL Server is next).