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

Filter Card Laravel Package

awesome-nova/filter-card

A Laravel Nova card that adds configurable filter controls to resource index screens, letting users narrow listings by date ranges, selections, and custom criteria. Lightweight, easy to register, and designed to drop into existing Nova dashboards with minimal setup.

View on GitHub
Deep Wiki
Context7

Getting Started

Step 0 — read composer.json before you run composer require. The last release is 2019-02-10, so the laravel/nova and php constraints will almost certainly refuse to resolve on Nova 4/5 (Vue 3 + Vite). That one file tells you whether this is a ten-minute install or a fork. If you're on a modern Nova, stop here and read the source as a reference implementation instead.

Step 1 — read the source. The whole package is roughly three files: a Card subclass, a service provider that registers the card and publishes assets, and a Vue component. Fifteen minutes of reading gives you the complete surface area, and tells you whether the filter definitions it exposes actually match the workflow you want. Do this before installing; reading is cheaper than fighting Composer.

Step 2 — install and register (Nova 1.x/2.x only):

composer require awesome-nova/filter-card
php artisan vendor:publish --tag=filter-card-assets   # or nova:publish

Then register it in app/Providers/NovaServiceProvider.php:

public function cards()
{
    return [
        new \AwesomeNova\FilterCard\FilterCard(),
        // ...metrics
    ];
}

Step 3 — verify the card mounts with no console errors before wiring any real filters. Load the dashboard, open the network tab, confirm the card's JS bundle is not 404ing, confirm Vue has mounted it. Only then add filter definitions. Most "it doesn't work" reports at this stage are asset-publishing problems, not code problems.

First real use case: put the card on the main Nova dashboard so ops/support can see and change the active filter set (region, status, date range) without opening a resource index and digging through the native dropdown. Pair it with a ValueMetric/PartitionMetric reading the same query string — the card is the control, the metric is the output. That's the entire value proposition on one screen, and the fastest way to decide whether the UX is worth keeping.

Implementation Patterns

Dashboard card + query-string metrics (the core pattern). The card owns filter state and reflects it; metrics read it. Couple them through the URL query string — Nova already round-trips filters through the query string, and users expect Back/Forward and bookmarkable dashboards to work.

// NovaServiceProvider::cards()
return [
    (new FilterCard())->withFilters([
        'region' => ['all', 'emea', 'apac', 'amer'],
        'status' => ['open', 'closed'],
    ]),
    new OpenTicketsByRegion, // reads request()->query('region')
];

Resource index as a summary banner. Register the card above the resource list (or via a resource's cards() method) to give users a persistent readout of which filters are currently applied. This is the "lift it out of the dropdown" pattern and the one most likely to survive a rewrite, because it's pure display with no backend coupling.

Fork-and-vendor as a first-party component. If a spike passes, don't keep the Packagist dependency. Copy the source into nova-components/filter-card/, add a Composer path repository (plus a replace entry for laravel/nova if needed), and register it as a locally built card. This is the sustainable pattern for Nova cards generally — they bind to Nova's private frontend API, so every major Nova upgrade is a migration you own either way. Vendoring just makes that ownership explicit.

Reimplementation against modern Nova. A card is roughly: a Card subclass with a component() name, a Vue SFC registered in resources/js/card.js via Nova.booting, and a provider that publishes the compiled bundle. The filter behaviour you're copying is simply reading this.$route.query on mount, emitting $router.replace({ query }) when a control changes, and re-rendering. Budget a day or two, not a sprint.

Persisting filter state per user. The package has no persistence — it rides on Nova's query string. If you need "my saved view," capture the query string into a user_settings-style table keyed by user_id + dashboard, and hydrate the card from that record on boot. Do this in your own card, not by patching the package.

Use it as a Nova filter-state study. Even if you never install it, the Vue component is a compact example of how Nova-era filters read and write route state — exactly the fiddly part of building any custom filter surface. Read it once before you write your own.

Gotchas and Tips

Composer resolution is the first wall, not the last. The laravel/nova constraint will typically refuse to resolve on a current install. --ignore-platform-reqs "works" and is a trap: it defers the failure to every fresh clone, every new hire, and CI. If you must proceed, use a path repository plus a replace entry and document why in the repo — otherwise the next engineer deletes it and everything breaks.

Asset compilation is the second wall. The package assumes Laravel Mix; a modern Nova app builds with Vite. Published assets land in public/vendor/... and are served as-is, so a stale published bundle silently shadows source changes. After any edit: rebuild, re-publish, php artisan view:clear, hard-refresh. Check the network tab for a 404 on the card's JS before debugging Vue.

Never patch inside vendor/. The PHP card is thin by design; the real logic is the Vue component. Publish the assets, edit the published copy, and move the whole thing to nova-components/ the moment you need a second change. Anything else vanishes on the next composer update.

Silent mount failure after a Nova upgrade is the expected failure mode. Nova's card API is effectively internal and shifts across majors. The card simply stops appearing — no PHP error, no exception, just a gap users quietly work around. Add a one-line smoke check to your upgrade runbook: load the dashboard, confirm the card renders, confirm changing a filter updates a metric.

Filter state must come from the route, not props. If the card caches filter values in component data on mount and never re-reads $route.query, the UI desyncs on Back/Forward and on any link that pre-applies filters. Treat the query string as the single source of truth in any custom build.

Watch for query-parameter collisions. Two cards, or a card plus a resource filter, both writing ?status= will fight. Namespace the card's parameters (?fc_region=...) if it coexists with anything else on the dashboard.

Verify the licence before you copy a line. A repo with no LICENSE file is all-rights-reserved by default, which blocks internal redistribution and forking. Check this during discovery, not after you've vendored it.

Treat the dependency graph as untrusted. 2019-era package.json pins are almost certainly flagged by npm audit with no upstream fix path. Run the audit in the sandbox; if you fork, plan to bump the JS toolchain as part of the fork rather than inheriting it.

Debugging checklist, in order: card not rendering → the component name registered in Nova.booting must match the name returned by the PHP component() method; card rendering but empty → check withMeta()/config payload reaches the component via the card prop; card rendering but filters inert → check the router emit and that your metrics read the same param names.

Scope it to internal admin surfaces only. Zero dependents, no releases in six years, no maintainer, no tests, no CI. It's a design reference that happens to be installable — not a dependency to put in front of customers, and not something to add to a build/buy matrix as a live candidate.

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.
socialdept/tenant-domains
tautvydasr/blade-class-names
socialdept/color-scales
maherelgamil/controller
coleus/widgets
coleus/table
coleus/users
coleus/music
coleus/health
coleus/calendar
coleus/notes
coleus/support
coleus/settings
coleus/apps
seampact/laravel
emmyconceptng/laravel-ng-postcode
jjsquady/round-robin
skyraptor/chatter
edlugz/sasapay
abbasudo/artisan-route