Weave Code
Weaver
Helps Laravel developers discover, compare, and choose open-source packages. See popularity, security, maintainers, and scores at a glance to make better decisions.
Feedback
Share your thoughts, report bugs, or suggest improvements.
Subject
Message

Laravel How It Works Laravel Package

jeffersongoncalves/laravel-how-it-works

A Laravel package for adding clear "How it works" step-by-step sections to your app. Define and order steps, then render a ready-made explanation block to help users understand your product flow, ideal for onboarding pages, landing sections, and docs.

View on GitHub
Deep Wiki
Context7

Getting Started

  • Install with composer require <vendor>/<package> and publish the migration/config: php artisan vendor:publish --tag="<package>-migrations" (and --tag="<package>-config" if a config file ships). Confirm the tags exist with php artisan vendor:publish listing before assuming names.
  • Run php artisan migrate. The package ships a table for steps plus a translations table (or a json translations column) backed by spatie/laravel-translatable; check which storage strategy the migration uses before you write queries by hand.
  • First use case: create a handful of steps, translate them, and render them in order on a marketing page.
use Vendor\Package\Models\Step;

Step::create([
    'title' => ['en' => 'Create an account', 'fr' => 'Créer un compte'],
    'description' => ['en' => 'Sign up in seconds.', 'fr' => 'Inscrivez-vous en quelques secondes.'],
    'is_active' => true,
]);
@foreach (\Vendor\Package\Models\Step::active()->ordered()->get() as $step)
    <div class="step">
        <h3>{{ $step->title }}</h3>   {{-- auto-resolved for current locale --}}
        <p>{{ $step->description }}</p>
    </div>
@endforeach

Where to look first: the model (fillable/translatable arrays, scopes), the migration (column names for the sort key and active flag), and the config file for fallback locale behaviour. Those three files tell you 90% of what the package actually does.

Implementation Patterns

Seeding content is the primary workflow. These are editorial rows, not user-generated data. Put steps in a seeder so environments stay reproducible, and give each step an explicit sort_order rather than relying on insert order.

Ordering. Use the package's ordered() scope in every read path. If you ever sort in PHP ($steps->sortBy(...)), you will break pagination and defeat the point of the column. Reordering is a bulk update — wrap it in a transaction and, if the sort key is unique, order the writes carefully or defer the unique index.

Locale handling. Because translation resolution is delegated to spatie/laravel-translatable, read properties ($step->title) and let the package return the current locale with fallback. Do not read $step->getTranslation('title', 'en') in views — that hardcodes a locale and bypasses the fallback config. For admin edit forms, keep the raw array ($step->getTranslations('title')) so every locale round-trips on save.

API / Inertia responses. Prefer an API Resource so the front end gets a stable shape:

return StepResource::collection(Step::active()->ordered()->get());
// -> ['id', 'title', 'description', 'sort_order']

Resolve translations server-side (current locale) instead of shipping all locales to the client — it halves payload size and keeps fallback logic in one place.

Admin integration. For Nova/Filament, map each locale to its own field with a ->rules()/translatable wrapper, and expose sort_order as a reorderable column. If the package has no reorder UI, a simple position integer + nova-sortable-style handler is usually less work than building drag-and-drop from scratch.

Caching. This content changes rarely and is read constantly. Cache the resolved, ordered collection per locale (cache()->remember("steps.{$locale}", ...)) and flush on save/delete/reorder via a model observer. Include the locale in the key; include the fallback locale if fallback output differs.

Blade component. Wrap the loop in an anonymous component (<x-how-it-works />) so the query, the active scope, and the ordering live in one place instead of being copy-pasted across pages.

Gotchas and Tips

  • Do not hand-roll where('title->en', ...) for the common case — the JSON path syntax differs between MySQL, Postgres, and SQLite, and spatie/laravel-translatable provides whereTranslation()/whereTranslatable() for a reason. Raw JSON where-clauses are the #1 source of "works locally, fails on Postgres" bugs here.
  • Eager-loading will not save you. Translations stored as JSON are already on the row; if the package uses a separate translations table, then with('translations') matters and you will get N+1 without it. Check the migration first.
  • Fallback locale can leak. With fallback enabled, a French page may render English text with no indication. If you need strictness, set the fallback to null per-locale or assert coverage in a test that fails on missing keys for shipped locales.
  • sort_order collisions. Seeding without explicit orders, or deleting a step and re-adding it, drifts the sequence. Re-normalise on delete, or accept gaps and never assume contiguity (sort_order = 1,2,3 is not guaranteed).
  • Route model binding + slugs. If steps get a translated slug, getRouteKeyName() will resolve only the current locale's slug. Either keep a non-translated canonical slug or implement resolveRouteBinding() across all locales — otherwise switching language 404s.
  • Cache invalidation on reorder is easy to miss. Saving an individual step flushes that step, but a bulk reorder saves many. Hook the observer on the reorder path too, not just saved.
  • Config quirks. Fallback locale and required-locale settings usually read from the package config, which reads from config('app.fallback_locale') — changing APP_LOCALE mid-project can silently change rendered output in tests. Assert locale explicitly in tests (app()->setLocale('fr')) rather than depending on the ambient config.
  • Extension points. The model is typically bound/configurable; if you need extra fields (icon, CTA link, duration), extend the model or add a migration rather than adding unmanaged columns — and re-check that $translatable and $fillable include anything you add, since those arrays are not auto-derived.
  • Testing. Use RefreshDatabase and assert on the resolved string for a set locale, plus one assertion on the raw translation array. That combination catches both "wrong locale shown" and "translation silently not saved" regressions in a single test file.
Weaver

How can I help you explore Laravel packages today?

Conversation history is not saved when not logged in.
Prompt
Add packages to context
No packages found.
3mdikram/worldmoneywords
snowsoft/config
itmosoft/laravel-subscriptions
larva/laravel-ai-qwen
diephp/sequences
users-au/socialite-provider
twidpay/twid-logger
mrnewport/laravel-plaid
mrnewport/laravel-repo
mrnewport/laravel-docsign
mrnewport/laravel-stow
mrnewport/laravel-flow
mrnewport/laravel-priceable
mrnewport/laravel-nestedterms
fredmeng/laravel-apidoc-generator
itstructure/laravel-multilingual-tools
pdustdar/elasticsearch
markupai/php-sdk
rlacerda83/lumem-microservice-shipment
uni-method/symfony-lib