2018-08-19 09:05:33 +00:00
|
|
|
<?php
|
|
|
|
|
|
|
|
namespace App\Services;
|
|
|
|
|
|
|
|
use App\Models\Album;
|
|
|
|
use App\Models\Artist;
|
2024-01-04 21:51:32 +00:00
|
|
|
use Illuminate\Support\Facades\File;
|
2022-07-16 23:11:24 +00:00
|
|
|
use Illuminate\Support\Str;
|
2020-12-22 20:11:22 +00:00
|
|
|
|
2018-08-19 09:05:33 +00:00
|
|
|
class MediaMetadataService
|
|
|
|
{
|
2022-08-08 16:00:59 +00:00
|
|
|
public function __construct(private SpotifyService $spotifyService, private ImageWriter $imageWriter)
|
|
|
|
{
|
2018-08-31 13:47:15 +00:00
|
|
|
}
|
|
|
|
|
2022-07-18 11:00:37 +00:00
|
|
|
public function tryDownloadAlbumCover(Album $album): void
|
2018-08-19 09:05:33 +00:00
|
|
|
{
|
2022-07-18 11:00:37 +00:00
|
|
|
optional($this->spotifyService->tryGetAlbumCover($album), function (string $coverUrl) use ($album): void {
|
|
|
|
$this->writeAlbumCover($album, $coverUrl);
|
|
|
|
});
|
2018-08-19 09:05:33 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
2022-07-16 23:11:24 +00:00
|
|
|
* Write an album cover image file and update the Album with the new cover attribute.
|
2018-08-19 09:05:33 +00:00
|
|
|
*
|
2022-07-16 22:42:29 +00:00
|
|
|
* @param string $source Path, URL, or even binary data. See https://image.intervention.io/v2/api/make.
|
2023-04-17 19:45:43 +00:00
|
|
|
* @param string|null $destination The destination path. Automatically generated if empty.
|
2018-08-19 09:05:33 +00:00
|
|
|
*/
|
2020-06-13 11:00:51 +00:00
|
|
|
public function writeAlbumCover(
|
|
|
|
Album $album,
|
2022-07-16 22:42:29 +00:00
|
|
|
string $source,
|
2022-07-16 23:11:24 +00:00
|
|
|
string $extension = 'png',
|
2022-07-18 11:00:37 +00:00
|
|
|
?string $destination = '',
|
2020-06-13 11:00:51 +00:00
|
|
|
bool $cleanUp = true
|
2020-09-06 21:20:42 +00:00
|
|
|
): void {
|
2022-08-08 16:00:59 +00:00
|
|
|
attempt(function () use ($album, $source, $extension, $destination, $cleanUp): void {
|
2018-08-19 09:05:33 +00:00
|
|
|
$extension = trim(strtolower($extension), '. ');
|
2022-07-16 23:11:24 +00:00
|
|
|
$destination = $destination ?: $this->generateAlbumCoverPath($extension);
|
2022-07-16 22:42:29 +00:00
|
|
|
$this->imageWriter->write($destination, $source);
|
2018-08-19 09:05:33 +00:00
|
|
|
|
2020-06-13 11:00:51 +00:00
|
|
|
if ($cleanUp) {
|
|
|
|
$this->deleteAlbumCoverFiles($album);
|
|
|
|
}
|
|
|
|
|
2018-08-19 09:05:33 +00:00
|
|
|
$album->update(['cover' => basename($destination)]);
|
2020-06-13 11:00:51 +00:00
|
|
|
$this->createThumbnailForAlbum($album);
|
2022-08-08 16:00:59 +00:00
|
|
|
});
|
2018-08-19 09:05:33 +00:00
|
|
|
}
|
|
|
|
|
2022-07-18 11:00:37 +00:00
|
|
|
public function tryDownloadArtistImage(Artist $artist): void
|
2018-08-19 09:05:33 +00:00
|
|
|
{
|
2022-07-18 11:00:37 +00:00
|
|
|
optional($this->spotifyService->tryGetArtistImage($artist), function (string $imageUrl) use ($artist): void {
|
|
|
|
$this->writeArtistImage($artist, $imageUrl);
|
|
|
|
});
|
2018-08-19 09:05:33 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
/**
|
2022-07-16 23:11:24 +00:00
|
|
|
* Write an artist image file update the Artist with the new image attribute.
|
2018-08-19 09:05:33 +00:00
|
|
|
*
|
2022-07-16 22:42:29 +00:00
|
|
|
* @param string $source Path, URL, or even binary data. See https://image.intervention.io/v2/api/make.
|
2023-04-17 19:45:43 +00:00
|
|
|
* @param string|null $destination The destination path. Automatically generated if empty.
|
2018-08-19 09:05:33 +00:00
|
|
|
*/
|
2018-08-24 15:27:19 +00:00
|
|
|
public function writeArtistImage(
|
|
|
|
Artist $artist,
|
2022-07-16 22:42:29 +00:00
|
|
|
string $source,
|
2022-07-16 23:11:24 +00:00
|
|
|
string $extension = 'png',
|
|
|
|
?string $destination = '',
|
2020-06-13 11:00:51 +00:00
|
|
|
bool $cleanUp = true
|
2018-08-24 15:27:19 +00:00
|
|
|
): void {
|
2022-08-08 16:00:59 +00:00
|
|
|
attempt(function () use ($artist, $source, $extension, $destination, $cleanUp): void {
|
2018-08-19 09:05:33 +00:00
|
|
|
$extension = trim(strtolower($extension), '. ');
|
2022-07-16 23:11:24 +00:00
|
|
|
$destination = $destination ?: $this->generateArtistImagePath($extension);
|
2022-07-16 22:42:29 +00:00
|
|
|
$this->imageWriter->write($destination, $source);
|
2018-08-19 09:05:33 +00:00
|
|
|
|
2020-06-13 11:00:51 +00:00
|
|
|
if ($cleanUp && $artist->has_image) {
|
2024-01-04 21:51:32 +00:00
|
|
|
File::delete($artist->image_path);
|
2020-06-13 11:00:51 +00:00
|
|
|
}
|
|
|
|
|
2018-08-19 09:05:33 +00:00
|
|
|
$artist->update(['image' => basename($destination)]);
|
2022-08-08 16:00:59 +00:00
|
|
|
});
|
2018-08-19 09:05:33 +00:00
|
|
|
}
|
|
|
|
|
2022-07-16 23:11:24 +00:00
|
|
|
private function generateAlbumCoverPath(string $extension): string
|
2018-08-19 09:05:33 +00:00
|
|
|
{
|
2022-07-16 23:11:24 +00:00
|
|
|
return album_cover_path(sprintf('%s.%s', sha1(Str::uuid()), trim($extension, '.')));
|
2018-08-19 09:05:33 +00:00
|
|
|
}
|
|
|
|
|
2022-07-16 23:11:24 +00:00
|
|
|
private function generateArtistImagePath(string $extension): string
|
2018-08-19 09:05:33 +00:00
|
|
|
{
|
2022-07-16 23:11:24 +00:00
|
|
|
return artist_image_path(sprintf('%s.%s', sha1(Str::uuid()), trim($extension, '.')));
|
2018-08-19 09:05:33 +00:00
|
|
|
}
|
2020-06-12 13:55:45 +00:00
|
|
|
|
2020-06-13 11:00:51 +00:00
|
|
|
/**
|
|
|
|
* Get the URL of an album's thumbnail.
|
|
|
|
* Auto-generate the thumbnail when possible, if one doesn't exist yet.
|
|
|
|
*/
|
2020-06-12 13:55:45 +00:00
|
|
|
public function getAlbumThumbnailUrl(Album $album): ?string
|
|
|
|
{
|
|
|
|
if (!$album->has_cover) {
|
|
|
|
return null;
|
|
|
|
}
|
|
|
|
|
2024-01-04 21:51:32 +00:00
|
|
|
if (!File::exists($album->thumbnail_path)) {
|
2020-06-13 11:00:51 +00:00
|
|
|
$this->createThumbnailForAlbum($album);
|
|
|
|
}
|
|
|
|
|
|
|
|
return $album->thumbnail;
|
|
|
|
}
|
2020-06-12 13:55:45 +00:00
|
|
|
|
2020-06-13 11:00:51 +00:00
|
|
|
private function createThumbnailForAlbum(Album $album): void
|
|
|
|
{
|
2022-07-16 22:42:29 +00:00
|
|
|
$this->imageWriter->write($album->thumbnail_path, $album->cover_path, ['max_width' => 48, 'blur' => 10]);
|
2020-06-13 11:00:51 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
private function deleteAlbumCoverFiles(Album $album): void
|
|
|
|
{
|
|
|
|
if (!$album->has_cover) {
|
|
|
|
return;
|
2020-06-12 13:55:45 +00:00
|
|
|
}
|
|
|
|
|
2024-01-04 21:51:32 +00:00
|
|
|
File::delete($album->cover_path);
|
|
|
|
File::delete($album->thumbnail_path);
|
2020-06-12 13:55:45 +00:00
|
|
|
}
|
2018-08-19 09:05:33 +00:00
|
|
|
}
|