Custom Cache Strategies

The bundle provides a comprehensive set of cache strategies through configuration. However, for advanced use cases requiring specific behaviors not covered by the YAML configuration, you can create custom cache strategies programmatically.

When to Use Custom Strategies

Use custom cache strategies when you need:

  • Dynamic behavior: Cache strategies that change based on runtime conditions

  • Complex matching logic: URL patterns too complex for regex or simple callbacks

  • Custom plugins: Workbox plugins with specific configuration

  • Conditional caching: Different strategies based on user state, headers, or other factors

  • Business logic integration: Caching tied to your application's domain logic

For most use cases, the YAML configuration and resource caching are sufficient.

Quick Start: Using WorkboxCacheStrategy

The easiest way to create custom cache strategies is using the WorkboxCacheStrategy helper class:

src/Service/MyCustomCacheStrategies.php
<?php

declare(strict_types=1);

namespace App\Service;

use SpomkyLabs\PwaBundle\CachingStrategy\CacheStrategyInterface;
use SpomkyLabs\PwaBundle\CachingStrategy\HasCacheStrategiesInterface;
use SpomkyLabs\PwaBundle\CachingStrategy\WorkboxCacheStrategy;
use SpomkyLabs\PwaBundle\WorkboxPlugin\ExpirationPlugin;

final readonly class MyCustomCacheStrategies implements HasCacheStrategiesInterface
{
    /**
     * @return array<CacheStrategyInterface>
     */
    public function getCacheStrategies(): array
    {
        return [
            // CacheFirst strategy for API data
            WorkboxCacheStrategy::create(
                enabled: true,
                requireWorkbox: true,
                strategy: CacheStrategyInterface::STRATEGY_CACHE_FIRST,
                matchCallback: '({url}) => url.pathname.startsWith("/api/static/")',
            )
                ->withName('api-static-data')
                ->withPlugin(
                    ExpirationPlugin::create(
                        maxEntries: 50,
                        maxAgeSeconds: 86400, // 1 day
                    )
                ),
        ];
    }
}
circle-info

With service autoconfiguration enabled (default in Symfony), the tag spomky_labs_pwa.cache_strategy is added automatically. Otherwise, you need to tag your service manually.

Complete Example: Multiple Strategies

A comprehensive example showing various cache strategies with different configurations:

WorkboxCacheStrategy API

The WorkboxCacheStrategy class provides a fluent interface for building cache strategies:

create()

Create a new strategy instance:

Available strategies:

  • CacheStrategyInterface::STRATEGY_CACHE_FIRST - Cache first, fallback to network

  • CacheStrategyInterface::STRATEGY_NETWORK_FIRST - Network first, fallback to cache

  • CacheStrategyInterface::STRATEGY_STALE_WHILE_REVALIDATE - Cache immediately, update in background

  • CacheStrategyInterface::STRATEGY_CACHE_ONLY - Cache only, never network

  • CacheStrategyInterface::STRATEGY_NETWORK_ONLY - Network only, never cache

withName()

Set a custom cache name:

withMethod()

Specify HTTP method to intercept (default: all methods):

withPlugin()

Add Workbox plugins to customize behavior:

withPreloadUrl()

Precache specific URLs when service worker installs:

withOptions()

Set additional Workbox options:

Available Workbox Plugins

ExpirationPlugin

Automatically remove old cache entries:

CacheableResponsePlugin

Control which responses get cached:

BroadcastUpdatePlugin

Notify clients when cached data updates:

Listen for updates in your application:

BackgroundSyncPlugin

Queue failed requests for retry when online:

Match Callback Patterns

The matchCallback parameter supports several formats:

1. Path Prefix

2. Regular Expression

3. Origin Match

4. Custom JavaScript Callback

5. Special Keywords

Advanced Example: Conditional Strategy

Create strategies that adapt based on conditions:

Real-World Use Cases

Use Case 1: Multi-tenant Application

Different caching for each tenant:

Use Case 2: Authenticated API with Token Refresh

Cache API calls but refresh when needed:

Use Case 3: Versioned API Endpoints

Different strategies for stable vs unstable API versions:

Implementing Custom Strategy Interface

For complete control, implement CacheStrategyInterface directly:

circle-exclamation

Service Registration

If service autoconfiguration is disabled, register your service manually:

Debugging Custom Strategies

1. Check Generated Service Worker

View the compiled service worker at /sw.js (or your configured dest) to see the generated JavaScript:

2. Enable Debug Mode

Set kernel.debug: true to get commented JavaScript output:

When debug is enabled, the generated code includes comments:

3. Chrome DevTools

  1. Open DevTools (F12)

  2. Go to ApplicationService Workers

  3. Click "Update" to reload service worker

  4. Check ApplicationCache Storage to see your custom caches

  5. Use Network tab with "Offline" to test cache behavior

Best Practices

  1. Start with YAML configuration: Only use custom strategies when necessary

  2. Use descriptive names: Make cache names clear (e.g., api-user-data not cache1)

  3. Set appropriate limits: Configure maxEntries and maxAgeSeconds to prevent cache bloat

  4. Test offline: Verify strategies work correctly without network

  5. Monitor cache size: Check DevTools → Storage to ensure caches don't grow too large

  6. Use typed callbacks: TypeScript-style types help prevent errors in matchCallback

  7. Document complex logic: Add comments explaining why custom strategies exist

Last updated

Was this helpful?