aboutsummaryrefslogtreecommitdiff
path: root/Jellyfin.Server.Implementations/Item/PeopleRepository.cs
diff options
context:
space:
mode:
Diffstat (limited to 'Jellyfin.Server.Implementations/Item/PeopleRepository.cs')
-rw-r--r--Jellyfin.Server.Implementations/Item/PeopleRepository.cs73
1 files changed, 56 insertions, 17 deletions
diff --git a/Jellyfin.Server.Implementations/Item/PeopleRepository.cs b/Jellyfin.Server.Implementations/Item/PeopleRepository.cs
index b52de5dd1..355ed6479 100644
--- a/Jellyfin.Server.Implementations/Item/PeopleRepository.cs
+++ b/Jellyfin.Server.Implementations/Item/PeopleRepository.cs
@@ -35,16 +35,22 @@ public class PeopleRepository(IDbContextFactory<JellyfinDbContext> dbProvider, I
using var context = _dbProvider.CreateDbContext();
var dbQuery = TranslateQuery(context.Peoples.AsNoTracking(), context, filter);
- // dbQuery = dbQuery.OrderBy(e => e.ListOrder);
- if (filter.Limit > 0)
+ // Include PeopleBaseItemMap
+ if (!filter.ItemId.IsEmpty())
{
- dbQuery = dbQuery.Take(filter.Limit);
+ dbQuery = dbQuery.Include(p => p.BaseItems!.Where(m => m.ItemId == filter.ItemId))
+ .OrderBy(e => e.BaseItems!.First(e => e.ItemId == filter.ItemId).ListOrder)
+ .ThenBy(e => e.PersonType)
+ .ThenBy(e => e.Name);
+ }
+ else
+ {
+ dbQuery = dbQuery.OrderBy(e => e.Name);
}
- // Include PeopleBaseItemMap
- if (!filter.ItemId.IsEmpty())
+ if (filter.Limit > 0)
{
- dbQuery = dbQuery.Include(p => p.BaseItems!.Where(m => m.ItemId == filter.ItemId));
+ dbQuery = dbQuery.Take(filter.Limit);
}
return dbQuery.AsEnumerable().Select(Map).ToArray();
@@ -68,20 +74,48 @@ public class PeopleRepository(IDbContextFactory<JellyfinDbContext> dbProvider, I
/// <inheritdoc />
public void UpdatePeople(Guid itemId, IReadOnlyList<PersonInfo> people)
{
- // TODO: yes for __SOME__ reason there can be duplicates.
- people = people.DistinctBy(e => e.Id).ToArray();
- var personids = people.Select(f => f.Id);
+ foreach (var item in people.Where(e => e.Role is null))
+ {
+ item.Role = string.Empty;
+ }
+
+ // multiple metadata providers can provide the _same_ person
+ people = people.DistinctBy(e => e.Name + "-" + e.Type).ToArray();
+ var personKeys = people.Select(e => e.Name + "-" + e.Type).ToArray();
using var context = _dbProvider.CreateDbContext();
using var transaction = context.Database.BeginTransaction();
- var existingPersons = context.Peoples.Where(p => personids.Contains(p.Id)).Select(f => f.Id).ToArray();
- context.Peoples.AddRange(people.Where(e => !existingPersons.Contains(e.Id)).Select(Map));
+ var existingPersons = context.Peoples.Select(e => new
+ {
+ item = e,
+ SelectionKey = e.Name + "-" + e.PersonType
+ })
+ .Where(p => personKeys.Contains(p.SelectionKey))
+ .Select(f => f.item)
+ .ToArray();
+
+ var toAdd = people
+ .Where(e => e.Type is not PersonKind.Artist && e.Type is not PersonKind.AlbumArtist)
+ .Where(e => !existingPersons.Any(f => f.Name == e.Name && f.PersonType == e.Type.ToString()))
+ .Select(Map);
+ context.Peoples.AddRange(toAdd);
context.SaveChanges();
- var maps = context.PeopleBaseItemMap.Where(e => e.ItemId == itemId).ToList();
+ var personsEntities = toAdd.Concat(existingPersons).ToArray();
+
+ var existingMaps = context.PeopleBaseItemMap.Include(e => e.People).Where(e => e.ItemId == itemId).ToList();
+
+ var listOrder = 0;
+
foreach (var person in people)
{
- var existingMap = maps.FirstOrDefault(e => e.PeopleId == person.Id);
+ if (person.Type == PersonKind.Artist || person.Type == PersonKind.AlbumArtist)
+ {
+ continue;
+ }
+
+ var entityPerson = personsEntities.First(e => e.Name == person.Name && e.PersonType == person.Type.ToString());
+ var existingMap = existingMaps.FirstOrDefault(e => e.People.Name == person.Name && e.People.PersonType == person.Type.ToString() && e.Role == person.Role);
if (existingMap is null)
{
context.PeopleBaseItemMap.Add(new PeopleBaseItemMap()
@@ -89,20 +123,25 @@ public class PeopleRepository(IDbContextFactory<JellyfinDbContext> dbProvider, I
Item = null!,
ItemId = itemId,
People = null!,
- PeopleId = person.Id,
- ListOrder = person.SortOrder,
+ PeopleId = entityPerson.Id,
+ ListOrder = listOrder,
SortOrder = person.SortOrder,
Role = person.Role
});
}
else
{
+ // Update the order for existing mappings
+ existingMap.ListOrder = listOrder;
+ existingMap.SortOrder = person.SortOrder;
// person mapping already exists so remove from list
- maps.Remove(existingMap);
+ existingMaps.Remove(existingMap);
}
+
+ listOrder++;
}
- context.PeopleBaseItemMap.RemoveRange(maps);
+ context.PeopleBaseItemMap.RemoveRange(existingMaps);
context.SaveChanges();
transaction.Commit();