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

Filament Otp Input Laravel Package

eg-mohamed/filament-otp-input

A Filament form component that adds a one-time password (OTP) input field to your admin panels. Users can enter verification codes with a clean, segmented input UI, making it easy to integrate OTP or PIN confirmation into Filament forms and workflows.

View on GitHub
Deep Wiki
Context7

Getting Started

filament-otp-input provides a OtpInput form field for Filament panels (v3/v4 line) that renders a segmented one-time-password entry control instead of a plain text input. Version 4.2.0 is a minor release on the 4.x line — the changelog entry published for it is a bare compare link, so treat the upgrade as a routine composer update with no migration work, but skim the diff before bumping in a large panel.

Minimal path:

  1. composer require eg-mohamed/filament-otp-input (pin ^4.2 once verified).
  2. If your panel serves assets from public/, run php artisan filament:assets after install and after every upgrade — the field ships Alpine/JS behaviour that is published, not injected at runtime.
  3. Drop the field into any form schema:
use EG\FilamentOtpInput\Forms\Components\OtpInput;

OtpInput::make('code')
    ->length(6)
    ->required();

First realistic use case: a two-step login challenge. Put the OTP field on a dedicated Filament page or a secondary step in an existing login flow, where step one collects credentials and step two verifies a code mailed or texted to the user.

Look first at the field class itself (Forms/Components/OtpInput.php) — the public fluent API is small and is the fastest way to discover the exact method names for your installed tag, since the README occasionally lags behind.

Implementation Patterns

Two-step login / 2FA challenge. Keep the password step and the OTP step as separate Livewire components or separate steps in a wizard, so the OTP field mounts fresh (and auto-focuses) after the challenge is issued. Store the pending user id and expiry in the session, not in the form state.

Pair with Filament's wizard or Action modal. For "verify phone number" inside a resource page, use a Action with a form schema containing the OTP field plus a resend link rendered via ->extraAttributes() or a placeholder. This keeps verification logic scoped to the record being edited.

Validation lives on the field. Align your rules with the rendered length:

OtpInput::make('code')
    ->length(6)
    ->rules(['required', 'digits:6'])
    ->validationMessages(['digits' => 'Enter the 6-digit code.']);

->required() alone does not enforce an exact digit count — always add digits:N or size:N.

Auto-submit. If the component supports auto-advance/auto-submit, wire the final box to call the form's submit action rather than duplicating button logic. Guard against double submission with a $this->otpSubmitting flag or by disabling the submit button while the verify call is in flight.

Resend cooldown. Model resend as a rate-limited action (RateLimiter::attempt keyed on user id + purpose) with a countdown in the UI. The OTP field is presentation only; expiry and attempt-count enforcement belong in your service class.

Testing. In Pest/PHPUnit Livewire tests, set the field as a plain string — ->fillForm(['code' => '123456'])->call('submit') — because the segmented UI is a client-side representation of a single string state. Assert both the success path and an expired-code path.

Gotchas and Tips

  • Upgrade hygiene. Run php artisan filament:assets and clear view:clear / config:clear after moving to 4.2.0. Stale published JS against a new field class is the most common "it renders but doesn't advance" report.
  • State shape. The field's dehydrated value is a string, not an array of digits. Don't type-hint it as array in your ->action() closures or form callbacks.
  • Numeric vs string typing. Values captured from the browser can arrive as strings; coerce with (string) before comparing against a stored code hash, and avoid loose == against ints.
  • Focus and re-render. Livewire updates that re-render the surrounding form can drop focus mid-entry. Prefer submitting from the final box or a dedicated button rather than binding wire:model.live on every keystroke.
  • Multiple OTP fields on one page. Autofocus on mount is convenient but hostile when two instances exist (e.g. modal + page form). Disable focus-on-load on all but the intended one.
  • Clipboard paste. Pasting a code from an SMS is the primary UX; verify it works in your build, and check masked mode doesn't defeat paste or screen readers. If masking is enabled, confirm the field still exposes a proper label/aria description, since segmented inputs frequently break assistive tech.
  • Validation message mismatch. Because the visual boxes and the underlying input can diverge, a generic "invalid" message confuses users. Surface a code-specific message and reset the field on failure so the user isn't editing a half-filled stale value.
  • Extension points. The field is a Filament Field, so ->extraInputAttributes(), ->extraAttributes(), ->helperText(), ->hint(), ->disabled(), and ->live() compose as expected. Reach for these before subclassing.
  • Version sensitivity. 4.2.0's changelog is a compare link only — if you depend on a specific fluent method, confirm it exists in the installed tag via composer show eg-mohamed/filament-otp-input and a quick read of the class. Pin the minor version in composer.json until you've eyeballed the diff.
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.
robertmarney/lara-hierarchial-collections
simonschaufi/rule-doc-generator
emissaoja/emissaoja
blackbricksoftware/gravityforms-civicrm-form-processor
al-rahabi/fancy-crud
jinas/dhivatar-component
mltstephane/laravel-quality
bernskiold/laravel-talentlms
bernskioldmedia/laravel-form-architect
youbar/easy-crud
c-point-labs/laravel-hostyourai
dbravoan/dbcms-admin-theme-dbcms
dbravoan/dbcms-theme-db-cyber
dbravoan/dbcms-blocks-basic
dbravoan/dbcms-module-content-audit
dbravoan/dbcms-module-ai-assistant
paygate-to/paygate-php
padosoft/askmydocs-connector-base
defstudio/supercharged-carbon
bernskioldmedia/laravel-matomo