Documentation

Tyro Checkpoint is a Laravel package that provides Git-like checkpoint functionality for your local development database. Create a snapshot before risky work, then restore that exact state when you need it.

Current version: v1.7.0 supports SQLite, MySQL, and PostgreSQL, with optional encryption, locks, flags, auto-checkpoints, and in-place encryption for existing snapshots.

Requirements

  • PHP 8.1 or higher
  • Laravel 10.x, 11.x, 12.x, or 13.x
  • SQLite, MySQL 8+, or PostgreSQL 12+
  • For MySQL: mysqldump and mysql CLI tools
  • For PostgreSQL: pg_dump and psql CLI tools

Installation

Install the package via Composer as a dev dependency:

composer require hasinhayder/tyro-checkpoint --dev

Run the installation command to setup everything:

php artisan tyro-checkpoint:install

This command verifies your database setup, checks required database binaries when needed, creates the checkpoint storage directory, and prepares the metadata registry.

How It Works

  1. Full Snapshots: Each checkpoint captures your full database state. SQLite uses file snapshots; MySQL and PostgreSQL use SQL dumps.
  2. Metadata Tracking: Metadata is stored in a JSON file outside the database to prevent data loss during restoration.
  3. Safe Restore: Restoring replaces the current database state and guards against restoring into the wrong database unless you explicitly force it.
  4. Encryption: Optional file-level encryption for new or existing checkpoints.

What are Checkpoints?

A checkpoint is a point-in-time snapshot of your entire local database. Unlike traditional migrations alone, a checkpoint captures the exact state of your data and schema at a specific moment.

Anatomy of a Checkpoint

  • Database Snapshot: A SQLite file copy or SQL dump for MySQL/PostgreSQL, optionally encrypted.
  • Metadata: A JSON record containing the checkpoint name, ID, creation timestamp, driver, database identity, optional notes, lock/flag state, and encryption status.

Storage

By default, all checkpoints are stored in storage/tyro-checkpoints/. This directory contains snapshot files or dumps plus the metadata registry at checkpoints.json.

Pro Tip: You can version control certain checkpoints or exclude the entire directory from your Git repository depending on your team's workflow.

Creating Checkpoints

Create a checkpoint with an auto-generated name:

php artisan tyro-checkpoint:create

Create a checkpoint with a custom name and an optional note:

php artisan tyro-checkpoint:create initial_state --note="Clean install"

Encrypted Checkpoints

To create an encrypted snapshot, use the --encrypt flag:

php artisan tyro-checkpoint:create secure_state --encrypt

Script-Friendly Checkpoints

Use --silent to skip interactive note prompts in cron jobs, CI helpers, or local scripts:

php artisan tyro-checkpoint:create nightly_backup --silent

Auto-Checkpoints

Auto-checkpoints create a safety snapshot before risky Artisan commands such as migrations, seeders, and database wipes.

TYRO_CHECKPOINT_AUTO_ENABLED=true

By default, Tyro Checkpoint watches these commands:

migrate
migrate:fresh
migrate:refresh
migrate:reset
migrate:rollback
db:seed
db:wipe

You can customize the watched commands, checkpoint name prefix, encryption behavior, and failure behavior in config/tyro-checkpoint.php.

Listing Checkpoints

View all saved checkpoints, their sizes, creation dates, and statuses:

php artisan tyro-checkpoint:list

Inspect a single checkpoint by ID or name:

php artisan tyro-checkpoint:details 1
php artisan tyro-checkpoint:list initial_state

Restoring Checkpoints

Restore a checkpoint by its ID or Name:

php artisan tyro-checkpoint:restore 1
php artisan tyro-checkpoint:restore initial_state

If you don't provide an identifier, the command will display a selection list. Encrypted checkpoints are decrypted automatically during restore.

Safety: Restore tracks the checkpoint driver and database identity. Use --force only when you intentionally want to bypass the database mismatch guard.

Notes, Locks & Flags

Adding Notes

Change or add a note to an existing checkpoint:

php artisan tyro-checkpoint:add-note 1

Locking Checkpoints

Lock a checkpoint to prevent accidental deletion via delete or flush commands:

php artisan tyro-checkpoint:lock 1

To enable deletion again, unlock it:

php artisan tyro-checkpoint:unlock 1

Flagging Checkpoints

Flag important checkpoints for attention without preventing restore or deletion:

php artisan tyro-checkpoint:flag 1
php artisan tyro-checkpoint:unflag 1

Delete & Flush

Delete a specific unlocked checkpoint:

php artisan tyro-checkpoint:delete 1

Delete all unlocked checkpoints to save disk space:

php artisan tyro-checkpoint:flush

Why Encryption Matters

When working with local development databases, developers often use production-like data or sensitive PII (Personally Identifiable Information). Tyro Checkpoint's encryption ensures that your data remains safe, even if your snapshots are shared or stored in insecure locations.

Key Benefits

  • Data Privacy: Protects sensitive user data (emails, passwords, personal details) within your local database snapshots.
  • Compliance: Helps meet security standards and internal policies regarding data handling during development.
  • Safe Sharing: Encrypted snapshots can be shared with teammates more securely when the encryption key is managed properly.
  • Zero Overhead: AES-256 encryption is blazingly fast on modern hardware, adding negligible time to the snapshot process.

Note: Encryption is handled at the file level. Once a snapshot is encrypted, it cannot be opened directly without first being decrypted by Tyro Checkpoint during restoration.

Encryption

Tyro Checkpoint supports AES-256 encryption for your snapshots. First, generate a key:

php artisan tyro-checkpoint:generate-key

⚠ WARNING: Replacing an existing encryption key will make all previously encrypted checkpoints impossible to restore. Always backup your key if you plan to keep your snapshots.

This adds TYRO_CHECKPOINT_ENCRYPTION_KEY to your .env file. Once configured, use --encrypt when creating checkpoints. Restoration will automatically detect and decrypt them.

Encrypt an Existing Checkpoint

Version 1.7.0 adds in-place encryption for checkpoints you already created:

php artisan tyro-checkpoint:encrypt 1
php artisan tyro-checkpoint:encrypt initial_state

The command removes the original unencrypted snapshot after encryption, updates the same checkpoint metadata record, and will not double-encrypt an already encrypted checkpoint.

Database Engines

Tyro Checkpoint supports three local development database engines:

  • SQLite: snapshots are based on database file copies.
  • MySQL: snapshots and restores use mysqldump and mysql.
  • PostgreSQL: snapshots and restores use pg_dump and psql.

By default, Tyro Checkpoint uses your Laravel default database connection. Set TYRO_CHECKPOINT_CONNECTION to checkpoint a different configured connection.

Configuration

Publish the configuration to customize storage, connections, binaries, process timeout, and auto-checkpoint behavior:

php artisan tyro-checkpoint:publish-config

Common environment variables:

TYRO_CHECKPOINT_STORAGE_PATH=/custom/path
TYRO_CHECKPOINT_CONNECTION=mysql
TYRO_CHECKPOINT_ENCRYPTION_KEY=base64:...
TYRO_CHECKPOINT_PROCESS_TIMEOUT=600
TYRO_CHECKPOINT_AUTO_ENABLED=true
TYRO_CHECKPOINT_AUTO_ENCRYPT=false
TYRO_CHECKPOINT_AUTO_STOP_ON_FAILURE=true

For MySQL and PostgreSQL, you can also override binary paths such as TYRO_CHECKPOINT_MYSQLDUMP_BIN, TYRO_CHECKPOINT_MYSQL_BIN, TYRO_CHECKPOINT_PG_DUMP_BIN, and TYRO_CHECKPOINT_PSQL_BIN.