opencode is a terminal coding agent you can run inside a Laravel project with the opencode command. This guide focuses on keeping it productive with Eloquent, migrations, Blade, queues, and tests, while avoiding changes that fight Laravel’s conventions.
Why opencode is a strong fit for Laravel
Laravel’s power comes from its conventions: models in app/Models, migrations in database/migrations, form requests in app/Http/Requests, jobs in app/Jobs, and tests in tests/Feature or tests/Unit. opencode can operate within those conventions when they are written down. Unlike a code generator that outputs a single file, opencode can plan a change across several layers, run php artisan test, read the failure, and adjust the code until the suite is green. That is exactly what many Laravel tasks need: a migration plus a model plus a feature test are not three isolated snippets, they are one contract. The agent also works well with Artisan commands and directory scaffolding because the expected file locations are predictable. See the opencode guide for how the agent works in a project. For a direct comparison with Claude Code, see opencode vs Claude Code: an honest comparison.
Preparing your Laravel project for opencode
The most important file is AGENTS.md in the project root. opencode reads it at the start of a session. Do not make it a generic AI prompt. For Laravel, write the commands you actually use, the folder rules, and the conventions you do not want the agent to break. A short, specific file is better than a long one.
# AGENTS.md
## Commands
- Install: composer install
- Test: php artisan test
- Lint: vendor/bin/pint --test
- Format: vendor/bin/pint
- Single test: php artisan test --filter=ExampleTest
- Migrate with seed: php artisan migrate:fresh --seed
## Folder conventions
- Models: app/Models, one class per file, use HasFactory.
- Migrations: database/migrations, timestamped names, never edit an existing migration.
- Controllers: app/Http/Controllers, stay thin, return responses only.
- Form requests: app/Http/Requests for validation.
- Jobs: app/Jobs, implement ShouldQueue for async work.
- Views: resources/views, use Blade components for repeated markup.
- Tests: tests/Feature for HTTP and tests/Unit for pure classes.
## Laravel rules
- Use route model binding and explicit route names.
- Prefer Eloquent scopes or query builder over raw SQL.
- Keep validation in Form Request classes, not controllers.
- Add fillable or guarded only where needed; do not use mass assignment without one.
- Run the full test suite before marking a task complete.
Start the agent with opencode in the project root after committing the current working tree. A clean git state makes it easier to review exactly what the agent changed. More setup details are covered in How to use opencode: a step-by-step guide.
A safe working loop: plan, implement, test, review
Treat opencode like a junior engineer who is fast but needs explicit boundaries. The loop is: plan, implement one small step, run the tests, review the diff, repeat. Do not ask for a large feature in one prompt.
Start with a planning request: “Describe the files you will create or edit for this change, and list the tests you will add.” After the plan looks right, say “Now implement step 1 only.” Then run php artisan test yourself or ask the agent to run it. Review the diff before moving on, especially migrations and model relationships.
Example prompts for common Laravel work:
- Create a migration and model for
organizationswith a one-to-many relationship tousers. Add a foreign key withconstrained()and an index. Write a feature test that creates an organization with a user and asserts the relationship. - Add a queued job that exports orders to a CSV file and dispatches it from an Artisan command. Use the
ShouldQueueinterface and write a Pest test for the job withQueue::fake(). - Refactor
OrderController@storeto use a Form Request and a service class. Keep the existing feature test passing and update the controller to return a redirect with a flash message. - Create a Blade component for an alert banner and replace the repeated alert markup in
resources/views/orderswith that component. Add a simple view test if one is missing. - Write a migration to add
soft_deletestoposts, update thePostmodel to useSoftDeletes, and add a test that soft-deleting a post hides it from the default query.
The agent handles these well because each task has a clear Laravel-shaped boundary: migration, model, test, or view component.
Tasks opencode handles well, and Laravel-specific pitfalls
opencode is usually reliable for:
- Generating a migration with the correct schema, indexes, and foreign keys when the relationship is described.
- Creating Eloquent models with relationships, casts, and accessors.
- Writing feature tests that follow the Arrange-Act-Assert pattern with
RefreshDatabase. - Building Artisan commands and wiring them to queued jobs.
- Refactoring Blade markup into components.
Watch it closely on these Laravel-specific pitfalls:
- Mass assignment: an agent may add a
create()call with request data and forget to update$fillableor$guarded. Check every new model. - N+1 issues: an eager-loading change can be undone when the agent rewrites a query. Review
with()calls in controllers and views. - Existing migrations: an agent may try to edit an old migration instead of creating a new one. Tell it explicitly never to modify applied migrations.
- Policy and middleware registration: a model may be created without a policy or a route without the expected middleware. Ask for the route list diff.
- Queue serialization: jobs that accept Eloquent models as constructor parameters are fine if the model is serializable, but an agent may pass a large object or a closure. Review job constructors.
- Blade syntax: an agent can produce a valid-looking component but miss the
@propsdirective or use{{ }}where{!! !!}is needed. Run the view tests or render the page before merging.
Verifying changes with Laravel’s test suite
Use PHPUnit or Pest; the AGENTS.md file should state which one the project uses. Ask opencode to run the full suite before considering a change complete, and to run a focused test when iterating. If a test fails, tell the agent to read the failure and fix only the failing part, not to rewrite the whole test.
The table below shows the commands to use as a verification checkpoint with the agent.
| Command | What it verifies |
|---|---|
php artisan test | Full test suite in the project’s configured runner |
php artisan test --filter=UserTest | A single test class while making a model change |
vendor/bin/pint --test | Laravel code style without modifying files |
php artisan migrate:fresh --seed | Clean schema and seeders before a test pass |
php artisan route:list | Registered routes, middleware, and route names after controller changes |
For database tests, require the agent to use RefreshDatabase. That prevents tests from leaking state between runs. For queue jobs, use Queue::fake() or run the jobs synchronously in tests. For Blade changes, a lightweight feature test that asserts the response contains the expected text is often enough; keep browser tests out of the default loop unless you already use them.
Coordinating multiple agents with AgentVera
AgentVera is a desktop app that runs opencode’s real CLI in a terminal panel alongside other agents. For Laravel work, separate git worktrees matter most: parallel agents can edit migrations, models, and tests without overwriting each other. When an agent’s turn ends, a second model reviews the diff and links findings to file:line, which catches Eloquent or Blade mistakes early. Checkpoints let you undo a bad migration or model refactor in one click, and token budgets keep long refactors from consuming the whole day.
Keep the loop small and review the diff
opencode works best in Laravel when the project’s rules are explicit in AGENTS.md and every change is small enough to verify with php artisan test. Keep migrations, models, and tests in the same task, review the diff against Laravel conventions, and use separate worktrees if you run more than one agent. That discipline turns the agent from a fast code generator into a reliable Laravel teammate.