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 Matomo Laravel Package

marcogermani87/filament-matomo

Integrates Matomo analytics with Filament, adding dashboard widgets to display website traffic, visits, and other key metrics inside your admin panel. Configure your Matomo URL and API credentials to get started.

View on GitHub
Deep Wiki
Context7

Getting Started

marcogermani87/filament-matomo is a Filament plugin that surfaces Matomo Analytics inside your admin panel — typically as dashboard widgets (visits, pageviews, referrers) and/or an embedded Matomo reporting view. v1.1.0 is primarily a compatibility release (Laravel 12.x support), so the install flow is unchanged from v1.0.0.

First steps:

  1. composer require marcogermani87/filament-matomo
  2. Publish the config: php artisan vendor:publish --tag="filament-matomo-config"
  3. Put your Matomo credentials in .env — at minimum the Matomo base URL and a site ID; an API token if you want API-driven widgets rather than an embedded iframe:
    MATOMO_URL=https://analytics.example.com
    MATOMO_SITE_ID=1
    MATOMO_TOKEN=your_api_token
    
  4. Register the plugin on your Filament panel in app/Providers/Filament/AdminPanelProvider.php:
    ->plugin(\Marcogermani87\FilamentMatomo\FilamentMatomoPlugin::make())
    
  5. php artisan config:clear (or config:cache in prod) and load the panel.

First use case to validate: add the plugin, open the dashboard, and confirm one widget renders real numbers for your configured site. If it renders, your URL/token/site ID wiring is correct and everything else is layout/policy tuning. If it doesn't, the problem is almost always auth or URL — not Filament.

Where to look first: the published config file (it's the whole surface area of the package) and the plugin's make() / widget registration methods. Everything you'll customize day-to-day lives in those two places.

Implementation Patterns

Panel-scoped registration. Register the plugin only on the panel that should see analytics (usually AdminPanelProvider), not globally. If you have separate Admin and Tenant panels, this keeps analytics out of tenant-facing UIs by default.

Config-as-source-of-truth, env-as-override. Keep non-secret defaults (default date range, number of top rows, which widgets are enabled) in config/filament-matomo.php and reserve .env for MATOMO_URL, MATOMO_SITE_ID, and MATOMO_TOKEN. This makes it easy to commit sane defaults while keeping secrets out of the repo.

Dashboard widget composition. Treat the Matomo widgets like any other Filament widget — control column span and sort order via the panel's ->widgets([...]) ordering and protected int|string|array $columnSpan. A common layout is: one "Visits (last 30 days)" stat/widget wide at the top, then a two-column split of pageviews and referrers below.

Authorization via Filament policies, not the plugin. Don't rely on hiding widgets to secure analytics data. Wrap access in canView() on a custom widget subclass, or gate the whole panel with ->authGuard() / role checks. The Matomo token can read all sites it has access to — treat the panel as privileged.

Custom widget subclassing for filters. The most common day-to-day customization is a date-range or segment filter (e.g., "last 7 days", "mobile only"). Subclass the package widget, override the query/parameter builder, and expose a Filament Select filter in getTableFilters() or via a form in a custom page. This avoids forking the package.

Testing. Mock the Matomo HTTP client in your feature tests so the dashboard tests don't hit a live instance. Assert the widget renders (200) and that canView() behaves per role — not the actual numbers.

CI/Laravel 12. v1.1.0 is the release to pin if you're on Laravel 12. If your Composer constraints include laravel/framework: ^12.0, require ^1.1 explicitly; ^1.0 may resolve to a version that hasn't been tested against L12.

Gotchas and Tips

Config caching bites hardest here. After changing MATOMO_URL or the token, php artisan config:clear before debugging — a stale cached config is the #1 cause of "widgets are empty after I fixed the env." In production, always config:cache on deploy.

Token exposure. The Matomo API token is a powerful secret: it grants read (and sometimes write, depending on scope) across all sites the user can access. Never commit it, never log it, and strip it from any exception handler that dumps config. Prefer a dedicated Matomo user with read-only access for the site(s) you display.

URL, not just host. MATOMO_URL typically needs the full base including scheme and, if Matomo lives on a subpath, that subpath (e.g. https://analytics.example.com/matomo). Trailing-slash inconsistencies are a frequent source of 404s from the API client.

Iframe-based widgets and CSP. If you use the embedded-report style rather than API widgets, the iframe is subject to your app's Content-Security-Policy (frame-src) and to Matomo's own X-Frame-Options. Self-hosted Matomo often needs its config.ini.php adjusted to allow framing from your admin domain. API-driven widgets sidestep this entirely — prefer them if CSP is strict.

Timezone and date-range drift. Matomo reports in the site's configured timezone, which may differ from config('app.timezone'). "Today" widgets can look wrong near midnight. Align the Matomo site timezone with your app, or make the widget's date range explicit rather than relying on implicit "today."

Site ID is per-site. Multi-site Matomo installs need the correct numeric MATOMO_SITE_ID; passing a site name silently returns empty data. If you support multiple sites, drive the site ID from tenant settings rather than a single env value, and be careful that the token can read all of them.

Extension points preferred over forks. The plugin's make() and widget classes are the intended extension surface — subclass widgets, override canView(), and inject filters rather than editing vendor files. Forking means you own the L12-compat maintenance that v1.1.0 just delivered.

Empty-but-not-error results. Matomo frequently returns a well-formed empty response (no visits in range, no token permission for that site) rather than an error. If a widget shows zeros, check the API response body and the token's site permissions before assuming the integration is broken.

Version pinning for CI. Dependabot bumps in v1.1.0 are CI-only and safe, but pin ^1.1 in composer.json so a future major doesn't surprise you mid-sprint; watch this package's releases — it's small and single-maintainer, so L13 compatibility may lag.

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.
shitoudev/permissionmanager
johannesclimacus/laravel-tui
hocvt/seotools
vitalybaev/sypexgeo
amphibee/themosis-ignition
gito-me/fast-excel
frankyso/laravel-ipaymu
geolize-studio/laravel-chile
boomerangui/chat
jinas/dhivatar
store-doc/laravel-storage-driver
plus-it/laravel-translation-manager
diephp/perhaps
diephp/telegraph
osmaviation/spreadsheet
microsoft/fluentui-system-icons
mmccook/php-json-canonicalization-scheme
middlewares/firewall
qubiqx/montapacking
nyoncode/laravel-package-console