Laravel provides 18 months of bug fixes and two years of security fixes. That puts Laravel 11 entirely out of support since 12 March 2026, and Laravel 12 without bug fixes since 13 August 2026, with security fixes until February 2027 only. The jump to 13 is small inside the framework, and the project itself quotes a day. What costs time are the packages around it, the PHP floor of 8.3, and the places where your code relies on behaviour rather than signatures.
11 & 12 out of bug fixesTarget Laravel 13PHP 8.3 as the floorFrom 950 €
What you get
An inventory: target branch, intermediate steps, the PHP version each one needs
A package list: what exists for Laravel 13, what is abandoned, what gets replaced
The places where your own code relies on framework behaviour
The upgrade major by major, each step going live on its own
A test net around the paths that get touched and that carry money
Handover to your team, in writing and in conversation
Scope & working together
The entry point is a fixed-price first upgrade step, implementation is quoted by scope. Also for applications without tests and without the people who built them.
Remote from Germany. Straight with me, no agency in between.
The starting point
The framework is not the problem.
Laravel ships annually in the first quarter and keeps its majors deliberately narrow. For 13 the project writes that most applications can be raised without changing much application code. That is not marketing but checkable: the upgrade guide per major is short, and the mechanical part has tooling. Anyone who only raises the framework really is done quickly.
The sentence that sinks projects sits in the small print of the same page: for all additional libraries, only the latest major release receives bug fixes. So an application with Horizon, Passport, Cashier, Scout, Telescope and a dozen community packages has as many timelines as it has dependencies, and if one of them has not seen a commit in three years it holds the whole jump. This is the point where cost estimates diverge.
Below that sits the language version: Laravel 13 requires PHP 8.3 as a minimum, Laravel 12 still ran from 8.2. Anyone on PHP 8.0 or below has two projects ahead, not one. And there is a trait that separates Laravel from Symfony: because much of it runs through facades, Eloquent and container bindings, a change often shows up not at boot but in behaviour, in a query that sorts differently or an exception that now lands somewhere else. No compiler finds that. Only a test does.
Does any of this sound familiar?
The application runs on Laravel 11 or older and receives no security updates.
Composer reports conflicts as soon as a single dependency is raised.
A community package is no longer maintained and blocks the jump.
The PHP version is not enough for Laravel 13, and nobody knows what depends on it.
An earlier upgrade attempt was abandoned and sits around as a branch.
After the last upgrade, errors only surfaced weeks later because tests are missing.
What I do
What happens along the way
01
Fixing the target branch and the order
InventoryComposer analysisPHP matrix
The target branch is usually 13, because it receives security fixes until 2028. Anyone on 10 today gets there via 11 and 12, not because the intermediate steps are an end in themselves, but because each major has its own upgrade guide and otherwise an error can no longer be traced to a step. The result is a chain with a PHP prerequisite per stage.
02
Sorting packages by their timelines
ComposerFirst-party packagesAnti-corruption layer
The same three questions per dependency: does it exist for the target branch, is it still maintained, and what takes its place if not. First-party packages such as Horizon, Passport or Cashier carry their own majors, which have to match the Laravel version. Abandoned packages get a maintained alternative, a narrow implementation of exactly what you actually use, or a boundary behind which they keep running, encapsulated.
03
The safety net first, not last
Pest / PHPUnitCharacterization tests
With Laravel this is not a precaution but the core of it: because a jump rarely breaks the boot and instead shifts behaviour, tests around the paths that carry money are needed beforehand. Where none exist, characterization tests are written. They record what the application does today, regardless of whether that is correct.
04
Making the mechanical part mechanical
RectorLaravel ShiftLarastan / PHPStan
Renamed methods, changed signatures, moved configuration keys: this part gets automated, with Rector rule sets and, where it fits, with Laravel Shift. What remains afterwards is measured rather than estimated, and that is exactly what quotes otherwise disagree about.
05
One major at a time
Step-by-step rolloutWay back per stepMix to Vite
Each stage is a step of its own with its own way back, and each goes live on its own. Taking two majors in one go saves time on paper and gives it back at the first error. The environment belongs to this too, including the part that gets forgotten: the build chain. Anyone still running Laravel Mix moves to Vite along the way.
06
Afterwards: not falling behind again
CI checksDependabotMaintenance plan
To close, the things that keep the distance small: tests and static analysis in the pipeline, automated dependency checks, and a note in the calendar for when the chosen branch drops out of support. On an annual cadence that is no longer a project but an appointment.
Is your Laravel sitting on an unmaintained branch?
Send me the key facts. You get the chain of intermediate steps and the effort involved before you commission anything.
Four steps, and after the first one you know the route and its stops along the way. No step assumes that you commission the next one.
STEP 01
Key facts and access
Laravel version, PHP version, rough size, test coverage, the composer.json. Read access to the repository is enough for the assessment.
STEP 02
Assessment
Target branch, intermediate steps, packages by replaceability, the places carrying behavioural risk. Enough for you to decide, including against me.
STEP 03
Securing and clearing up
A test net around the paths that carry money, then the mechanical part automated. Both happen before the first version number goes up.
STEP 04
Rolling out stage by stage
One jump, one rollout, one way back. To close, checks in the pipeline and the handover.
Entry offer
First upgrade step. From 950 €
Starting price. The further intermediate steps are quoted by scope, and always before they begin.
Not an expert report but a start: the first jump of your upgrade chain is carried out in a branch of its own. Whatever the tooling does not handle stands afterwards as a measured list, not an estimate.
What you get
Target branch and the chain of intermediate steps, with the PHP version each stage needs
The first jump carried out in a branch of its own, each run its own commit
What remains open afterwards, as a measured list with location and effort
Package check: available, maintained, replaceable, first-party and community kept apart
The places with behavioural risk named, where a test is needed before the jump
An assessment of test coverage and the safety net required
One hour discussing the results, recorded on request
What you do not get
Not the full upgrade chain. The branch carries the first jump, not all of them
No fixing of what remains open after the automated runs
No refactoring, no new features
No PHP upgrade, that is a project of its own with a page of its own
No frontend work. Moving from Mix to Vite belongs to the build chain, a new theme does not
No security assessment in the sense of a penetration test
Read access to the repository is enough. The upgrade branch is created alongside, your main branch stays untouched
The branch is yours and stays yours, even if you decide against the implementation
Price net, plus VAT
From around 200,000 lines or several applications, the scope is agreed beforehand
The amount is credited if you commission the implementation afterwards
You are committed to nothing. Some clients carry the chain on themselves from there, and that is a valid outcome
Bug fixes and security fixes arrive again, and the question in the next audit is answered.
Dependencies movable again
A new package can be installed without three others blocking it. That was the actual standstill before.
The annual cadence becomes an appointment
Laravel ships every year. With tests and checks in the pipeline, the next jump is a week in the calendar instead of a project with a budget request.
A net that stays
The tests written for the upgrade are yours afterwards and secure every further change.
Technologies I use
What I work with
Framework
Laravel 13
Laravel 12
Eloquent
Blade
First-party
Horizon
Passport
Sanctum
Cashier
Scout
Language
PHP 8.2
PHP 8.3
PHP 8.4
PHP 8.5
Analysis
Rector
Larastan / PHPStan
Laravel Shift
Pint
Tests
Pest
PHPUnit
Dusk
Characterization tests
Packages
Composer
Packagist
Composer Audit
Dependabot
Data
MySQL
MariaDB
PostgreSQL
Valkey / Redis
Delivery
Docker
Vite
GitHub Actions
AWS
Evidence
PHP and Zend Framework certified.
Most suppliers know the destination. With an old system, what decides the outcome is whether someone also knows the starting point: why a passage is written the way it is, and what replacing it sets off. Zend Technologies no longer exists under that name, and neither do the exams of the time. For the database side there is an Oracle certification on MySQL 5, because that is where the quieter traps sit: character sets, collations and a strict mode that starts refusing what used to pass.
A pending PHP 8 upgrade was the trigger, and Laravel was modernized as the framework base. Alongside it a new search architecture and the move to Kubernetes, all while the editorial team kept publishing, without a single day of downtime.
Why the tools from a Symfony upgrade do not bite here, and the four places that really cost time: Eloquent, the package ecosystem, the front-end chain, and the project skeleton that drifts over the years.
Read the article
Who you are talking to
Directly with me as a freelancer. No agency in between.
I am Tim Rutte. More than 20 years in software development, and Laravel is one of the frameworks whose existing systems I have taken over and modernized. You talk to the person who touches your code, from the first call to the handover.
Laravel provides 18 months of bug fixes and two years of security fixes. As of August 2026 that means: Laravel 13 (since March 2026) is the current branch, with security fixes until March 2028. Laravel 12 has had no bug fixes since 13 August 2026 and security fixes until February 2027. Laravel 11 has been entirely out of support since 12 March 2026, Laravel 10 since February 2025. Anything below 12 is therefore a security matter, not just a comfort one.
Laravel says an upgrade takes a day. Why would I need someone for that?+
Because the sentence is true and still misleading. It applies to the framework, which is the predictable part. Your bill is written by two other things: the packages, where only the latest major receives bug fixes, and the PHP floor. If both are fine, an upgrade really is small. Then the first step tells you exactly that, and you have spent 950 euros on a reliable answer instead of three weeks on a surprise.
What does a Laravel upgrade cost?+
The first upgrade step costs from 950 euros net and tells you what the implementation costs. The range after that does not depend on the size of the codebase but on two other numbers: how many packages are abandoned, and whether tests exist. Implementation is quoted afterwards by scope, at a fixed price or by time spent to suit the project and the model you prefer, and always before it begins.
Do you use Laravel Shift?+
Where it fits, yes. Shift handles the mechanical part of a major jump reliably and cheaply, and charging day rates for that would be dishonest. What Shift cannot do is decide: whether an abandoned package gets replaced or encapsulated, whether PHP or Laravel goes up first, and which paths need a test net before the jump. That part is the work.
Can several majors be skipped at once?+
Technically often yes, in practice rarely sensible. Each major has its own upgrade guide, and anyone taking two stages in one go can no longer trace an error to a stage afterwards. With Laravel there is the added point that changes tend to show up in behaviour rather than at boot, and that is exactly the kind of error you want to isolate one at a time.
What if a package is no longer maintained?+
That is the most common hard case. Three answers apply: a maintained alternative with the same job, your own narrow implementation of exactly what you use, or a boundary behind which the old package keeps running until it is replaced. Which one holds is in the assessment, with the effort involved.
Do I need a PHP upgrade first?+
If you are below PHP 8.3, yes, that is the floor for Laravel 13. Changing both at once is the most reliable way to lose the ability to trace an error. Which step comes first depends on the starting point and is in the assessment; the PHP upgrade has a page and a scope of its own.
Does the application have to be taken offline?+
No. The test net and the automated runs happen alongside the running system, in a branch of its own. Every version jump afterwards is a rollout of its own with its own way back, like any other change.
We have no tests. Is this possible at all?+
Yes, and it is the normal case. It only shifts the order: first a net is built around the paths that carry money, then things are raised. With Laravel that is not caution but necessity, because a jump shifts behaviour rather than breaking the boot. The tests are yours afterwards.
From PHP 5.6, 7 or early 8 to a supported version, while everything keeps running: compatibility assessment, a test net, automated rewriting, staged rollout.