4
0
mirror of https://github.com/AzuraCast/AzuraCast.git synced 2024-06-14 05:06:37 +00:00

Fixes #5951 -- Fix custom field sorting on Media Manager.

This commit is contained in:
Buster Neece 2022-12-18 18:12:40 -06:00
parent fcdede7122
commit ec50492047
No known key found for this signature in database
GPG Key ID: F1D2E64A0005E80E
3 changed files with 51 additions and 54 deletions

View File

@ -234,7 +234,7 @@ export default {
_.forEach(this.customFields.slice(), (field) => { _.forEach(this.customFields.slice(), (field) => {
fields.push({ fields.push({
key: 'media.custom_fields.' + field.id, key: 'media.custom_fields[' + field.id + ']',
label: field.name, label: field.name,
sortable: true, sortable: true,
selectable: true, selectable: true,

View File

@ -19,6 +19,7 @@ use Doctrine\ORM\Query\Expr;
use League\Flysystem\StorageAttributes; use League\Flysystem\StorageAttributes;
use Psr\Http\Message\ResponseInterface; use Psr\Http\Message\ResponseInterface;
use Psr\SimpleCache\CacheInterface; use Psr\SimpleCache\CacheInterface;
use Symfony\Component\PropertyAccess\PropertyAccessorInterface;
final class ListAction final class ListAction
{ {
@ -26,8 +27,7 @@ final class ListAction
public function __construct( public function __construct(
private readonly EntityManagerInterface $em, private readonly EntityManagerInterface $em,
private readonly CacheInterface $cache, private readonly CacheInterface $cache
private readonly Entity\Repository\StationRepository $stationRepo
) { ) {
} }
@ -327,11 +327,14 @@ final class ListAction
// Apply sorting // Apply sorting
[$sort, $sortOrder] = $this->getSortFromRequest($request); [$sort, $sortOrder] = $this->getSortFromRequest($request);
$propertyAccessor = self::getPropertyAccessor();
usort( usort(
$result, $result,
static fn(Entity\Api\FileList $a, Entity\Api\FileList $b) => self::sortRows( static fn(Entity\Api\FileList $a, Entity\Api\FileList $b) => self::sortRows(
$a, $a,
$b, $b,
$propertyAccessor,
$searchPhrase, $searchPhrase,
$sort, $sort,
$sortOrder $sortOrder
@ -353,9 +356,10 @@ final class ListAction
private static function sortRows( private static function sortRows(
Entity\Api\FileList $a, Entity\Api\FileList $a,
Entity\Api\FileList $b, Entity\Api\FileList $b,
PropertyAccessorInterface $propertyAccessor,
?string $searchPhrase = null, ?string $searchPhrase = null,
?string $sort = null, ?string $sort = null,
?string $sortOrder = Criteria::ASC string $sortOrder = Criteria::ASC
): int { ): int {
if ('special:duplicates' === $searchPhrase) { if ('special:duplicates' === $searchPhrase) {
return $a->media->id <=> $b->media->id; return $a->media->id <=> $b->media->id;
@ -366,33 +370,13 @@ final class ListAction
return $isDirComp; return $isDirComp;
} }
$sort ??= ''; if (!$sort) {
if (str_starts_with($sort, 'media_custom_fields_')) {
$property = str_replace('media_custom_fields_', '', $sort);
$aVal = $a->media->custom_fields[$property] ?? null;
$bVal = $b->media->custom_fields[$property] ?? null;
} elseif (str_starts_with($sort, 'media_')) {
$property = str_replace('media_', '', $sort);
$aVal = property_exists($a->media, $property) ? $a->media->{$property} : null;
$bVal = property_exists($b->media, $property) ? $b->media->{$property} : null;
} elseif (!empty($sort)) {
$aVal = property_exists($a, $sort) ? $a->{$sort} : null;
$bVal = property_exists($b, $sort) ? $b->{$sort} : null;
} else {
$aVal = $a->path; $aVal = $a->path;
$bVal = $b->path; $bVal = $b->path;
return (Criteria::ASC === $sortOrder) ? $aVal <=> $bVal : $bVal <=> $aVal;
} }
if (is_string($aVal)) { return self::sortByDotNotation($a, $b, $propertyAccessor, $sort, $sortOrder);
$aVal = mb_strtolower($aVal, 'UTF-8');
}
if (is_string($bVal)) {
$bVal = mb_strtolower($bVal, 'UTF-8');
}
return (Criteria::ASC === $sortOrder)
? $aVal <=> $bVal
: $bVal <=> $aVal;
} }
private static function postProcessRow( private static function postProcessRow(

View File

@ -8,6 +8,7 @@ use App\Http\ServerRequest;
use Doctrine\Common\Collections\Criteria; use Doctrine\Common\Collections\Criteria;
use Doctrine\ORM\QueryBuilder; use Doctrine\ORM\QueryBuilder;
use Symfony\Component\PropertyAccess\PropertyAccess; use Symfony\Component\PropertyAccess\PropertyAccess;
use Symfony\Component\PropertyAccess\PropertyAccessorInterface;
trait CanSortResults trait CanSortResults
{ {
@ -48,36 +49,11 @@ trait CanSortResults
return $results; return $results;
} }
$propertyAccessor = PropertyAccess::createPropertyAccessorBuilder() $propertyAccessor = self::getPropertyAccessor();
->disableExceptionOnInvalidIndex()
->disableExceptionOnInvalidPropertyPath()
->disableMagicMethods()
->getPropertyAccessor();
usort( usort(
$results, $results,
static function ( static fn(mixed $a, mixed $b) => self::sortByDotNotation($a, $b, $propertyAccessor, $sortValue, $sortOrder)
mixed $a,
mixed $b
) use (
$propertyAccessor,
$sortValue,
$sortOrder
) {
$aVal = $propertyAccessor->getValue($a, $sortValue);
$bVal = $propertyAccessor->getValue($b, $sortValue);
if (is_string($aVal)) {
$aVal = mb_strtolower($aVal, 'UTF-8');
}
if (is_string($bVal)) {
$bVal = mb_strtolower($bVal, 'UTF-8');
}
return (Criteria::ASC === $sortOrder)
? $aVal <=> $bVal
: $bVal <=> $aVal;
}
); );
return $results; return $results;
@ -94,4 +70,41 @@ trait CanSortResults
: Criteria::ASC, : Criteria::ASC,
]; ];
} }
protected static function sortByDotNotation(
mixed $a,
mixed $b,
PropertyAccessorInterface $propertyAccessor,
string $sortValue,
string $sortOrder
): int {
$aVal = $propertyAccessor->getValue($a, $sortValue);
$bVal = $propertyAccessor->getValue($b, $sortValue);
if (is_string($aVal)) {
$aVal = mb_strtolower($aVal, 'UTF-8');
}
if (is_string($bVal)) {
$bVal = mb_strtolower($bVal, 'UTF-8');
}
return (Criteria::ASC === $sortOrder)
? $aVal <=> $bVal
: $bVal <=> $aVal;
}
protected static ?PropertyAccessorInterface $propertyAccessor = null;
protected static function getPropertyAccessor(): PropertyAccessorInterface
{
if (null === self::$propertyAccessor) {
self::$propertyAccessor = PropertyAccess::createPropertyAccessorBuilder()
->disableExceptionOnInvalidIndex()
->disableExceptionOnInvalidPropertyPath()
->disableMagicMethods()
->getPropertyAccessor();
}
return self::$propertyAccessor;
}
} }