Weave Code
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

Cache Contracts Laravel Package

symfony/cache-contracts

Symfony Cache Contracts defines lightweight, PSR-friendly interfaces for cache and tag-aware caching, enabling consistent cache usage across Symfony components and third-party libraries. Use it to type-hint against stable APIs while swapping cache implementations.

View on GitHub
Deep Wiki
Context7

Getting Started

  1. No Installation Needed in Laravel Since Laravel already bundles symfony/cache-contracts via symfony/cache, skip composer require. Focus on Laravel’s built-in Cache facade or dependency-injected interfaces.

  2. First Use Case: Caching a Value

    // Cache a value for 10 minutes
    Cache::put('key', 'value', now()->addMinutes(10));
    
    // Retrieve with fallback
    $value = Cache::remember('key', now()->addMinutes(10), function () {
        return expensiveOperation();
    });
    
  3. Where to Look First

    • Laravel’s Cache Documentation (uses these contracts under the hood).
    • Symfony’s Cache Component for adapter examples.
    • vendor/symfony/cache-contracts for interfaces like CacheItemPoolInterface and TagAwareCacheInterface.

Implementation Patterns

1. Dependency Injection (PSR-6)

Inject Psr\Cache\CacheItemPoolInterface (PSR-6) or Symfony\Contracts\Cache\CacheInterface (Symfony’s PSR-6 subset) into services:

use Psr\Cache\CacheItemPoolInterface;

class MyService {
    public function __construct(private CacheItemPoolInterface $cache) {}

    public function getCachedData(string $key): mixed {
        $item = $this->cache->getItem($key);
        return $item->isHit() ? $item->get() : $this->fetchFreshData($key);
    }
}

2. Tag-Based Invalidation

Use Laravel’s Cache::tags() for grouped invalidation (leverages TagAwareCacheInterface):

// Store with tags
Cache::tags(['products', 'inventory'])->put('product:1', $product, now()->addHour());

// Invalidate all tagged items
Cache::tags(['products'])->flush();

3. Fallback Cache Chain

Combine adapters (e.g., in-memory + Redis) using Cache::extend():

Cache::extend('fallback', function ($app) {
    $store = new CacheManager();
    $store->setDefaultDriver('redis');
    $store->extend('array', function () {
        return new ArrayAdapter(); // Fallback to in-memory
    });
    return $store->driver('redis');
});

4. Deferred Writes

Batch operations with CacheItemPoolInterface:

$pool = Cache::store('array'); // PSR-6 pool
$pool->getItem('key1')->set('value1');
$pool->getItem('key2')->set('value2');
$pool->commit(); // Atomic write

5. Custom Cache Drivers

Extend Laravel’s cache system by implementing CacheItemPoolInterface:

// config/cache.php
'stores' => [
    'custom' => [
        'driver' => 'custom',
        'connection' => 'default',
    ],
],

// app/Providers/AppServiceProvider.php
Cache::extend('custom', function () {
    return new CustomCachePool(); // Your PSR-6 implementation
});

Gotchas and Tips

1. No Concrete Implementation

  • Pitfall: symfony/cache-contracts is only interfaces. Pair it with:
    • Laravel’s built-in drivers (redis, file, database).
    • Symfony’s adapters (FilesystemAdapter, RedisAdapter).
    • PSR-6 libraries like doctrine/cache.

2. Version Alignment

  • Symfony 5+ uses cache-contracts v2.x (PSR-6).
  • Symfony 4.x used v1.x (older contracts).
  • Laravel 8+ requires symfony/cache-contracts:^2.0 for PSR-6 compliance.
  • Fix: Run composer require symfony/cache:^5.0 to auto-pull the correct contracts.

3. Serialization Behavior

  • FilesystemAdapter: Serializes all values (including objects).
  • ArrayAdapter: In-memory only; loses data on request end.
  • RedisAdapter: Uses native serialization (check serializer config).
  • Tip: Use Cache::put('key', serialize($data), ...) for complex objects.

4. Debugging Stale Cache

  • ArrayAdapter: Resets on each request (use only for testing).
  • FilesystemAdapter: Check storage/framework/cache for stale files.
  • Redis: Use Cache::forget() or Cache::flush() to clear.

5. PSR-6 vs PSR-16

  • This package = PSR-6 (CacheItemPoolInterface).
  • PSR-16 (Psr\SimpleCache\CacheInterface) is separate (use symfony/cache's SimpleCacheAdapter).
  • Mistake: Mixing get() (PSR-16) with getItem() (PSR-6) causes errors.

6. Extension Points

  • Decorate adapters: Extend CacheItemPoolDecorator to log/monitor cache hits.
  • Custom tags: Implement TagAwareCacheInterface for advanced invalidation.
  • Example:
    class LoggingCachePool extends CacheItemPoolDecorator {
        public function getItem($key) {
            $item = parent::getItem($key);
            if ($item->isHit()) {
                Log::debug("Cache hit for: $key");
            }
            return $item;
        }
    }
    

7. Laravel-Specific Quirks

  • Cache::driver(): Returns a CacheManager (not a PSR-6 pool). Use Cache::store('redis')->getItem() for PSR-6.
  • Tag support: Only available in file, database, and redis drivers.
  • Testing: Use Cache::shouldReceive('get') in PHPUnit or ArrayAdapter for isolated tests.
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.
hamzi/corewatch
minionfactory/raw-hydrator
hexters/coinpayment
rjcodes/rjcms
act-training/laravel-permissions-manager
alimarchal/laravel-chart-of-accounts
babenkoivan/elastic-scout-driver
mkwebdesign/filament-watchdog-v5
renatomarinho/laravel-page-speed
zedmagdy/filament-business-hours
renatovdemoura/blade-elements-ui
devgeek/beacon-admin
benjamin-rqt/data-watcher-bundle
atriumphp/atrium
sandermuller/package-boost-laravel
sandermuller/boost-skills
redaxo/core
yusufgenc/filament-api-forge
l3aro/rating-star-for-filament
leek/filament-subtenant-scope