Laravel LSP brings framework context to every editor
Laravel’s official language server gives editors practical awareness of routes, Blade, configuration, containers, and more.
PHP awareness is not the same as Laravel awareness
An editor can understand PHP perfectly well and still miss the important parts of a Laravel application. Routes, views, config keys, environment variables, and container bindings are not always symbols that a generic PHP tool can resolve reliably. That missing framework context is where a dedicated language server becomes useful.
Laravel LSP is the official effort to expose that context through the Language Server Protocol. Rather than locking the experience into one IDE, it provides completions, hover information, diagnostics, document links, Go to Definition, and code actions for selected Laravel and Blade features. (github.com)
A server instead of another editor lock-in
The important detail is that it communicates over stdio. Your editor launches the process and talks to it directly, with no separate HTTP service and no proprietary integration layer required. The project recommends starting it from the Laravel application root whenever possible. (github.com)
The repository documents official integrations for VS Code and Zed, while the VS Code extension also works with Cursor. Neovim and OpenCode are covered as well, so trying it does not require moving a project to a different editor. (github.com)
What it knows about a Laravel application
The documented scope includes routes, views and Blade, translations, configuration, environment variables, assets, middleware, authorization, application bindings, controller actions, and storage disks. It also covers Livewire components and Inertia pages and properties. This is not vague “Laravel support”; the README lists the supported capability for each area. (github.com)
Routes, for example, provide completions, hover details, diagnostics, and document links. Calls involving config() keys and env() values get the same kind of assistance, while views and Blade also include code actions. Eloquent and validation rules are currently listed as completion-only features. (github.com)
Installing it and getting started
The documented installation is global through Composer. After that, Composer’s global bin directory needs to be available in your PATH, because the editor will run the laravel-lsp command. You do not need to add it as a dependency to every Laravel repository just to start using it. (github.com)
composer global require laravel/lspThe official Neovim setup looks for an artisan file before selecting a project root. That matters because it prevents the server from starting for every unrelated PHP repository you open. It is a small safeguard, but it reflects the fact that this tool needs a Laravel application context rather than just PHP files. (github.com)
vim.lsp.config("laravel_lsp", {
cmd = { "laravel-lsp" },
filetypes = { "php", "blade" },
root_dir = function(bufnr, on_dir)
local root = vim.fs.root(bufnr, "artisan")
if root then
on_dir(root)
end
end,
})
vim.lsp.enable("laravel_lsp")It also makes sense in container-based setups
For Sail users and self-contained homelab environments, phpEnvironment is worth noting. Its default value, auto, tries to detect Herd, Valet, Sail, Lando, DDEV, and then local PHP. If that guess does not match your setup, phpCommand can define the exact command and arguments used to run PHP. (github.com)
Priority matters here: a non-empty phpCommand overrides phpEnvironment. That makes it possible to explicitly use ./vendor/bin/sail php instead of hoping the editor process finds the correct PHP executable on its own. On a remote development box or inside a persistent container, being explicit is usually more useful than detection that only works under ideal conditions. (github.com)
Configuration without making it opaque
LSP clients pass settings through initializationOptions, and every option is optional. Individual capabilities can be disabled with settings such as routeCompletion, configDiagnostics, envHover, inertiaLink, or livewireComponentCompletion. That is useful when a specific feature clashes with another tool or simply is not relevant to a project. (github.com)
There are also Pest-specific options: pestGenerateDocBlocks and pestHelperFilePath. The first generates and refreshes helper docblocks when tests or Composer autoload files change. The second changes the output location, which defaults to storage/framework/testing/_pest.php. (github.com)
The fine print matters
Laravel LSP should not be presented as a complete replacement for every form of PHP static analysis. Its own capability matrix shows clear boundaries: Eloquent and validation rules offer completions, while Livewire components do not advertise diagnostics or code actions. It is worth testing it alongside the rest of the project tooling before removing anything from an existing workflow.
Quick fixes should not be read as a promise of universal automatic repair either. The documented configuration explicitly names envViteQuickFix for environment variables, while the feature overview lists code actions for views and Blade. If you expect project-wide refactors, perfect type inference, or automatic fixes for every Laravel error, that is not the published scope of the server. (github.com)
A practical upgrade without switching editors
The real benefit is fewer context switches. Completing a route, opening a view, checking a configuration key, or spotting an environment variable issue from the editor removes repetitive project-wide searches. Each task is small, but they happen often enough during a normal day to matter.
What I like most is that it does not force a choice between a preferred editor and Laravel-specific support. VS Code, Cursor, Zed, Neovim, and OpenCode can use the same server as a shared layer. For local Laravel work and for stacks living in a home lab, that client-server split is a sensible design choice.
Source: Laravel Magazine
Official documentation: laravel/lsp on GitHub (github.com)