Minimal steps:
composer require ymigval/laravel-model-cache
HasCachedQueries trait to your Eloquent model:
use YMigVal\LaravelModelCache\HasCachedQueries;
class Post extends Model
{
use HasCachedQueries;
}
php artisan vendor:publish --provider="YMigVal\LaravelModelCache\ModelCacheServiceProvider" --tag="config"
First use case: Cache a simple query in a controller:
// Automatically cached for 60 minutes (config default)
$posts = Post::where('published', true)->get();
1. Basic Query Caching
// Implicit caching (default behavior)
$posts = Post::where('status', 'active')->get();
// Explicit caching (more readable)
$posts = Post::where('status', 'active')->getFromCache();
2. Model-Specific Configuration
class Post extends Model
{
use HasCachedQueries;
// Override default cache duration (2 hours)
protected $cacheMinutes = 120;
// Custom cache prefix
protected $cachePrefix = 'posts_';
}
3. Dynamic Cache Duration
$cacheMinutes = $user->isAdmin() ? 5 : 60;
$posts = Post::where('status', 'active')->remember($cacheMinutes)->get();
4. Conditional Caching
$posts = Post::when($forceFresh, function($query) {
return $query->withoutCache();
})->get();
5. Relationship Caching
// Cache posts with fresh comments
$posts = Post::with(['comments' => function($query) {
$query->withoutCache();
}])->remember(30)->get();
6. Cache Invalidation Workflow
// In controller after update
$post->save(); // Automatically invalidates cache
// OR manually
Post::flushModelCache();
7. Command-Line Cache Management
# Clear cache for specific model
php artisan mcache:flush "App\Models\Post"
# Clear all model caches
php artisan mcache:flush
8. Scope Integration
// In model
public function scopePopular($query)
{
return $query->where('views', '>', 1000)
->remember(60); // Cache popular posts for 1 hour
}
// In controller
$posts = Post::popular()->get(); // Automatically cached
Pitfalls:
config('model-cache.cache_key_prefix') to identify themDebugging Tips:
$key = Post::where('id', 1)->get()->getCacheKey();
Cache::tags(['model_cache'])->get('model_cache:App\Models\Post:select * from posts where id = 1');
withoutCache() to bypass cache for testing:
Post::withoutCache()->get();
Configuration Quirks:
enabled: false in config to disable globallycache_store to specify a dedicated cache driver for modelscache_duration per-model or globallyExtension Points:
getCacheKey() in your modelflushCache() for model-specific logicmodelCache:cleared events for side effectsgetCacheQuery()Performance Optimization:
Cache::stats(); // For Redis/Memcached
Common Pitfalls and Solutions:
| Issue | Solution |
|---|---|
| Cache not updating after model save | Ensure model events are firing; check observables array in model |
| Entire cache cleared unexpectedly | Verify cache driver supports tags; check for manual Cache::flush() calls |
| Complex queries not caching | Simplify query or use explicit cache keys |
| Memory issues with large caches | Implement pagination or shorter cache durations |
| Race conditions with cache invalidation | Use Cache::lock() for critical operations |
How can I help you explore Laravel packages today?