devdojo/themes
DevDojo Themes is a lightweight Laravel package for adding switchable themes to your application. Organize theme views, assets, and settings, then activate a theme to change your app’s look without modifying core code.
Architecture fit
devdojo/themes is a thin Laravel package: a service provider that registers config, publishes theme assets/views, and provides a resolution layer for swapping the active Blade theme — with the selection UI surfaced through Voyager's admin panel. As a TPM, the distinction that matters is that the durable value here is the theme resolution abstraction, not the Voyager binding. The abstraction (active theme → view path + asset path + fallback chain) is a ~200-line concern most teams would otherwise write themselves.
Fit is therefore conditional:
Integration feasibility
Mechanically straightforward: Composer install, publish config and assets, create resources/views/themes/{slug} and public/themes/{slug}, seed theme metadata, register the middleware or helper that sets the active theme. Expect a day of integration work for a developer familiar with Laravel packaging, plus design/content work to populate themes.
The friction is not installation — it is verifying the constraints. Before committing, confirm from composer.json: required PHP version, illuminate/* version range, and whether tcg/voyager is a hard require or a suggest. A hard Voyager require is the deciding factor, because Voyager's Laravel support ceiling becomes your application's upgrade ceiling.
Technical risk
| Risk | Severity | Note |
|---|---|---|
| Voyager coupling | High | Binds theme layer to an admin panel with its own stalled release cadence |
| Abandonment / bus factor | High | 21 stars, 0 dependents, single-vendor maintenance; last release Aug 2024 but low activity signal |
| Dependency lock-in | High | Composer constraints can block future Laravel majors — the most expensive failure mode |
| View resolution fragility | Medium | Custom view finders interact badly with view:cache and per-request theming |
| Supply chain surface | Medium | Voyager transitively pulls image/manipulation and admin-panel dependencies |
The 0-dependents figure is the loudest signal: there is no ecosystem exercising this code in production, so you will be the first to hit edge cases. Budget for treating this as a vendored internal component rather than a third-party dependency.
Key questions
require or suggest? Can the theme layer be used standalone?View::addLocation, a custom FileViewFinder, or a middleware-driven path swap? This determines cache behavior and whether per-request (multi-tenant) theming is viable.asset(), or Vite? Does it compose with our build?Stack fit
Assumes PHP 8.x, Laravel, Blade, and a server-rendered front end. It composes naturally with an existing Voyager-administered monolith. It does not compose cleanly with Vite-based asset pipelines unless the theme's asset references are rewritten at the theme contract level; the package predates and likely assumes simpler asset helpers. Verify this before scoping.
Migration path
resources/views/themes/default/, mirror public assets into public/themes/default/, and introduce a compatibility shim — an interface your app codes against (ThemeResolver::active(), ThemeResolver::asset()) that delegates to the package when present and falls back to a hardcoded path when absent. This shim is the actual deliverable; the package becomes an implementation detail you can swap.Compatibility
Establish and pin a support matrix: Laravel version × PHP version × Voyager version. Add a CI job that installs the lowest and highest supported combinations. Watch specifically for: Laravel's compiled view cache (theme switches must invalidate it), Voyager's settings-key persistence for the active theme, and published-asset overwrite semantics on vendor:publish --force.
Sequencing
Maintenance
Expect to own the code. Upstream activity is low and the dependent count is zero, so upstream will not surface your bugs. Budget roughly 2–5 engineer-days per year for a forked, tested copy — mostly dependency bumps and Laravel-major compatibility. The larger hidden cost is Voyager maintenance, which you inherit whether or not you use its other features.
Support
No commercial support. Community channels via DevDojo; issue throughput likely low. Requirements: a named internal owner, a written theme contract, and a documented "how to add a theme" runbook. Without those, every new theme becomes a support ticket to the platform team.
Scaling
Runtime theme resolution is cheap — config lookup plus a view path — and will not be a throughput bottleneck. Real scaling considerations:
Failure modes
view:clear, or key the cache by theme.--force in deploy pipelines; treat public/themes/* as owned content.Ramp-up
Low for the theme consumer: a Laravel developer can author a theme in hours once the contract is documented. Moderate for the operator: whoever manages themes through Voyager needs admin-panel familiarity. The genuine ramp cost is Voyager itself — if your team does not already run it, adopting this package means onboarding an entire admin framework to gain a theme dropdown, which is a poor trade. If the team is already on Voyager, ramp-up is negligible and the package is a reasonable convenience.
How can I help you explore Laravel packages today?