<!-- mobian-agent-page publisher="dailydev" canonical="https://daily.dev/posts/difflock-lint-laravel-migrations-and-diff-your-schema-laeif7wfj" -->

---
title: Difflock: Lint Laravel Migrations and Diff Your Schema
description: Difflock is a new Laravel package by Rati Rukhadze that lints pending database migrations against the live schema, flagging risky operations like non-null...
canonical: https://daily.dev/posts/difflock-lint-laravel-migrations-and-diff-your-schema-laeif7wfj
twitter:card: summary_large_image
twitter:site: @dailydotdev
og:type: website
og:site_name: daily.dev
og:title: Difflock: Lint Laravel Migrations and Diff Your Schema | daily.dev
og:description: Difflock is a new Laravel package by Rati Rukhadze that lints pending database migrations against the live schema, flagging risky operations like non-null...
og:url: https://daily.dev/posts/difflock-lint-laravel-migrations-and-diff-your-schema-laeif7wfj
og:image: https://api.daily.dev/og/posts/lAeif7wFj.png
og:image:alt: Difflock: Lint Laravel Migrations and Diff Your Schema
og:image:width: 1200
og:image:height: 630
og:locale: en
---

> ## Documentation Index
> Fetch the complete documentation index at: https://daily.dev/llms.txt
> Use this file to discover all available pages before exploring further.

# Difflock: Lint Laravel Migrations and Diff Your Schema

