PHPackages                             turahe/laravel-counters - PHPackages - PHPackages  [Skip to content](#main-content)[PHPackages](/)[Directory](/)[Categories](/categories)[Trending](/trending)[Leaderboard](/leaderboard)[Changelog](/changelog)[Analyze](/analyze)[Collections](/collections)[Log in](/login)[Sign up](/register)

1. [Directory](/)
2. /
3. turahe/laravel-counters

ActiveLibrary

turahe/laravel-counters
=======================

management for counters in laravel system

v2.0.0(9mo ago)2449[1 PRs](https://github.com/turahe/laravel-counters/pulls)MITPHPPHP ^8.4CI passing

Since Mar 14Pushed 5mo ago1 watchersCompare

[ Source](https://github.com/turahe/laravel-counters)[ Packagist](https://packagist.org/packages/turahe/laravel-counters)[ Docs](https://github.com/turahe/laravel-counters)[ RSS](/packages/turahe-laravel-counters/feed)WikiDiscussions master Synced 1mo ago

READMEChangelog (2)Dependencies (6)Versions (9)Used By (0)

Laravel Counters
================

[](#laravel-counters)

A modern, optimized counter management package for Laravel 11/12 with PHP 8.4 support.

A flexible and powerful counter management system for Laravel applications. Easily track and manage various types of counters like page views, downloads, user actions, and more without cluttering your database schema.

🚀 Features
----------

[](#-features)

- ✅ **PHP 8.4 Optimized**: Uses readonly properties, constructor property promotion, match expressions, and improved type declarations
- ✅ **Laravel 11/12 Compatible**: Modern service provider patterns and dependency injection
- ✅ **High Performance**: Built-in caching, bulk operations, and optimized database queries
- ✅ **Type Safe**: Full type declarations and strict typing throughout
- ✅ **Modern Patterns**: Uses modern PHP and Laravel patterns and best practices
- ✅ **Comprehensive Testing**: Full test coverage with modern testing practices
- **Model-specific counters**: Associate counters with any Eloquent model
- **Global counters**: System-wide counters for general statistics
- **Cookie-based tracking**: Prevent duplicate increments from the same user
- **Flexible configuration**: Customizable table names and settings
- **Artisan commands**: Create counters via command line
- **Laravel 10-12 support**: Compatible with modern Laravel versions
- **PHP 8.2+ support**: Built for modern PHP applications

📋 Table of Contents
-------------------

[](#-table-of-contents)

- [Installation](#installation)
- [Quick Start](#quick-start)
- [Usage](#usage)
    - [Model Counters](#model-counters)
    - [Global Counters](#global-counters)
    - [Cookie-based Tracking](#cookie-based-tracking)
- [API Reference](#api-reference)
- [Configuration](#configuration)
- [Testing](#testing)
- [Contributing](#contributing)

Installation
------------

[](#installation)

### Requirements

[](#requirements)

- **PHP**: 8.4 or higher
- **Laravel**: 11.x or 12.x

### Step-by-Step Installation

[](#step-by-step-installation)

1. **Install the package via Composer:**

```
composer require turahe/laravel-counters
```

2. **Publish the configuration and migrations:**

```
php artisan vendor:publish --tag=counters-config
```

This will publish:

- Configuration file: `config/counter.php`
- Migration file: `database/migrations/xxxx_xx_xx_xxxxxx_create_counters_tables.php`

3. **Run the migrations:**

```
php artisan migrate
```

This creates the `counters` and `counterables` tables in your database.

Quick Start
-----------

[](#quick-start)

### 1. Create a Counter

[](#1-create-a-counter)

```
use Turahe\Counters\Models\Counter;

// Create a counter for page views
Counter::create([
    'key' => 'page_views',
    'name' => 'Page Views',
    'initial_value' => 0,
    'step' => 1
]);
```

### 2. Use with Models

[](#2-use-with-models)

```
use Turahe\Counters\Traits\HasCounter;

class Post extends Model
{
    use HasCounter;

    // Your model code...
}
```

### 3. Track Views

[](#3-track-views)

```
// In your controller
public function show(Post $post)
{
    $post->incrementCounter('page_views');

    return view('posts.show', compact('post'));
}
```

### 4. Global Counters

[](#4-global-counters)

```
use Turahe\Counters\Facades\Counters;

// Track total downloads
Counters::increment('total_downloads');
```

Usage
-----

[](#usage)

### Model Counters

[](#model-counters)

Add the `HasCounter` trait to any model you want to track:

```
use Turahe\Counters\Traits\HasCounter;

class Post extends Model
{
    use HasCounter;

    // Your model code...
}
```

#### Available Methods

[](#available-methods)

```
// Add a counter to a model
$post->addCounter('views');

// Get counter value
$views = $post->getCounterValue('views');

// Increment counter
$post->incrementCounter('views');

// Decrement counter
$post->decrementCounter('views', 2); // Decrement by 2

// Reset counter to initial value
$post->resetCounter('views');

// Remove counter from model
$post->removeCounter('views');

// Check if model has counter
if ($post->hasCounter('views')) {
    // Do something
}
```

### Global Counters

[](#global-counters)

Use the `Counters` facade for system-wide counters:

```
use Turahe\Counters\Facades\Counters;

// Create a counter
Counters::create('total_downloads', 'Total Downloads', 0, 1);

// Get counter value
$downloads = Counters::getValue('total_downloads');

// Increment counter
Counters::increment('total_downloads');

// Decrement counter
Counters::decrement('total_downloads', 2);

// Set specific value
Counters::setValue('total_downloads', 100);

// Reset to initial value
Counters::reset('total_downloads');
```

### Cookie-based Tracking

[](#cookie-based-tracking)

Prevent duplicate increments from the same user:

```
// Only increment if user doesn't have cookie
Counters::incrementIfNotHasCookies('daily_visitors');
Counters::decrementIfNotHasCookies('available_slots');
```

API Reference
-------------

[](#api-reference)

### Model Methods (HasCounter Trait)

[](#model-methods-hascounter-trait)

MethodDescriptionParameters`addCounter($key, $initialValue = null)`Add counter to model`$key`: Counter key, `$initialValue`: Optional initial value`getCounter($key)`Get counter object`$key`: Counter key`getCounterValue($key)`Get counter value`$key`: Counter key`hasCounter($key)`Check if model has counter`$key`: Counter key`incrementCounter($key, $step = null)`Increment counter`$key`: Counter key, `$step`: Optional step value`decrementCounter($key, $step = null)`Decrement counter`$key`: Counter key, `$step`: Optional step value`resetCounter($key, $initialValue = null)`Reset counter`$key`: Counter key, `$initialValue`: Optional reset value`removeCounter($key)`Remove counter from model`$key`: Counter key### Global Counter Methods (Counters Facade)

[](#global-counter-methods-counters-facade)

MethodDescriptionParameters`create($key, $name, $initialValue = 0, $step = 1)`Create a counter`$key`: Counter key, `$name`: Display name, `$initialValue`: Initial value, `$step`: Step value`get($key)`Get counter object`$key`: Counter key`getValue($key, $default = null)`Get counter value`$key`: Counter key, `$default`: Default value if not found`setValue($key, $value)`Set counter value`$key`: Counter key, `$value`: New value`setStep($key, $step)`Set counter step`$key`: Counter key, `$step`: Step value`increment($key, $step = null)`Increment counter`$key`: Counter key, `$step`: Optional step value`decrement($key, $step = null)`Decrement counter`$key`: Counter key, `$step`: Optional step value`reset($key)`Reset counter`$key`: Counter key`incrementIfNotHasCookies($key)`Increment if no cookie`$key`: Counter key`decrementIfNotHasCookies($key)`Decrement if no cookie`$key`: Counter keyConfiguration
-------------

[](#configuration)

The package configuration is located at `config/counter.php`:

```
return [
    'models' => [
        'counter' => Turahe\Counters\Models\Counter::class,
    ],

    'tables' => [
        'table_name' => 'counters',
        'table_pivot_name' => 'counterables',
    ],

    'database_connection' => env('COUNTER_DB_CONNECTION'),
];
```

### Customizing Table Names

[](#customizing-table-names)

You can customize the table names in the configuration:

```
'tables' => [
    'table_name' => 'my_counters',
    'table_pivot_name' => 'my_counterables',
],
```

Artisan Commands
----------------

[](#artisan-commands)

### Create Counter

[](#create-counter)

Create a counter via command line:

```
php artisan make:counter page_views "Page Views" 0 1
```

Parameters:

- `page_views`: Counter key
- `"Page Views"`: Display name
- `0`: Initial value
- `1`: Step value

Testing
-------

[](#testing)

The package includes comprehensive tests. Run them with:

```
./vendor/bin/phpunit
```

### Test Coverage

[](#test-coverage)

- ✅ Model counter operations
- ✅ Global counter operations
- ✅ Cookie-based tracking
- ✅ Exception handling
- ✅ Database operations
- ✅ Configuration flexibility

Common Usage Patterns
---------------------

[](#common-usage-patterns)

### ✅ Best Practices

[](#-best-practices)

1. **Always create counters before using them:**

```
// Create the counter first
Counter::create([
    'key' => 'page_views',
    'name' => 'Page Views',
    'initial_value' => 0,
    'step' => 1
]);

// Then use it
$post->incrementCounter('page_views');
```

2. **Use meaningful counter keys:**

```
// Good
$post->incrementCounter('article_views');
$user->incrementCounter('login_count');

// Avoid generic names
$post->incrementCounter('count');
```

3. **Handle counter existence gracefully:**

```
if ($post->hasCounter('views')) {
    $post->incrementCounter('views');
} else {
    $post->addCounter('views');
    $post->incrementCounter('views');
}
```

### ❌ Common Mistakes

[](#-common-mistakes)

1. **Don't forget to run migrations:**

```
php artisan migrate
```

2. **Don't use counters without creating them first:**

```
// This might fail if counter doesn't exist
$post->incrementCounter('undefined_counter');

// Better approach
$post->addCounter('new_counter');
$post->incrementCounter('new_counter');
```

Performance Optimizations
-------------------------

[](#performance-optimizations)

### Caching

[](#caching)

The package includes built-in caching for counter lookups, significantly improving performance for frequently accessed counters.

### Bulk Operations

[](#bulk-operations)

Use bulk operations to update multiple counters efficiently:

```
// Bulk increment
$results = Counters::bulkIncrement(['counter1', 'counter2'], 5);

// Bulk decrement
$results = Counters::bulkDecrement(['counter1', 'counter2'], 3);
```

### Database Indexes

[](#database-indexes)

The migration includes optimized indexes for better query performance.

Testing
-------

[](#testing-1)

Run the test suite:

```
composer test
```

PHP 8.4 Features Used
---------------------

[](#php-84-features-used)

- **Readonly Properties**: Immutable data structures
- **Constructor Property Promotion**: Cleaner class definitions
- **Match Expressions**: Modern control flow
- **Named Arguments**: Self-documenting function calls
- **Improved Type Declarations**: Better type safety
- **Strict Types**: Enforced type checking

Laravel 11/12 Features Used
---------------------------

[](#laravel-1112-features-used)

- **Modern Service Providers**: Deferrable providers for better performance
- **Improved Dependency Injection**: Constructor injection and type hints
- **Enhanced Model Features**: Better relationships and scopes
- **Modern Command Structure**: Improved Artisan commands

Example Seeder
--------------

[](#example-seeder)

Example seeder for creating counters:

```
use Illuminate\Database\Seeder;
use Turahe\Counters\Models\Counter;

class CounterSeeder extends Seeder
{
    public function run()
    {
        // Create global counters
        Counter::create([
            'key' => 'total_downloads',
            'name' => 'Total Downloads',
            'initial_value' => 0,
            'step' => 1
        ]);

        Counter::create([
            'key' => 'daily_visitors',
            'name' => 'Daily Visitors',
            'initial_value' => 0,
            'step' => 1
        ]);

        // Create model-specific counters
        Counter::create([
            'key' => 'page_views',
            'name' => 'Page Views',
            'initial_value' => 0,
            'step' => 1
        ]);
    }
}
```

Contributing
------------

[](#contributing)

1. Fork the repository
2. Create your feature branch (`git checkout -b feature/amazing-feature`)
3. Commit your changes (`git commit -m 'Add some amazing feature'`)
4. Push to the branch (`git push origin feature/amazing-feature`)
5. Open a Pull Request

License
-------

[](#license)

This package is open-sourced software licensed under the [MIT license](https://opensource.org/licenses/MIT).

Support
-------

[](#support)

- **Issues**: [GitHub Issues](https://github.com/turahe/laravel-counters/issues)
- **Discussions**: [GitHub Discussions](https://github.com/turahe/laravel-counters/discussions)

---

Made with ❤️ by [Nur Wachid](https://www.wach.id)

###  Health Score

45

—

FairBetter than 92% of packages

Maintenance66

Regular maintenance activity

Popularity15

Limited adoption so far

Community9

Small or concentrated contributor base

Maturity75

Established project with proven stability

 Bus Factor1

Top contributor holds 90% of commits — single point of failure

How is this calculated?**Maintenance (25%)** — Last commit recency, latest release date, and issue-to-star ratio. Uses a 2-year decay window.

**Popularity (30%)** — Total and monthly downloads, GitHub stars, and forks. Logarithmic scaling prevents top-heavy scores.

**Community (15%)** — Contributors, dependents, forks, watchers, and maintainers. Measures real ecosystem engagement.

**Maturity (30%)** — Project age, version count, PHP version support, and release stability.

###  Release Activity

Cadence

Every ~321 days

Recently: every ~347 days

Total

6

Last Release

278d ago

Major Versions

0.0.2 → v1.0.02024-06-26

v1.1.1 → v2.0.02025-08-07

PHP version history (3 changes)0.0.1PHP ^7.3|^8.0

v1.0.0PHP ^8.2

v2.0.0PHP ^8.4

### Community

Maintainers

![](https://www.gravatar.com/avatar/f3513bd6100438bcb8c6b1a7e241a66e1ddaf1c11ee33883e06ef4a2784120db?d=identicon)[turahe](/maintainers/turahe)

---

Top Contributors

[![turahe](https://avatars.githubusercontent.com/u/6832622?v=4)](https://github.com/turahe "turahe (18 commits)")[![cursoragent](https://avatars.githubusercontent.com/u/199161495?v=4)](https://github.com/cursoragent "cursoragent (2 commits)")

---

Tags

countersincrementslaravelpackageslaravelvisitorsincrementcountersDecrementnumber of visitorsturahe

###  Code Quality

TestsPHPUnit

Code StyleLaravel Pint

### Embed Badge

![Health badge](/badges/turahe-laravel-counters/health.svg)

```
[![Health](https://phpackages.com/badges/turahe-laravel-counters/health.svg)](https://phpackages.com/packages/turahe-laravel-counters)
```

###  Alternatives

[barryvdh/laravel-ide-helper

Laravel IDE Helper, generates correct PHPDocs for all Facade classes, to improve auto-completion.

14.9k123.0M687](/packages/barryvdh-laravel-ide-helper)[maher/laravel-counters

management for counters in laravel system

4511.2k](/packages/maher-laravel-counters)[clickbar/laravel-magellan

This package provides functionality for working with the postgis extension in Laravel.

423715.4k1](/packages/clickbar-laravel-magellan)[api-platform/laravel

API Platform support for Laravel

59126.4k6](/packages/api-platform-laravel)

PHPackages © 2026

[Directory](/)[Categories](/categories)[Trending](/trending)[Changelog](/changelog)[Analyze](/analyze)
