Passed
Push — master ( 23afda...b1ae99 )
by Pauli
03:08
created

AmpacheImageController::setClientCaching()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 3
Code Lines 2

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 1
eloc 2
c 0
b 0
f 0
nc 1
nop 2
dl 0
loc 3
rs 10
1
<?php declare(strict_types=1);
2
3
/**
4
 * ownCloud - Music app
5
 *
6
 * This file is licensed under the Affero General Public License version 3 or
7
 * later. See the COPYING file.
8
 *
9
 * @author Pauli Järvinen <[email protected]>
10
 * @copyright Pauli Järvinen 2023 - 2025
11
 */
12
13
namespace OCA\Music\Controller;
14
15
use OCA\Music\BusinessLayer\AlbumBusinessLayer;
16
use OCA\Music\BusinessLayer\ArtistBusinessLayer;
17
use OCA\Music\BusinessLayer\PlaylistBusinessLayer;
18
use OCA\Music\AppFramework\BusinessLayer\BusinessLayer;
19
use OCA\Music\AppFramework\BusinessLayer\BusinessLayerException;
20
use OCA\Music\AppFramework\Core\Logger;
21
use OCA\Music\Http\ErrorResponse;
22
use OCA\Music\Http\FileResponse;
23
use OCA\Music\Utility\AmpacheImageService;
24
use OCA\Music\Utility\CoverHelper;
25
use OCA\Music\Utility\HttpUtil;
26
use OCA\Music\Utility\LibrarySettings;
27
use OCA\Music\Utility\PlaceholderImage;
28
use OCP\AppFramework\Controller;
29
use OCP\AppFramework\Http;
30
use OCP\AppFramework\Http\Response;
31
use OCP\IRequest;
32
33
class AmpacheImageController extends Controller {
34
	private AmpacheImageService $service;
35
	private CoverHelper $coverHelper;
36
	private LibrarySettings $librarySettings;
37
	private AlbumBusinessLayer $albumBusinessLayer;
38
	private ArtistBusinessLayer $artistBusinessLayer;
39
	private PlaylistBusinessLayer $playlistBusinessLayer;
40
	private Logger $logger;
41
42
	public function __construct(
43
			string $appname,
44
			IRequest $request,
45
			AmpacheImageService $service,
46
			CoverHelper $coverHelper,
47
			LibrarySettings $librarySettings,
48
			AlbumBusinessLayer $albumBusinessLayer,
49
			ArtistBusinessLayer $artistBusinessLayer,
50
			PlaylistBusinessLayer $playlistBusinessLayer,
51
			Logger $logger) {
52
		parent::__construct($appname, $request);
53
		$this->service = $service;
54
		$this->coverHelper = $coverHelper;
55
		$this->librarySettings = $librarySettings;
56
		$this->albumBusinessLayer = $albumBusinessLayer;
57
		$this->artistBusinessLayer = $artistBusinessLayer;
58
		$this->playlistBusinessLayer = $playlistBusinessLayer;
59
		$this->logger = $logger;
60
	}
61
62
	/**
63
	 * @NoAdminRequired
64
	 * @PublicPage
65
	 * @NoCSRFRequired
66
	 * @NoSameSiteCookieRequired
67
	 * @CORS
68
	 */
69
	public function image(?string $token, ?string $object_id, string $object_type='album', ?int $size=null) : Response {
70
		if ($token === null) {
71
			// Workaround for Ample client which uses this kind of call to get the placeholder graphics
72
			$response = new FileResponse(PlaceholderImage::generateForResponse('?', $object_type, 200));
73
			HttpUtil::setClientCachingDays($response, 365);
74
			return $response;
75
		}
76
77
		$userId = $this->service->getUserForToken($token, $object_type, (int)$object_id);
78
		if ($userId === null) {
79
			return new ErrorResponse(Http::STATUS_FORBIDDEN, 'invalid token');
80
		}
81
82
		$businessLayer = $this->getBusinessLayer($object_type);
83
		if ($businessLayer === null) {
84
			return new ErrorResponse(Http::STATUS_NOT_FOUND, "invalid object_type $object_type");
85
		}
86
87
		try {
88
			$entity = $businessLayer->find((int)$object_id, $userId);
89
		} catch (BusinessLayerException $e) {
90
			return new ErrorResponse(Http::STATUS_NOT_FOUND, "$object_type $object_id not found");
91
		}
92
93
		$coverImage = $this->coverHelper->getCover($entity, $userId, $this->librarySettings->getFolder($userId), $size);
94
		if ($coverImage === null) {
95
			return new ErrorResponse(Http::STATUS_NOT_FOUND, "$object_type $object_id has no cover image");
96
		}
97
98
		$response = new FileResponse($coverImage);
99
		HttpUtil::setClientCachingDays($response, 30);
100
		return $response;
101
	}
102
103
	private function getBusinessLayer(string $object_type) : ?BusinessLayer {
104
		switch ($object_type) {
105
			case 'album':		return $this->albumBusinessLayer;
106
			case 'artist':		return $this->artistBusinessLayer;
107
			case 'playlist':	return $this->playlistBusinessLayer;
108
			default:			return null;
109
		}
110
	}
111
}
112