**[Laravel News](https://daily.dev/sources/ln)** · 4 min read · 20 upvotes · 4 comments

## Summary

Difflock is a new Laravel package by Rati Rukhadze that lints pending database migrations against the live schema, flagging risky operations like non-null column additions on populated tables, destructive drops, renames, and cascading deletes that bypass model events. It records schema baselines as JSON for diffing between connections or against committed snapshots, offers a migrate guard command to block risky migrations before they run, and provides CI checks with distinct exit codes. It also ships MCP tools so AI coding agents can lint a migration or check table context before writing a file. Difflock 1.0.0 requires PHP 8.3 and supports Laravel 12 and 13, working with MySQL, MariaDB, PostgreSQL, and SQLite.

## Full article

daily.dev links to this article rather than hosting it. Read it at the original source: <https://laravel-news.com/difflock-migration-linter>

## Questions this post answers

### What does Difflock check for when linting Laravel migrations?

Difflock analyzes pending Laravel migrations against the live database schema to flag destructive operations, column changes, indexes, foreign keys, and sensitive column names. It catches issues static analysis on an empty test database would miss, such as adding a non-null column to a populated table, dropColumn calls, column renames, and cascadeOnDelete deleting child rows outside model events and observers.

_Teams hardening migration review before production deploys can track tools like this through daily.dev._

### How does Difflock detect schema drift between database environments?

Difflock records an observed schema snapshot with the php artisan difflock:diff --save command, writing a committable database/difflock/schema.json file containing tables, columns, indexes, defaults, and foreign keys but no row data or credentials. Running difflock:diff again compares the current connection against that baseline, or you can compare two configured connections directly with --from and --to flags.

_Anyone comparing staging and production schemas can follow database drift tooling like this on daily.dev._

### What are the requirements to install the Difflock Laravel package?

Difflock 1.0.0 requires PHP 8.3 and supports Laravel 12 and 13, working with MySQL, MariaDB, PostgreSQL, and SQLite. Install it via composer require heyosseus/difflock --dev, then publish its config and run php artisan difflock:doctor to check the connection, pending migrations, registered rules, and write access of the configured database role.

_Laravel developers evaluating migration safety tooling can keep up with releases like this on daily.dev._

## Community discussion

Top comments from developers on daily.dev.

**@agustinbarrientos** · 1 upvotes

> Can a baseline acceptance expire when the table gets bigger? I'd want a row-count limit linked to that exception. The next deployment should ask for another review once it goes over that limit.

**@pdfopsdev** · 0 upvotes

> does the non-null check look at server version? on pg 11+ and mysql 8 a constant default is basically free so that flag is mostly noise. the one that bites in laravel is index creation, CREATE INDEX CONCURRENTLY can't run in the migration transaction unless you set $withinTransaction = false.

**@ristotoldsep** · 0 upvotes

> I'd rather a migration hurt my feelings in CI than my database in production.

## Similar posts on daily.dev

- [Laravel Schema Sentinel: Detect and Fix Database Schema Drift](https://daily.dev/posts/laravel-schema-sentinel-detect-and-fix-database-schema-drift-hmb4acjqr) · Laravel News · 71 upvotes · 5 comments
- [Laravel Lock: Distributed Locks for Models and Routes](https://daily.dev/posts/laravel-lock-distributed-locks-for-models-and-routes-2prsaaot3) · Laravel News · 27 upvotes · 5 comments
- [There's no artisan schema:show, so I built one](https://daily.dev/posts/there-s-no-artisan-schema-show-so-i-built-one-jxodfs8j7) · FREEK.DEV · 10 upvotes · 4 comments

---

Tags: [#database](https://daily.dev/tags/database), [#cicd](https://daily.dev/tags/cicd), [#php](https://daily.dev/tags/php), [#laravel](https://daily.dev/tags/laravel), [#mcp](https://daily.dev/tags/mcp)

[View this post on daily.dev](https://daily.dev/posts/difflock-lint-laravel-migrations-and-diff-your-schema-laeif7wfj)

```json
{"@context":"https://schema.org","@graph":[{"@type":"Organization","@id":"https://daily.dev/#organization","name":"daily.dev","url":"https://daily.dev","logo":{"@type":"ImageObject","url":"https://daily.dev/apple-touch-icon.png","width":180,"height":180},"sameAs":["https://twitter.com/dailydotdev","https://github.com/dailydotdev","https://www.linkedin.com/company/daily-dev-ltd"]},{"@type":"WebSite","@id":"https://daily.dev/#website","url":"https://daily.dev","name":"daily.dev","publisher":{"@id":"https://daily.dev/#organization"},"potentialAction":{"@type":"SearchAction","target":{"@type":"EntryPoint","urlTemplate":"https://daily.dev/search?q={search_term_string}"},"query-input":"required name=search_term_string"}}]}
{"@context":"https://schema.org","@type":"TechArticle","headline":"Difflock: Lint Laravel Migrations and Diff Your Schema","url":"https://daily.dev/posts/difflock-lint-laravel-migrations-and-diff-your-schema-laeif7wfj","mainEntityOfPage":{"@type":"WebPage","@id":"https://daily.dev/posts/difflock-lint-laravel-migrations-and-diff-your-schema-laeif7wfj"},"datePublished":"2026-09-21T13:29:12.255Z","dateModified":"2026-09-21T13:29:33.174Z","description":"Difflock is a new Laravel package by Rati Rukhadze that lints pending database migrations against the live schema, flagging risky operations like non-null...","image":"https://media.daily.dev/image/upload/f_auto,q_auto/v1/posts/116b3110ebb6382deeefe466a4797804?_a=AQAEuop","thumbnailUrl":"https://media.daily.dev/image/upload/f_auto,q_auto/v1/posts/116b3110ebb6382deeefe466a4797804?_a=AQAEuop","isAccessibleForFree":true,"articleSection":"Laravel News","inLanguage":"en","publisher":{"@type":"Organization","name":"daily.dev","url":"https://daily.dev","logo":{"@type":"ImageObject","url":"https://daily.dev/apple-touch-icon.png","width":180,"height":180}},"author":{"@type":"Organization","name":"Laravel News","logo":"https://media.daily.dev/image/upload/t_logo,f_auto/v1/logos/ln","url":"https://daily.dev/sources/ln"},"commentCount":4,"discussionUrl":"https://daily.dev/posts/difflock-lint-laravel-migrations-and-diff-your-schema-laeif7wfj","interactionStatistic":[{"@type":"InteractionCounter","interactionType":{"@type":"LikeAction"},"userInteractionCount":20},{"@type":"InteractionCounter","interactionType":{"@type":"CommentAction"},"userInteractionCount":4}],"keywords":"database,cicd,php,laravel,mcp","timeRequired":"PT4M"}
{"@context":"https://schema.org","@type":"BreadcrumbList","itemListElement":[{"@type":"ListItem","position":1,"name":"Home","item":"https://daily.dev"},{"@type":"ListItem","position":2,"name":"Laravel News","item":"https://daily.dev/sources/ln"},{"@type":"ListItem","position":3,"name":"Difflock: Lint Laravel Migrations and Diff Your Schema"}]}
{"@context":"https://schema.org","@type":"WebPage","@id":"https://daily.dev/posts/difflock-lint-laravel-migrations-and-diff-your-schema-laeif7wfj","comment":[{"@type":"Comment","text":"Can a baseline acceptance expire when the table gets bigger? I’d want a row-count limit linked to that exception. The next deployment should ask for another review once it goes over that limit.","datePublished":"2026-09-24T01:00:24.079Z","url":"https://daily.dev/posts/lAeif7wFj#c-6MiMM0mlj","author":{"@type":"Person","name":"Agustin Barrientos","url":"https://daily.dev/agustinbarrientos","image":"https://media.daily.dev/image/upload/s--5ayxQnqn--/f_auto/v1788281802/avatars/avatar_wQYYVe5Tbj0NJ7C7qPoa8?_a=BAMAMicg0"},"interactionStatistic":{"@type":"InteractionCounter","interactionType":{"@type":"LikeAction"},"userInteractionCount":1}},{"@type":"Comment","text":"does the non-null check look at server version? on pg 11+ and mysql 8 a constant default is basically free so that flag is mostly noise. the one that bites in laravel is index creation, CREATE INDEX CONCURRENTLY can’t run in the migration transaction unless you set $withinTransaction = false.","datePublished":"2026-09-21T18:02:37.888Z","url":"https://daily.dev/posts/lAeif7wFj#c-5eJPupCJH","author":{"@type":"Person","name":"PDFops","url":"https://daily.dev/pdfopsdev","image":"https://media.daily.dev/image/upload/s---8isRBKc--/f_auto/v1782922291/avatars/avatar_orjMeK8QKaaVZwGq7ScPz?_a=BAMAMicg0"}},{"@type":"Comment","text":"I’d rather a migration hurt my feelings in CI than my database in production.","datePublished":"2026-09-23T14:18:44.429Z","url":"https://daily.dev/posts/lAeif7wFj#c-iqYu3t77v","author":{"@type":"Person","name":"Risto Tõldsep","url":"https://daily.dev/ristotoldsep","image":"https://lh3.googleusercontent.com/a/ACg8ocLDWc6mZn0JwNmXXw6WY0L_HJ6pegzRttooC5VgtXESHSj3MNYx=s96-c"}}]}
{"@context":"https://schema.org","@type":"FAQPage","@id":"https://daily.dev/posts/difflock-lint-laravel-migrations-and-diff-your-schema-laeif7wfj#faq","mainEntity":[{"@type":"Question","name":"What does Difflock check for when linting Laravel migrations?","acceptedAnswer":{"@type":"Answer","text":"Difflock analyzes pending Laravel migrations against the live database schema to flag destructive operations, column changes, indexes, foreign keys, and sensitive column names. It catches issues static analysis on an empty test database would miss, such as adding a non-null column to a populated table, dropColumn calls, column renames, and cascadeOnDelete deleting child rows outside model events and observers. Teams hardening migration review before production deploys can track tools like this through daily.dev."}},{"@type":"Question","name":"How does Difflock detect schema drift between database environments?","acceptedAnswer":{"@type":"Answer","text":"Difflock records an observed schema snapshot with the php artisan difflock:diff --save command, writing a committable database/difflock/schema.json file containing tables, columns, indexes, defaults, and foreign keys but no row data or credentials. Running difflock:diff again compares the current connection against that baseline, or you can compare two configured connections directly with --from and --to flags. Anyone comparing staging and production schemas can follow database drift tooling like this on daily.dev."}},{"@type":"Question","name":"What are the requirements to install the Difflock Laravel package?","acceptedAnswer":{"@type":"Answer","text":"Difflock 1.0.0 requires PHP 8.3 and supports Laravel 12 and 13, working with MySQL, MariaDB, PostgreSQL, and SQLite. Install it via composer require heyosseus/difflock --dev, then publish its config and run php artisan difflock:doctor to check the connection, pending migrations, registered rules, and write access of the configured database role. Laravel developers evaluating migration safety tooling can keep up with releases like this on daily.dev."}}]}
```

