No description
  • PHP 80.6%
  • Blade 19.1%
  • CSS 0.3%
Find a file
Troy Siedsma 54fc2674b8 Security M: never persist query strings or secret path tokens
Tracker stored request()->fullUrl() into the plaintext visits table,
capturing signed-URL signatures, reset/verify tokens and PII from the
query string. Drop the query string wholesale (store request()->url())
and add a configurable redact_url_patterns pass so magic-link tokens
that live in the path itself can be redacted. Default is empty (full
path kept) for generic installs.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-06-28 16:47:02 +00:00
assets Re-platform onto LithiumHosting/laravel-visitor-tracker Forgejo origin 2026-05-22 13:14:19 +00:00
src Security M: never persist query strings or secret path tokens 2026-06-28 16:47:02 +00:00
tests Re-platform onto LithiumHosting/laravel-visitor-tracker Forgejo origin 2026-05-22 13:14:19 +00:00
.gitattributes Re-platform onto LithiumHosting/laravel-visitor-tracker Forgejo origin 2026-05-22 13:14:19 +00:00
.gitignore Re-platform onto LithiumHosting/laravel-visitor-tracker Forgejo origin 2026-05-22 13:14:19 +00:00
composer.json Modernize for Laravel 11/12 2026-05-22 16:08:27 +00:00
LICENSE.md Standardize composer.json + README + LICENSE 2026-05-22 15:03:53 +00:00
README.md Modernize for Laravel 11/12 2026-05-22 16:08:27 +00:00

Laravel Visitor Tracker and Statistics

Track your authenticated and unauthenticated visitors, login attempts, ajax requests, and more. Includes a controller and a bunch of routes and views to display the statistics, as well as a helper class to fetch the statistics easily (in case you want to display the statistics yourself).

Installation - Basic

  1. Install the package using composer:
composer require lithiumhosting/laravel-visitor-tracker
  1. Run the migration to install the package's table to record visits to by executing:
php artisan migrate
  1. Register the middleware in bootstrap/app.php (Laravel 11/12):
use LithiumHosting\LaravelVisitorTracker\Middleware\RecordVisits;

->withMiddleware(function (Middleware $middleware) {
    $middleware->appendToGroup('web', [
        RecordVisits::class,
    ]);
})

The service provider and VisitStats facade alias auto-register.

  1. Publish the config file, assets, and views by running:
php artisan vendor:publish --provider="LithiumHosting\LaravelVisitorTracker\VisitorTrackerServiceProvider"

Installation - Geoapi

The tracker uses external API to fetch the geolocation data. To turn geoapi off set the geoip_on setting in the config file to false. To change a provider change the geoip_driver field. The supported drivers are listed in the configuration file. You might need to fill out additional API keys depending on the driver you choose.

Since fetching data from an external API takes time, the operation is queued an performed asynchronously. This is done using Laravel Jobs and probably won't work on a shared hosting. There are multiple drivers supported. We'll describe how to set up the database driver.

First, in your .env file you need to set:

QUEUE_DRIVER=database

Then run these commands one after another:

php artisan queue:table
php artisan queue:failed-table
php artisan migrate

Finally, you need to start the worker that will take care of the queue. Run the following command and keep it running:

php artisan queue:work

Read more on Queues and Jobs in the Laravel queues documentation. Use Horizon (Redis) or Supervisor to keep workers running in production.

Restart workers after editing the package's config file so they pick up changes.

Configuration

Check out the config/visitortracker.php file. It is well commented and additional explanations are not required. You can exclude certain user groups, individual users, and certain requests from being tracked there among other things.

Testing

The external API calls to retrieve geolocation information are disabled in the testing environment. Otherwise your tests would run really slow, since the tracker tracks all the requests.

Displaying Statistics

The package comes with a controller and a bunch of routes and views to display statistics. You can fetch and display the stats yourself using the VisitStats class, but we'll talk about it later. The provided views are uncomplicated and styled with the standard Bootstrap classes.

To install the in-built routes add this line to your routes.php file:

VisitStats::routes();

You can put this line inside a group to restrict the access with middlewares and/or to add a prefix to the routes. For example, like this:

Route::middleware('auth')->prefix('admin')->group(function () {
    VisitStats::routes();
});

You can integrate the views into your existing layouts. Take a look at the Views section of the config file. All the routes are named so you could easily add and style links to all the pages. Below is the complete list of routes.

Route name Description
visitortracker.summary A small summary page
visitortracker.all_requests A list of all the requests
visitortracker.visits A list of page visits (same as all request minus ajax calls, bot visits, and login attempts)
visitortracker.ajax_requests A list of AJAX requests
visitortracker.bots A list of visits from bots/crawlers
visitortracker.login_attempts A list of login attempts (check the "Tracking login attempts" section of the config file)
visitortracker.countries A list of countries with the number of visits and unique visitors in each ordered by the date of last visit
visitortracker.os A list of operating systems with the number of visits and unique visitors from each ordered by the date of last visit
visitortracker.browsers A list of browsers with the number of visits and unique visitors from each ordered by the date of last visit
visitortracker.languages A list of browser languages with the number of visits and unique visitors in each ordered by the date of last visit
visitortracker.unique A list of unique visitors (unique IPs) ordered by the date of last visit
visitortracker.users A list of registered users with the total number of visits ordered by the date of last visit
visitortracker.urls A list of URLs with the total number of visits and unique visitors ordered by the date of last visit

What Information is Being Collected

This is the data that is being collected by the tracker.

Database field Description
user_id An id of an authenticated user performing the request
ip e.g. '127.0.0.1'
method e.g. 'GET'
is_ajax Whether the request is an AJAX request
url e.g. 'http://voerro.com'
referer e.g. 'http://google.com'
user_agent e.g. 'Mozilla/5.0 (X11; Ubuntu; Linux x86_64; rv:58.0) Gecko/20100101 Firefox/58.0'
is_desktop Whether the request is made from a desktop
is_mobile Whether the request is made from a mobile device
is_bot Whether the visitor is a bot/crawler
bot e.g. 'Googlebot'
os_family e.g. 'linux'
os e.g. 'Ubuntu'
browser_family e.g. 'firefox'
browser e.g. 'Firefox 58.0'
is_login_attempt Whether the request is a login attempt
country e.g. 'Russia'
country_code e.g. 'RU'
city e.g. 'Moscow'
lat Latitude
long Longitude
browser_language_family e.g. 'en'
browser_language e.g. 'en-US'
created_at A standard Laravel field which is also used as a visit/request datetime

The package uses matomo/device-detector to parse the user agent.

Manually Fetching and Displaying Statistics

In case you are not content with the provided views, you can use the LithiumHosting\LaravelVisitorTracker\Facades\VisitStats class to fetch the statistics data and then make your own controller and views to display this data.

Take a look at the controller located at src/Controllers/StatisticsController.php to understand how to work with the class, it's pretty simple. The original class is located at src/VisitStats.php and all the methods inside are documented, in case you need more insights.

License

This package, laravel-visitor-tracker is licensed under The MIT License (MIT). Please see License File for more information.

Is it any good?

Yes.

When people first hear about a new product, they frequently ask if it is any good. A Hacker News user remarked:

Note to self: Starting immediately, all raganwald projects will have a "Is it any good?" section in the readme, and the answer shall be "yes.".