PHPackages                             roslov/laravel-migration-checker - PHPackages - PHPackages  [Skip to content](#main-content)[PHPackages](/)[Directory](/)[Categories](/categories)[Trending](/trending)[Leaderboard](/leaderboard)[Changelog](/changelog)[Analyze](/analyze)[Collections](/collections)[Log in](/login)[Sign up](/register)

1. [Directory](/)
2. /
3. [Database &amp; ORM](/categories/database)
4. /
5. roslov/laravel-migration-checker

ActiveLibrary[Database &amp; ORM](/categories/database)

roslov/laravel-migration-checker
================================

Up/down database migration checker for Laravel

1.0.0(2mo ago)3336↑30%1[3 issues](https://github.com/roslov/laravel-migration-checker/issues)[1 PRs](https://github.com/roslov/laravel-migration-checker/pulls)MITPHPPHP ^8.1CI passing

Since Jan 7Pushed 2mo agoCompare

[ Source](https://github.com/roslov/laravel-migration-checker)[ Packagist](https://packagist.org/packages/roslov/laravel-migration-checker)[ RSS](/packages/roslov-laravel-migration-checker/feed)WikiDiscussions main Synced 1mo ago

READMEChangelog (8)Dependencies (12)Versions (10)Used By (0)

Database Migration Checker For Laravel
======================================

[](#database-migration-checker-for-laravel)

[![Latest Stable Version](https://camo.githubusercontent.com/16193dbe15ae1139cb9863fcd14cc7cea688a01e3035c1d280e93a5dea76ac43/68747470733a2f2f706f7365722e707567782e6f72672f726f736c6f762f6c61726176656c2d6d6967726174696f6e2d636865636b65722f76)](https://packagist.org/packages/roslov/laravel-migration-checker)[![Total Downloads](https://camo.githubusercontent.com/fef71fef3ab23eced86c1d9cbf272ae23488280360dbaaf3c2b70d38362dcfe8/68747470733a2f2f706f7365722e707567782e6f72672f726f736c6f762f6c61726176656c2d6d6967726174696f6e2d636865636b65722f646f776e6c6f616473)](https://packagist.org/packages/roslov/laravel-migration-checker)[![License](https://camo.githubusercontent.com/1088b765573c52c0be44a195a761d89c4f050295f054db86d08696efca234fc0/68747470733a2f2f706f7365722e707567782e6f72672f726f736c6f762f6c61726176656c2d6d6967726174696f6e2d636865636b65722f6c6963656e7365)](https://packagist.org/packages/roslov/laravel-migration-checker)[![PHP Version Require](https://camo.githubusercontent.com/c5ec751d32bb9669ea24b81214588ed7892446639561478b89e0c93c2ddbf6a7/68747470733a2f2f706f7365722e707567782e6f72672f726f736c6f762f6c61726176656c2d6d6967726174696f6e2d636865636b65722f726571756972652f706870)](https://packagist.org/packages/roslov/laravel-migration-checker)

This package validates Laravel database migrations by ensuring every pending migration can be applied and rolled back without leaving schema differences. It is a Laravel wrapper around [Migration Checker](https://github.com/roslov/migration-checker) and integrates directly with Artisan, so you can use it as part of your local workflow or CI.

The checker runs migrations one by one:

1. Creates the migrations table if needed.
2. Takes a schema snapshot.
3. Applies the next pending migration.
4. Rolls the migration back.
5. Compares the schema dump to the original state.

If the schema differs, the command fails and prints a diff so you can pinpoint what was left behind.

Requirements
------------

[](#requirements)

- PHP 8.1 or higher,
- Laravel 10.0 or higher

Supported database types and versions
-------------------------------------

[](#supported-database-types-and-versions)

This bundle supports MySQL, MariaDB, PostgreSQL, and others.

See all supported database types and versions in the [Migration Checker documentation](https://github.com/roslov/migration-checker#supported-database-types-and-versions).

Limitations
-----------

[](#limitations)

The console command `migration-checker:check` runs only in the test environment to avoid accidentally affecting the working database. Therefore, it should always be used with the option `--env=testing`.

The command checks only pending migrations and executes them one at a time. It uses the migration paths in `database/migrations` and `database/settings` by default.

Installation
------------

[](#installation)

The package can be installed with Composer:

```
composer require --dev roslov/laravel-migration-checker
```

General usage
-------------

[](#general-usage)

### 1. Ensure a clean test database

[](#1-ensure-a-clean-test-database)

Run the checker against a disposable database. It must be empty, so the schema snapshot reflects only what your migrations create.

### 2. Run the checker

[](#2-run-the-checker)

You can run the command to check your migrations in the test environment:

```
php artisan migration-checker:check --env=testing -vv
```

By default, the command searches for migrations in such folders:

- `database/migrations`
- `database/settings`

But you can add extra paths. For example, if there are some vendors that add their migrations. Use `--extra-path` for this:

```
php artisan migration-checker:check --env=testing -vv \
    --extra-path=vendor/laravel/sanctum/database/migrations \
    --extra-path=vendor/another-vendor/some-project/database/migrations
```

Be careful to run it in the test environment, otherwise you can damage your data.

You can target a specific connection if you have multiple databases configured:

```
php artisan migration-checker:check --env=testing --database=mysql_testing -vv
```

### 3. Review output

[](#3-review-output)

The output example of the successful run:

```
[info] Migration check started.
[info] Preparing migration environment...
[info] Checking if another migration can be applied...
[info] Saving the current state...
[info] Applying the up migration...
[info] Applying the down migration...
[info] Saving the state after up and down migrations...
[info] Comparing the states...
[info] The up and down migrations have been applied successfully without any state changes.
[info] Applying the up migration before the next step...
[info] Checking if another migration can be applied...
[info] There are no migrations available.
[info] Cleaning up migration environment...
[info] Migration check completed successfully.

```

The output example of the failed run:

```
[info] Migration check started.
[info] Preparing migration environment...
[info] Checking if another migration can be applied...
[info] Saving the current state...
[info] Applying the up migration...
[info] Applying the down migration...
[info] Saving the state after up and down migrations...
[info] Comparing the states...
[error] The down migration has resulted in a different schema state after rollback.
--- Original
+++ New
@@ @@
 ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci

+-- Table:
+event
+
+-- Create Table:
+CREATE TABLE `event` (
+  `id` bigint(20) NOT NULL AUTO_INCREMENT,
+  `microtime` double(16,6) NOT NULL COMMENT 'Unix timestamp with microseconds',
+  `producer_name` varchar(64) NOT NULL COMMENT 'Producer name',
+  `body` varchar(4096) NOT NULL COMMENT 'Full message body',
+  `created_at` timestamp NOT NULL DEFAULT current_timestamp() COMMENT 'Creation timestamp',
+  `updated_at` timestamp NOT NULL DEFAULT current_timestamp() ON UPDATE current_timestamp() COMMENT 'Update timestamp',
+  PRIMARY KEY (`id`)
+) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci COMMENT='Events (transactional outbox)'
+
+
 -- ### Triggers ###

In MigrationChecker.php line 67:

  [Roslov\MigrationChecker\Exception\SchemaDiffersException]
  The up and down migrations have resulted in a different schema state after rollback.

```

If you want to run it in your CI, you can do something like this:

```
# Stops the previously running test environment and database (if the previous run failed)
docker stop test-db || true
docker network rm test-network || true
# Prepares the new test environment
docker network create test-network
# Starts the test database
docker run --name test-db --network=test-network -d --rm \
    -e MYSQL_ROOT_PASSWORD=testrootpass \
    -e MYSQL_DATABASE=test \
    -e MYSQL_USER=testuser \
    -e MYSQL_PASSWORD=testpass \
    mysql:8.4.5 --character-set-server=utf8mb4 --collation-server=utf8mb4_0900_ai_ci
# Waits until the database is ready
while ! docker exec test-db \
    mysql --user=testuser --password=testpass \
    -e 'SELECT 1' \
    >/dev/null 2>&1; do
    echo 'Waiting for database connection...'
    sleep 1
done
# Runs the migration check.
# This command should fail if there are problems with migrations
docker run --network=test-network --rm \
    your-project-image:latest \
    php artisan migration-checker:check --env=testing -vv
# Stops the test database
docker stop test-db
# Stops the test environment
docker network rm test-network
```

Testing
-------

[](#testing)

### Unit testing

[](#unit-testing)

The package is tested with [PHPUnit](https://phpunit.de/). To run tests:

```
./vendor/bin/phpunit
```

inside a container, or

```
make test
```

from the host machine.

### Code style analysis

[](#code-style-analysis)

The code style is analyzed with [PHP\_CodeSniffer](https://github.com/squizlabs/PHP_CodeSniffer) and [PSR-12 Ext coding standard](https://github.com/roslov/psr12ext). To run code style analysis:

```
./vendor/bin/phpcs --extensions=php --colors --standard=PSR12Ext --ignore=vendor/* -p -s .
```

inside a container, or

```
make phpcs
```

from the host machine.

### Static analysis

[](#static-analysis)

Static analysis is performed with [PHPStan](https://phpstan.org/). To run it:

```
./vendor/bin/phpstan analyse --memory-limit=256M .
```

inside a container, or

```
make phpstan
```

from the host machine.

### All validations

[](#all-validations)

To run all validations at once (syntax check, code style, static analysis, and Rector):

```
make validate
```

###  Health Score

38

—

LowBetter than 85% of packages

Maintenance64

Regular maintenance activity

Popularity22

Limited adoption so far

Community7

Small or concentrated contributor base

Maturity49

Maturing project, gaining track record

 Bus Factor1

Top contributor holds 100% of commits — single point of failure

How is this calculated?**Maintenance (25%)** — Last commit recency, latest release date, and issue-to-star ratio. Uses a 2-year decay window.

**Popularity (30%)** — Total and monthly downloads, GitHub stars, and forks. Logarithmic scaling prevents top-heavy scores.

**Community (15%)** — Contributors, dependents, forks, watchers, and maintainers. Measures real ecosystem engagement.

**Maturity (30%)** — Project age, version count, PHP version support, and release stability.

###  Release Activity

Cadence

Every ~5 days

Total

8

Last Release

88d ago

Major Versions

0.5.1 → 1.0.02026-02-13

### Community

Maintainers

![](https://www.gravatar.com/avatar/464fc58072b48a348a355eeca35b6fe2e341fd494b4ffb8e30f2007c3a2a6ad5?d=identicon)[tr](/maintainers/tr)

---

Top Contributors

[![roslov](https://avatars.githubusercontent.com/u/6573063?v=4)](https://github.com/roslov "roslov (16 commits)")

---

Tags

laraveldevmigrationdatabasedownUp

###  Code Quality

TestsPHPUnit

Static AnalysisPHPStan, Rector

Type Coverage Yes

### Embed Badge

![Health badge](/badges/roslov-laravel-migration-checker/health.svg)

```
[![Health](https://phpackages.com/badges/roslov-laravel-migration-checker/health.svg)](https://phpackages.com/packages/roslov-laravel-migration-checker)
```

###  Alternatives

[cybercog/laravel-clickhouse

ClickHouse migrations for Laravel

163166.8k](/packages/cybercog-laravel-clickhouse)[clickbar/laravel-magellan

This package provides functionality for working with the postgis extension in Laravel.

423715.4k1](/packages/clickbar-laravel-magellan)[dragon-code/migrate-db

Easy data transfer from one database to another

15717.4k](/packages/dragon-code-migrate-db)[toponepercent/baum

Baum is an implementation of the Nested Set pattern for Eloquent models.

3154.7k](/packages/toponepercent-baum)[dragon-code/laravel-data-dumper

Adding data from certain tables when executing the `php artisan schema:dump` console command

3418.6k](/packages/dragon-code-laravel-data-dumper)[ntanduy/cloudflare-d1-database

Easy configuration and setup for D1 Database connections in Laravel.

215.4k](/packages/ntanduy-cloudflare-d1-database)

PHPackages © 2026

[Directory](/)[Categories](/categories)[Trending](/trending)[Changelog](/changelog)[Analyze](/analyze)
