Skip to content

Instantly share code, notes, and snippets.

@Yahav
Created October 30, 2021 09:34
Show Gist options
  • Save Yahav/65e3fd68614653bc93c66d5679069ba9 to your computer and use it in GitHub Desktop.
Save Yahav/65e3fd68614653bc93c66d5679069ba9 to your computer and use it in GitHub Desktop.
spatie/laravel-medialibrary Caching
<?php
namespace App\Cache;
use Illuminate\Support\Facades\Cache;
use Spatie\MediaLibrary\HasMedia;
class CachedMedia
{
public static function get(HasMedia $modelInstance, $collection, array $filters)
{
$modelId = $modelInstance->getKey();
$modelType = (new \ReflectionClass($modelInstance))->getName();
$encodedFilters = sha1(json_encode($filters));
return Cache::tags(['media', "media.$modelType.$modelId"])->get("media.$modelType.$modelId.$collection.$encodedFilters", function () use ($modelInstance, $modelId, $modelType, $collection, $filters, $encodedFilters) {
$media = $modelInstance->getMediaRepository()
->getCollection($modelInstance, $collection, $filters)
->collectionName($collection);
Cache::tags(['media', "media.$modelType.$modelId"])->put("media.$modelType.$modelId.$collection.$encodedFilters", $media, now()->addHours(12));
return $media;
});
}
public static function forget($modelType, $modelId) {
return Cache::tags(['media', "media.$modelType.$modelId"])->flush();
}
}
<?php
namespace App\Observers;
use App\Cache\CachedMedia;
use App\Models\Media;
class MediaObserver
{
/**
* Handle the Media "created" event.
*
* @param \App\Models\Media $media
* @return void
*/
public function created(Media $media)
{
CachedMedia::forget($media->model_type, $media->model_id);
}
/**
* Handle the Media "updated" event.
*
* @param \App\Models\Media $media
* @return void
*/
public function updated(Media $media)
{
CachedMedia::forget($media->model_type, $media->model_id);
}
/**
* Handle the Media "deleted" event.
*
* @param \App\Models\Media $media
* @return void
*/
public function deleted(Media $media)
{
CachedMedia::forget($media->model_type, $media->model_id);
}
/**
* Handle the Media "restored" event.
*
* @param \App\Models\Media $media
* @return void
*/
public function restored(Media $media)
{
CachedMedia::forget($media->model_type, $media->model_id);
}
/**
* Handle the Media "force deleted" event.
*
* @param \App\Models\Media $media
* @return void
*/
public function forceDeleted(Media $media)
{
CachedMedia::forget($media->model_type, $media->model_id);
}
}
<?php
namespace App\Traits;
use App\Cache\CachedMedia;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Support\Collection;
use Spatie\MediaLibrary\MediaCollections\MediaCollection;
trait HasCachedMedia {
/**
* Get media collection by its collectionName.
*
* @param string $collectionName
* @param array|callable $filters
*
* @return MediaCollections\Models\Collections\MediaCollection
*/
public function getMedia(string $collectionName = 'default', $filters = []): Collection
{
/** @var Model $this */
return CachedMedia::get($this, $collectionName, $filters);
}
}
<?php
namespace App\Models\Website;
use App\Traits\HasCachedMedia;
use Spatie\MediaLibrary\MediaCollections\File;
use Spatie\MediaLibrary\HasMedia;
use Spatie\MediaLibrary\InteractsWithMedia;
use Spatie\MediaLibrary\MediaCollections\Models\Media;
class News extends Model implements HasMedia
{
use HasFactory, InteractsWithMedia, HasCachedMedia {
HasCachedMedia::getMedia insteadof InteractsWithMedia;
}
// ...REST OF MODEL
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment