ClusterController::findIgnored()   B
last analyzed

Complexity

Conditions 6
Paths 6

Size

Total Lines 42
Code Lines 29

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 42

Importance

Changes 0
Metric Value
cc 6
eloc 29
c 0
b 0
f 0
nc 6
nop 0
dl 0
loc 42
ccs 0
cts 30
cp 0
crap 42
rs 8.8337
1
<?php
2
/**
3
 * @copyright Copyright (c) 2018-2024 Matias De lellis <[email protected]>
4
 *
5
 * @author Matias De lellis <[email protected]>
6
 *
7
 * @license GNU AGPL version 3 or any later version
8
 *
9
 * This program is free software: you can redistribute it and/or modify
10
 * it under the terms of the GNU Affero General Public License as
11
 * published by the Free Software Foundation, either version 3 of the
12
 * License, or (at your option) any later version.
13
 *
14
 * This program is distributed in the hope that it will be useful,
15
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
16
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17
 * GNU Affero General Public License for more details.
18
 *
19
 * You should have received a copy of the GNU Affero General Public License
20
 * along with this program.  If not, see <http://www.gnu.org/licenses/>.
21
 *
22
 */
23
24
namespace OCA\FaceRecognition\Controller;
25
26
use OCP\IRequest;
27
use OCP\Files\File;
28
29
use OCP\AppFramework\Http;
30
use OCP\AppFramework\Http\DataResponse;
31
use OCP\AppFramework\Http\JSONResponse;
32
use OCP\AppFramework\Http\DataDisplayResponse;
33
use OCP\AppFramework\Controller;
34
35
use OCA\FaceRecognition\Db\Face;
36
use OCA\FaceRecognition\Db\FaceMapper;
37
38
use OCA\FaceRecognition\Db\Image;
39
use OCA\FaceRecognition\Db\ImageMapper;
40
41
use OCA\FaceRecognition\Db\Person;
42
use OCA\FaceRecognition\Db\PersonMapper;
43
44
use OCA\FaceRecognition\Service\SettingsService;
45
use OCA\FaceRecognition\Service\UrlService;
46
47
48
class ClusterController extends Controller {
49
50
	/** @var FaceMapper */
51
	private $faceMapper;
52
53
	/** @var ImageMapper */
54
	private $imageMapper;
55
56
	/** @var PersonMapper */
57
	private $personMapper;
58
59
	/** @var SettingsService */
60
	private $settingsService;
61
62
	/** @var UrlService */
63
	private $urlService;
64
65
	/** @var string */
66
	private $userId;
67
68
	public function __construct($AppName,
69
	                            IRequest        $request,
70
	                            FaceMapper      $faceMapper,
71
	                            ImageMapper     $imageMapper,
72
	                            PersonMapper    $personmapper,
73
	                            SettingsService $settingsService,
74
	                            UrlService      $urlService,
75
	                            $UserId)
76
	{
77
		parent::__construct($AppName, $request);
78
79
		$this->faceMapper      = $faceMapper;
80
		$this->imageMapper     = $imageMapper;
81
		$this->personMapper    = $personmapper;
82
		$this->settingsService = $settingsService;
83
		$this->urlService      = $urlService;
84
		$this->userId          = $UserId;
85
	}
86
87
	/**
88
	 * @NoAdminRequired
89
	 *
90
	 * @return DataResponse
91
	 */
92
	public function find(int $id): DataResponse {
93
		$person = $this->personMapper->find($this->userId, $id);
94
95
		$resp = [];
96
		$faces = [];
97
		$personFaces = $this->faceMapper->findFromCluster($this->userId, $person->getId(), $this->settingsService->getCurrentFaceModel());
98
		foreach ($personFaces as $personFace) {
99
			$image = $this->imageMapper->find($this->userId, $personFace->getImage());
100
101
			$file =  $this->urlService->getFileNode($image->getFile());
102
			if ($file === null) continue;
103
104
			$face = [];
105
			$face['thumbUrl'] = $this->urlService->getThumbUrl($personFace->getId(), 50);
106
			$face['fileUrl'] = $this->urlService->getRedirectToFileUrl($file);
107
			$faces[] = $face;
108
		}
109
		$resp['name'] = $person->getName();
110
		$resp['id'] = $person->getId();
111
		$resp['faces'] = $faces;
112
113
		return new DataResponse($resp);
114
	}
115
116
	/**
117
	 * @NoAdminRequired
118
	 *
119
	 * @return DataResponse
120
	 */
121
	public function findByName(string $personName): DataResponse {
122
		$userEnabled = $this->settingsService->getUserEnabled($this->userId);
123
124
		$resp = array();
125
		$resp['clusters'] = array();
126
127
		if (!$userEnabled)
128
			return new DataResponse($resp);
129
130
		$modelId = $this->settingsService->getCurrentFaceModel();
131
132
		$persons = $this->personMapper->findByName($this->userId, $modelId, $personName);
133
		foreach ($persons as $person) {
134
			$personFaces = $this->faceMapper->findFromCluster($this->userId, $person->getId(), $modelId);
135
136
			$faces = [];
137
			foreach ($personFaces as $personFace) {
138
				$image = $this->imageMapper->find($this->userId, $personFace->getImage());
139
140
				$file = $this->urlService->getFileNode($image->getFile());
141
				if ($file === null) continue;
142
143
				$face = [];
144
				$face['thumbUrl'] = $this->urlService->getThumbUrl($personFace->getId(), 50);
145
				$face['fileUrl'] = $this->urlService->getRedirectToFileUrl($file);
146
				$faces[] = $face;
147
			}
148
149
			$cluster = [];
150
			$cluster['name'] = $person->getName();
151
			$cluster['count'] = count($personFaces);
152
			$cluster['id'] = $person->getId();
153
			$cluster['faces'] = $faces;
154
			$resp['clusters'][] = $cluster;
155
		}
156
157
		return new DataResponse($resp);
158
	}
159
160
	/**
161
	 * @NoAdminRequired
162
	 *
163
	 * @return DataResponse
164
	 */
165
	public function findUnassigned(): DataResponse {
166
		$userEnabled = $this->settingsService->getUserEnabled($this->userId);
167
168
		$resp = array();
169
		$resp['enabled'] = $userEnabled;
170
		$resp['clusters'] = array();
171
172
		if (!$userEnabled)
173
			return new DataResponse($resp);
174
175
		$modelId = $this->settingsService->getCurrentFaceModel();
176
		$minClusterSize = $this->settingsService->getMinimumFacesInCluster();
177
178
		$clusters = $this->personMapper->findUnassigned($this->userId, $modelId);
179
		foreach ($clusters as $cluster) {
180
			$clusterSize = $this->personMapper->countClusterFaces($cluster->getId());
181
			if ($clusterSize < $minClusterSize)
182
				continue;
183
184
			$personFaces = $this->faceMapper->findFromCluster($this->userId, $cluster->getId(), $modelId, 40);
185
			$faces = [];
186
			foreach ($personFaces as $personFace) {
187
				$image = $this->imageMapper->find($this->userId, $personFace->getImage());
188
189
				$file = $this->urlService->getFileNode($image->getFile());
190
				if ($file === null) continue;
191
192
				$face = [];
193
				$face['thumbUrl'] = $this->urlService->getThumbUrl($personFace->getId(), 50);
194
				$face['fileUrl'] = $this->urlService->getRedirectToFileUrl($file);
195
196
				$faces[] = $face;
197
			}
198
199
			$entry = [];
200
			$entry['count'] = $clusterSize;
201
			$entry['id'] = $cluster->getId();
202
			$entry['faces'] = $faces;
203
			$resp['clusters'][] = $entry;
204
		}
205
206
		return new DataResponse($resp);
207
	}
208
209
	/**
210
	 * @NoAdminRequired
211
	 *
212
	 * @return DataResponse
213
	 */
214
	Public function findIgnored(): DataResponse {
215
		$userEnabled = $this->settingsService->getUserEnabled($this->userId);
216
217
		$resp = array();
218
		$resp['enabled'] = $userEnabled;
219
		$resp['clusters'] = array();
220
221
		if (!$userEnabled)
222
			return new DataResponse($resp);
223
224
		$modelId = $this->settingsService->getCurrentFaceModel();
225
		$minClusterSize = $this->settingsService->getMinimumFacesInCluster();
226
227
		$clusters = $this->personMapper->findIgnored($this->userId, $modelId);
228
		foreach ($clusters as $cluster) {
229
			$clusterSize = $this->personMapper->countClusterFaces($cluster->getId());
230
			if ($clusterSize < $minClusterSize)
231
				continue;
232
233
			$personFaces = $this->faceMapper->findFromCluster($this->userId, $cluster->getId(), $modelId, 40);
234
			$faces = [];
235
			foreach ($personFaces as $personFace) {
236
				$image = $this->imageMapper->find($this->userId, $personFace->getImage());
237
238
				$file = $this->urlService->getFileNode($image->getFile());
239
				if ($file === null) continue;
240
241
				$face = [];
242
				$face['thumbUrl'] = $this->urlService->getThumbUrl($personFace->getId(), 50);
243
				$face['fileUrl'] = $this->urlService->getRedirectToFileUrl($file);
244
245
				$faces[] = $face;
246
			}
247
248
			$entry = [];
249
			$entry['count'] = $clusterSize;
250
			$entry['id'] = $cluster->getId();
251
			$entry['faces'] = $faces;
252
			$resp['clusters'][] = $entry;
253
		}
254
255
		return new DataResponse($resp);
256
	}
257
258
	/**
259
	 * @NoAdminRequired
260
	 *
261
	 * @param int $id
262
	 * @param bool $visible
263
	 *
264
	 * @return DataResponse
265
	 */
266
	public function setVisibility (int $id, bool $visible): DataResponse {
267
		$resp = array();
268
		$this->personMapper->setVisibility($id, $visible);
269
		return new DataResponse($resp);
270
	}
271
272
	/**
273
	 * @NoAdminRequired
274
	 *
275
	 * @param int $id if of cluster
276
	 * @param int $face id of face.
277
	 * @param string|null $name optional name to rename it.
278
	 *
279
	 * @return DataResponse
280
	 */
281
	public function detachFace (int $id, int $face, $name = null): DataResponse {
282
		$person = $this->personMapper->detachFace($id, $face, $name);
283
		return new DataResponse($person);
284
	}
285
286
	/**
287
	 * @NoAdminRequired
288
	 *
289
	 * @param int $id of cluster
290
	 * @param string $name to rename them.
291
	 * @param int|null $face_id optional face id if you just want to name that face
292
	 *
293
	 * @return DataResponse new person with that update.
294
	 */
295
	public function updateName($id, $name, $face_id = null): DataResponse {
296
		if (is_null($face_id)) {
297
			$person = $this->personMapper->find($this->userId, $id);
298
			$person->setName($name);
299
			$this->personMapper->update($person);
300
		} else {
301
			$person = $this->personMapper->detachFace($id, $face_id, $name);
302
		}
303
		return new DataResponse($person);
304
	}
305
306
}
307