Add albums transform
parent
50bb55536f
commit
8d97dc7914
|
@ -95,6 +95,12 @@ class ApiController extends Controller
|
||||||
return new JSONResponse(['message' => 'Folder not found'], Http::STATUS_NOT_FOUND);
|
return new JSONResponse(['message' => 'Folder not found'], Http::STATUS_NOT_FOUND);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Remove folder if album
|
||||||
|
// Permissions will be checked during the transform
|
||||||
|
if ($this->request->getParam('album')) {
|
||||||
|
$folder = null;
|
||||||
|
}
|
||||||
|
|
||||||
// Run actual query
|
// Run actual query
|
||||||
try {
|
try {
|
||||||
$list = $this->timelineQuery->getDays(
|
$list = $this->timelineQuery->getDays(
|
||||||
|
@ -255,7 +261,6 @@ class ApiController extends Controller
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @NoAdminRequired
|
* @NoAdminRequired
|
||||||
* @NoCSRFRequired
|
|
||||||
*
|
*
|
||||||
* Get list of albums with counts of images
|
* Get list of albums with counts of images
|
||||||
*/
|
*/
|
||||||
|
@ -672,12 +677,18 @@ class ApiController extends Controller
|
||||||
|
|
||||||
// Filter only for one tag
|
// Filter only for one tag
|
||||||
if ($this->tagsIsEnabled()) {
|
if ($this->tagsIsEnabled()) {
|
||||||
$tagName = $this->request->getParam('tag');
|
if ($tagName = $this->request->getParam('tag')) {
|
||||||
if ($tagName) {
|
|
||||||
$transforms[] = [$this->timelineQuery, 'transformTagFilter', $tagName];
|
$transforms[] = [$this->timelineQuery, 'transformTagFilter', $tagName];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Filter for one album
|
||||||
|
if ($this->albumsIsEnabled()) {
|
||||||
|
if ($albumId = $this->request->getParam('album')) {
|
||||||
|
$transforms[] = [$this->timelineQuery, 'transformAlbumFilter', $albumId];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// Limit number of responses for day query
|
// Limit number of responses for day query
|
||||||
$limit = $this->request->getParam('limit');
|
$limit = $this->request->getParam('limit');
|
||||||
if ($limit) {
|
if ($limit) {
|
||||||
|
@ -687,8 +698,15 @@ class ApiController extends Controller
|
||||||
return $transforms;
|
return $transforms;
|
||||||
}
|
}
|
||||||
|
|
||||||
/** Preload a few "day" at the start of "days" response */
|
/**
|
||||||
private function preloadDays(array &$days, Folder &$folder, bool $recursive, bool $archive)
|
* Preload a few "day" at the start of "days" response.
|
||||||
|
*
|
||||||
|
* @param array $days the days array
|
||||||
|
* @param null|Folder $folder the folder to search in
|
||||||
|
* @param bool $recursive search in subfolders
|
||||||
|
* @param bool $archive search in archive folder only
|
||||||
|
*/
|
||||||
|
private function preloadDays(array &$days, &$folder, bool $recursive, bool $archive)
|
||||||
{
|
{
|
||||||
$uid = $this->userSession->getUser()->getUID();
|
$uid = $this->userSession->getUser()->getUID();
|
||||||
$transforms = $this->getTransformations(false);
|
$transforms = $this->getTransformations(false);
|
||||||
|
@ -696,13 +714,15 @@ class ApiController extends Controller
|
||||||
$preloadDayIds = [];
|
$preloadDayIds = [];
|
||||||
$preloadDays = [];
|
$preloadDays = [];
|
||||||
foreach ($days as &$day) {
|
foreach ($days as &$day) {
|
||||||
if ($day['count'] <= 0) continue;
|
if ($day['count'] <= 0) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
$preloaded += $day['count'];
|
$preloaded += $day['count'];
|
||||||
$preloadDayIds[] = $day['dayid'];
|
$preloadDayIds[] = $day['dayid'];
|
||||||
$preloadDays[] = &$day;
|
$preloadDays[] = &$day;
|
||||||
|
|
||||||
if ($preloaded >= 50 || count($preloadDayIds) > 5) { // should be enough
|
if ($preloaded >= 50 || \count($preloadDayIds) > 5) { // should be enough
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -8,11 +8,11 @@ use OCP\IDBConnection;
|
||||||
|
|
||||||
class TimelineQuery
|
class TimelineQuery
|
||||||
{
|
{
|
||||||
|
use TimelineQueryAlbums;
|
||||||
use TimelineQueryDays;
|
use TimelineQueryDays;
|
||||||
use TimelineQueryFaces;
|
use TimelineQueryFaces;
|
||||||
use TimelineQueryFilters;
|
use TimelineQueryFilters;
|
||||||
use TimelineQueryTags;
|
use TimelineQueryTags;
|
||||||
use TimelineQueryAlbums;
|
|
||||||
|
|
||||||
protected IDBConnection $connection;
|
protected IDBConnection $connection;
|
||||||
|
|
||||||
|
|
|
@ -4,12 +4,28 @@ declare(strict_types=1);
|
||||||
|
|
||||||
namespace OCA\Memories\Db;
|
namespace OCA\Memories\Db;
|
||||||
|
|
||||||
|
use OCP\DB\QueryBuilder\IQueryBuilder;
|
||||||
use OCP\IDBConnection;
|
use OCP\IDBConnection;
|
||||||
|
|
||||||
trait TimelineQueryAlbums
|
trait TimelineQueryAlbums
|
||||||
{
|
{
|
||||||
protected IDBConnection $connection;
|
protected IDBConnection $connection;
|
||||||
|
|
||||||
|
/** Transform only for album */
|
||||||
|
public function transformAlbumFilter(IQueryBuilder &$query, string $uid, string $albumId)
|
||||||
|
{
|
||||||
|
if (!$this->hasAlbumPermission($query->getConnection(), $uid, (int) $albumId)) {
|
||||||
|
throw new \Exception("Album {$albumId} not found");
|
||||||
|
}
|
||||||
|
|
||||||
|
// WHERE these are items with this album
|
||||||
|
$query->innerJoin('m', 'photos_albums_files', 'paf', $query->expr()->andX(
|
||||||
|
$query->expr()->eq('paf.album_id', $query->createNamedParameter($albumId)),
|
||||||
|
$query->expr()->eq('paf.file_id', 'm.fileid'),
|
||||||
|
));
|
||||||
|
}
|
||||||
|
|
||||||
|
/** Get list of albums */
|
||||||
public function getAlbums(string $uid)
|
public function getAlbums(string $uid)
|
||||||
{
|
{
|
||||||
$query = $this->connection->getQueryBuilder();
|
$query = $this->connection->getQueryBuilder();
|
||||||
|
@ -20,7 +36,7 @@ trait TimelineQueryAlbums
|
||||||
$query->expr()->eq('user', $query->createNamedParameter($uid)),
|
$query->expr()->eq('user', $query->createNamedParameter($uid)),
|
||||||
);
|
);
|
||||||
|
|
||||||
// WHERE there are items with this tag
|
// WHERE these are items with this album
|
||||||
$query->innerJoin('pa', 'photos_albums_files', 'paf', $query->expr()->andX(
|
$query->innerJoin('pa', 'photos_albums_files', 'paf', $query->expr()->andX(
|
||||||
$query->expr()->eq('paf.album_id', 'pa.album_id'),
|
$query->expr()->eq('paf.album_id', 'pa.album_id'),
|
||||||
));
|
));
|
||||||
|
@ -29,7 +45,7 @@ trait TimelineQueryAlbums
|
||||||
$query->innerJoin('paf', 'memories', 'm', $query->expr()->eq('m.fileid', 'paf.file_id'));
|
$query->innerJoin('paf', 'memories', 'm', $query->expr()->eq('m.fileid', 'paf.file_id'));
|
||||||
|
|
||||||
// WHERE these photos are in the filecache
|
// WHERE these photos are in the filecache
|
||||||
$query->innerJoin('m', 'filecache', 'f', $query->expr()->eq('m.fileid', 'f.fileid'),);
|
$query->innerJoin('m', 'filecache', 'f', $query->expr()->eq('m.fileid', 'f.fileid'));
|
||||||
|
|
||||||
// GROUP and ORDER by
|
// GROUP and ORDER by
|
||||||
$query->groupBy('pa.album_id');
|
$query->groupBy('pa.album_id');
|
||||||
|
@ -48,4 +64,30 @@ trait TimelineQueryAlbums
|
||||||
|
|
||||||
return $albums;
|
return $albums;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private function hasAlbumPermission(IDBConnection $conn, string $uid, int $albumId)
|
||||||
|
{
|
||||||
|
// Check if owner
|
||||||
|
$query = $conn->getQueryBuilder();
|
||||||
|
$query->select('album_id')->from('photos_albums')->where(
|
||||||
|
$query->expr()->andX(
|
||||||
|
$query->expr()->eq('album_id', $query->createNamedParameter($albumId, IQueryBuilder::PARAM_INT)),
|
||||||
|
$query->expr()->eq('user', $query->createNamedParameter($uid)),
|
||||||
|
)
|
||||||
|
);
|
||||||
|
if (false !== $query->executeQuery()->fetchOne()) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check in collaborators
|
||||||
|
$query = $conn->getQueryBuilder();
|
||||||
|
$query->select('album_id')->from('photos_collaborators')->where(
|
||||||
|
$query->expr()->andX(
|
||||||
|
$query->expr()->eq('album_id', $query->createNamedParameter($albumId, IQueryBuilder::PARAM_INT)),
|
||||||
|
$query->expr()->eq('collaborator_id', $query->createNamedParameter($uid)),
|
||||||
|
)
|
||||||
|
);
|
||||||
|
|
||||||
|
return false !== $query->executeQuery()->fetchOne();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -15,15 +15,15 @@ trait TimelineQueryDays
|
||||||
/**
|
/**
|
||||||
* Get the days response from the database for the timeline.
|
* Get the days response from the database for the timeline.
|
||||||
*
|
*
|
||||||
* @param Folder $folder The folder to get the days from
|
* @param null|Folder $folder The folder to get the days from
|
||||||
* @param bool $recursive Whether to get the days recursively
|
* @param bool $recursive Whether to get the days recursively
|
||||||
* @param bool $archive Whether to get the days only from the archive folder
|
* @param bool $archive Whether to get the days only from the archive folder
|
||||||
* @param array $queryTransforms An array of query transforms to apply to the query
|
* @param array $queryTransforms An array of query transforms to apply to the query
|
||||||
*
|
*
|
||||||
* @return array The days response
|
* @return array The days response
|
||||||
*/
|
*/
|
||||||
public function getDays(
|
public function getDays(
|
||||||
Folder &$folder,
|
&$folder,
|
||||||
string $uid,
|
string $uid,
|
||||||
bool $recursive,
|
bool $recursive,
|
||||||
bool $archive,
|
bool $archive,
|
||||||
|
@ -56,18 +56,18 @@ trait TimelineQueryDays
|
||||||
/**
|
/**
|
||||||
* Get the day response from the database for the timeline.
|
* Get the day response from the database for the timeline.
|
||||||
*
|
*
|
||||||
* @param Folder $folder The folder to get the day from
|
* @param null|Folder $folder The folder to get the day from
|
||||||
* @param string $uid The user id
|
* @param string $uid The user id
|
||||||
* @param int[] $dayid The day id
|
* @param int[] $dayid The day id
|
||||||
* @param bool $recursive If the query should be recursive
|
* @param bool $recursive If the query should be recursive
|
||||||
* @param bool $archive If the query should include only the archive folder
|
* @param bool $archive If the query should include only the archive folder
|
||||||
* @param array $queryTransforms The query transformations to apply
|
* @param array $queryTransforms The query transformations to apply
|
||||||
* @param mixed $day_ids
|
* @param mixed $day_ids
|
||||||
*
|
*
|
||||||
* @return array An array of day responses
|
* @return array An array of day responses
|
||||||
*/
|
*/
|
||||||
public function getDay(
|
public function getDay(
|
||||||
Folder &$folder,
|
&$folder,
|
||||||
string $uid,
|
string $uid,
|
||||||
$day_ids,
|
$day_ids,
|
||||||
bool $recursive,
|
bool $recursive,
|
||||||
|
@ -227,10 +227,10 @@ trait TimelineQueryDays
|
||||||
/**
|
/**
|
||||||
* Get the query for oc_filecache join.
|
* Get the query for oc_filecache join.
|
||||||
*
|
*
|
||||||
* @param IQueryBuilder $query Query builder
|
* @param IQueryBuilder $query Query builder
|
||||||
* @param array|Folder $folder Either the top folder or array of folder Ids
|
* @param null|array|Folder $folder Either the top folder or array of folder Ids
|
||||||
* @param bool $recursive Whether to get the days recursively
|
* @param bool $recursive Whether to get the days recursively
|
||||||
* @param bool $archive Whether to get the days only from the archive folder
|
* @param bool $archive Whether to get the days only from the archive folder
|
||||||
*/
|
*/
|
||||||
private function getFilecacheJoinQuery(
|
private function getFilecacheJoinQuery(
|
||||||
IQueryBuilder &$query,
|
IQueryBuilder &$query,
|
||||||
|
@ -238,7 +238,14 @@ trait TimelineQueryDays
|
||||||
bool $recursive,
|
bool $recursive,
|
||||||
bool $archive
|
bool $archive
|
||||||
) {
|
) {
|
||||||
$pathQuery = null;
|
// Join with memories
|
||||||
|
$baseOp = $query->expr()->eq('f.fileid', 'm.fileid');
|
||||||
|
if (null === $folder) {
|
||||||
|
return $baseOp; // No folder, get all
|
||||||
|
}
|
||||||
|
|
||||||
|
// Filter by folder (recursive or otherwise)
|
||||||
|
$pathOp = null;
|
||||||
if ($recursive) {
|
if ($recursive) {
|
||||||
// Get all subfolder Ids recursively
|
// Get all subfolder Ids recursively
|
||||||
$folderIds = [];
|
$folderIds = [];
|
||||||
|
@ -250,15 +257,15 @@ trait TimelineQueryDays
|
||||||
}
|
}
|
||||||
|
|
||||||
// Join with folder IDs
|
// Join with folder IDs
|
||||||
$pathQuery = $query->expr()->in('f.parent', $query->createNamedParameter($folderIds, IQueryBuilder::PARAM_INT_ARRAY));
|
$pathOp = $query->expr()->in('f.parent', $query->createNamedParameter($folderIds, IQueryBuilder::PARAM_INT_ARRAY));
|
||||||
} else {
|
} else {
|
||||||
// If getting non-recursively folder only check for parent
|
// If getting non-recursively folder only check for parent
|
||||||
$pathQuery = $query->expr()->eq('f.parent', $query->createNamedParameter($folder->getId(), IQueryBuilder::PARAM_INT));
|
$pathOp = $query->expr()->eq('f.parent', $query->createNamedParameter($folder->getId(), IQueryBuilder::PARAM_INT));
|
||||||
}
|
}
|
||||||
|
|
||||||
return $query->expr()->andX(
|
return $query->expr()->andX(
|
||||||
$query->expr()->eq('f.fileid', 'm.fileid'),
|
$baseOp,
|
||||||
$pathQuery,
|
$pathOp,
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue