elipzis/laravel-cacheable-model
## Getting Started
### Minimal Setup
1. **Installation** (Laravel 10+ and PHP 8.5+):
```bash
composer require elipzis/laravel-cacheable-model
php artisan vendor:publish --provider="ElipZis\Cacheable\CacheableServiceProvider"
Publish the config file to customize defaults (e.g., cache driver, TTL, or Laravel 13 compatibility settings).
Enable Caching:
Add the Cacheable trait to your Eloquent model:
use ElipZis\Cacheable\Models\Traits\Cacheable;
class Post extends Model
{
use Cacheable;
}
First Use Case: Immediately cache queries like this:
// Automatically cached for 10 minutes (configurable)
$posts = Post::where('published', true)->get();
The package now handles edge cases like whereNull() safely (fixed in v0.6.0).
config/cacheable.php – Adjust TTL, cache driver, and query hashing strategy. Check for Laravel 13-specific optimizations.ElipZis\Cacheable\Models\Traits\Cacheable – Understand how caching is triggered, including new PHP 8.5 type safety.storage/logs/laravel.log (debug level) to verify keys. Enable debug mode with:
Cacheable::setDebug(true);
Automatic Caching (with edge-case fixes):
// All `get()`, `first()`, `find()`, etc., are cached automatically.
$user = User::find(1); // Cached under `user:1`
$posts = Post::whereNull('deleted_at')->get(); // Now handles `whereNull` safely
Customizing Cache Keys:
Override the getCacheKey() method in your model:
public function getCacheKey()
{
return "custom_prefix:{$this->id}";
}
TTL Management: Set per-model TTL in the config or dynamically:
Post::setCacheTTL(3600); // Override for 1 hour
Cache Invalidation: The package auto-flushes cache on:
create(), update(), delete().Cacheable::flushCache() manually if needed:
Post::flushCache(); // Clears all Post cache entries
Laravel 13+ Compatibility:
Cacheable::supportsLaravel13() to check compatibility in custom logic.Cache Drivers:
Supports Redis, Memcached, database, and file caching. Configure in .env:
CACHE_DRIVER=redis
Query Complexity:
Avoid caching overly complex queries (e.g., OR conditions). Use Cacheable::disableCache() for one-off queries:
Post::disableCache()->whereRaw('...')->get();
Testing: Mock the cache in tests:
$this->partialMock(Cache::class, ['get', 'put', 'forget']);
Laravel Events: Extend cache logic via events:
Cacheable::addListener('beforeCache', function ($model, $query) {
// Custom logic before caching
});
Key Collisions:
class:query_hash. Complex queries (e.g., OR conditions) may produce identical hashes.getCacheKey() or use Cacheable::setQueryHashStrategy('md5').Cache Stampede:
Cacheable::lockCache() for critical queries.Model Events:
saved, deleted). Custom events may not trigger flushes.flushCache() or bind to Cacheable::flushed event.Debugging:
'debug' => env('CACHEABLE_DEBUG', false),
PHP 8.5+ Type Safety:
declare(strict_types=1) in your models.whereNull() Edge Case:
whereNull() could trigger undefined array key errors. This is now fixed in v0.6.0.Log Cache Keys:
Cacheable::setDebug(true);
Outputs keys to storage/logs/laravel.log (debug level).
Clear Cache:
php artisan cache:clear
Or manually:
Cache::forget(Cacheable::getCacheKey($model));
Verify Cache:
Cache::has(Cacheable::getCacheKey($model)); // Check existence
Cache::get(Cacheable::getCacheKey($model)); // Inspect cached data
Custom Cache Stores:
Bind a custom cache store to the Cacheable service provider:
CacheableServiceProvider::extend('custom', function () {
return Cache::store('custom_driver');
});
Query Hashing: Override the hashing strategy:
Cacheable::setQueryHashStrategy('sha256');
Cache Tags: Use Laravel’s cache tags for bulk invalidation:
Cacheable::tag(['posts', 'published']);
Post::flushCache(); // Clears tags 'posts' and 'published'
Conditional Caching: Disable caching for specific queries:
Post::disableCache()->where('draft', true)->get();
Laravel 13+ Features:
Cacheable::listenForModelEvents() to hook into Laravel 13’s event system.
NO_UPDATE_NEEDED was not applicable due to meaningful updates.
How can I help you explore Laravel packages today?