update user data queries

This commit is contained in:
Luke Pulverenti 2016-05-11 10:36:28 -04:00
parent 66d2f25555
commit 3118196ac6
13 changed files with 199 additions and 105 deletions

View File

@ -429,7 +429,7 @@ namespace MediaBrowser.Api
if (request.IsMissing.HasValue) if (request.IsMissing.HasValue)
{ {
var val = request.IsMissing.Value; var val = request.IsMissing.Value;
items = items.Where(i => i.IsMissingSeason == val); items = items.Where(i => (i.IsMissingSeason ?? false) == val);
} }
if (request.IsVirtualUnaired.HasValue) if (request.IsVirtualUnaired.HasValue)

View File

@ -149,6 +149,12 @@ namespace MediaBrowser.Controller.Entities
} }
} }
[IgnoreDataMember]
public bool IsUnaired
{
get { return PremiereDate.HasValue && PremiereDate.Value.ToLocalTime().Date >= DateTime.Now.Date; }
}
public string OriginalTitle { get; set; } public string OriginalTitle { get; set; }
/// <summary> /// <summary>

View File

@ -1316,7 +1316,8 @@ namespace MediaBrowser.Controller.Entities
{ {
var folder = (Folder)child; var folder = (Folder)child;
folder.AddChildrenToList(result, includeLinkedChildren, true, filter); // We can only support includeLinkedChildren for the first folder, or we might end up stuck in a loop of linked items
folder.AddChildrenToList(result, false, true, filter);
} }
} }

View File

@ -210,12 +210,6 @@ namespace MediaBrowser.Controller.Entities.TV
} }
} }
[IgnoreDataMember]
public bool IsUnaired
{
get { return PremiereDate.HasValue && PremiereDate.Value.ToLocalTime().Date >= DateTime.Now.Date; }
}
[IgnoreDataMember] [IgnoreDataMember]
public bool IsVirtualUnaired public bool IsVirtualUnaired
{ {

View File

@ -54,8 +54,8 @@ namespace MediaBrowser.Controller.Entities.TV
// Genre, Rating and Stuido will all be the same // Genre, Rating and Stuido will all be the same
protected override IEnumerable<string> GetIndexByOptions() protected override IEnumerable<string> GetIndexByOptions()
{ {
return new List<string> { return new List<string> {
{"None"}, {"None"},
{"Performer"}, {"Performer"},
{"Director"}, {"Director"},
{"Year"}, {"Year"},
@ -128,22 +128,23 @@ namespace MediaBrowser.Controller.Entities.TV
return IndexNumber != null ? IndexNumber.Value.ToString("0000") : Name; return IndexNumber != null ? IndexNumber.Value.ToString("0000") : Name;
} }
[IgnoreDataMember] public override bool RequiresRefresh()
public bool IsMissingSeason
{ {
get { return LocationType == LocationType.Virtual && GetEpisodes().All(i => i.IsMissingEpisode); } var result = base.RequiresRefresh();
}
private bool GetIsUnaired() if (!result)
{ {
return GetEpisodes().All(i => i.IsUnaired); if (!IsMissingSeason.HasValue)
{
return true;
}
}
return result;
} }
[IgnoreDataMember] [IgnoreDataMember]
public bool IsUnaired public bool? IsMissingSeason { get; set; }
{
get { return GetIsUnaired(); }
}
[IgnoreDataMember] [IgnoreDataMember]
public bool IsVirtualUnaired public bool IsVirtualUnaired
@ -154,7 +155,7 @@ namespace MediaBrowser.Controller.Entities.TV
[IgnoreDataMember] [IgnoreDataMember]
public bool IsMissingOrVirtualUnaired public bool IsMissingOrVirtualUnaired
{ {
get { return LocationType == LocationType.Virtual && GetEpisodes().All(i => i.IsVirtualUnaired || i.IsMissingEpisode); } get { return (IsMissingSeason ?? false) || (LocationType == LocationType.Virtual && IsUnaired); }
} }
[IgnoreDataMember] [IgnoreDataMember]
@ -223,7 +224,7 @@ namespace MediaBrowser.Controller.Entities.TV
episodes = list.DistinctBy(i => i.Id); episodes = list.DistinctBy(i => i.Id);
} }
if (!includeMissingEpisodes) if (!includeMissingEpisodes)
{ {
episodes = episodes.Where(i => !i.IsMissingEpisode); episodes = episodes.Where(i => !i.IsMissingEpisode);
@ -238,7 +239,7 @@ namespace MediaBrowser.Controller.Entities.TV
.Cast<Episode>(); .Cast<Episode>();
} }
private IEnumerable<Episode> GetEpisodes() public IEnumerable<Episode> GetEpisodes()
{ {
var episodes = GetRecursiveChildren().OfType<Episode>(); var episodes = GetRecursiveChildren().OfType<Episode>();
var series = Series; var series = Series;

View File

@ -201,23 +201,30 @@ namespace MediaBrowser.Controller.Entities.TV
public IEnumerable<Season> GetSeasons(User user, bool includeMissingSeasons, bool includeVirtualUnaired) public IEnumerable<Season> GetSeasons(User user, bool includeMissingSeasons, bool includeVirtualUnaired)
{ {
var seriesIds = LibraryManager.GetItemIds(new InternalItemsQuery(user)
{
PresentationUniqueKey = PresentationUniqueKey,
IncludeItemTypes = new[] { typeof(Series).Name }
});
IEnumerable<Season> seasons; IEnumerable<Season> seasons;
if (seriesIds.Count > 1) if (EnablePooling())
{ {
seasons = LibraryManager.GetItemList(new InternalItemsQuery(user) var seriesIds = LibraryManager.GetItemIds(new InternalItemsQuery(user)
{ {
AncestorIds = seriesIds.Select(i => i.ToString("N")).ToArray(), PresentationUniqueKey = PresentationUniqueKey,
IncludeItemTypes = new[] { typeof(Season).Name }, IncludeItemTypes = new[] { typeof(Series).Name }
SortBy = new[] { ItemSortBy.SortName } });
}).Cast<Season>(); if (seriesIds.Count > 1)
{
seasons = LibraryManager.GetItemList(new InternalItemsQuery(user)
{
AncestorIds = seriesIds.Select(i => i.ToString("N")).ToArray(),
IncludeItemTypes = new[] { typeof(Season).Name },
SortBy = new[] { ItemSortBy.SortName }
}).Cast<Season>();
}
else
{
seasons = LibraryManager.Sort(base.GetChildren(user, true), user, new[] { ItemSortBy.SortName }, SortOrder.Ascending).OfType<Season>();
}
} }
else else
{ {
@ -232,7 +239,7 @@ namespace MediaBrowser.Controller.Entities.TV
{ {
if (!includeMissingSeasons) if (!includeMissingSeasons)
{ {
seasons = seasons.Where(i => !i.IsMissingSeason); seasons = seasons.Where(i => !(i.IsMissingSeason ?? false));
} }
if (!includeVirtualUnaired) if (!includeVirtualUnaired)
{ {
@ -338,25 +345,38 @@ namespace MediaBrowser.Controller.Entities.TV
return GetEpisodes(user, seasonNumber, config.DisplayMissingEpisodes, config.DisplayUnairedEpisodes); return GetEpisodes(user, seasonNumber, config.DisplayMissingEpisodes, config.DisplayUnairedEpisodes);
} }
private bool EnablePooling()
{
return false;
}
public IEnumerable<Episode> GetEpisodes(User user, int seasonNumber, bool includeMissingEpisodes, bool includeVirtualUnairedEpisodes) public IEnumerable<Episode> GetEpisodes(User user, int seasonNumber, bool includeMissingEpisodes, bool includeVirtualUnairedEpisodes)
{ {
var seriesIds = LibraryManager.GetItemIds(new InternalItemsQuery(user)
{
PresentationUniqueKey = PresentationUniqueKey,
IncludeItemTypes = new[] { typeof(Series).Name }
});
IEnumerable<Episode> episodes; IEnumerable<Episode> episodes;
if (seriesIds.Count > 1) if (EnablePooling())
{ {
episodes = LibraryManager.GetItemList(new InternalItemsQuery(user) var seriesIds = LibraryManager.GetItemIds(new InternalItemsQuery(user)
{ {
AncestorIds = seriesIds.Select(i => i.ToString("N")).ToArray(), PresentationUniqueKey = PresentationUniqueKey,
IncludeItemTypes = new[] { typeof(Episode).Name }, IncludeItemTypes = new[] { typeof(Series).Name }
SortBy = new[] { ItemSortBy.SortName } });
}).Cast<Episode>(); if (seriesIds.Count > 1)
{
episodes = LibraryManager.GetItemList(new InternalItemsQuery(user)
{
AncestorIds = seriesIds.Select(i => i.ToString("N")).ToArray(),
IncludeItemTypes = new[] { typeof(Episode).Name },
SortBy = new[] { ItemSortBy.SortName }
}).Cast<Episode>();
}
else
{
episodes = GetRecursiveChildren(user, i => i is Episode)
.Cast<Episode>();
}
} }
else else
{ {

View File

@ -1077,7 +1077,7 @@ namespace MediaBrowser.Controller.Entities
var e = i as Season; var e = i as Season;
if (e != null) if (e != null)
{ {
return e.IsMissingSeason == val; return (e.IsMissingSeason ?? false) == val;
} }
return true; return true;
}); });

View File

@ -29,22 +29,6 @@ namespace MediaBrowser.Controller.Library
/// <returns>Task.</returns> /// <returns>Task.</returns>
Task SaveUserData(Guid userId, IHasUserData item, UserItemData userData, UserDataSaveReason reason, CancellationToken cancellationToken); Task SaveUserData(Guid userId, IHasUserData item, UserItemData userData, UserDataSaveReason reason, CancellationToken cancellationToken);
/// <summary>
/// Gets the user data.
/// </summary>
/// <param name="userId">The user id.</param>
/// <param name="key">The key.</param>
/// <returns>Task{UserItemData}.</returns>
UserItemData GetUserData(string userId, string key);
/// <summary>
/// Gets the user data.
/// </summary>
/// <param name="userId">The user id.</param>
/// <param name="key">The key.</param>
/// <returns>Task{UserItemData}.</returns>
UserItemData GetUserData(Guid userId, string key);
UserItemData GetUserData(IHasUserData user, IHasUserData item); UserItemData GetUserData(IHasUserData user, IHasUserData item);
UserItemData GetUserData(string userId, IHasUserData item); UserItemData GetUserData(string userId, IHasUserData item);

View File

@ -7,6 +7,7 @@ using MediaBrowser.Model.Logging;
using MediaBrowser.Providers.Manager; using MediaBrowser.Providers.Manager;
using System; using System;
using System.Collections.Generic; using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks; using System.Threading.Tasks;
using CommonIO; using CommonIO;
@ -31,6 +32,13 @@ namespace MediaBrowser.Providers.TV
} }
} }
if (isFullRefresh || currentUpdateType > ItemUpdateType.None)
{
var episodes = item.GetEpisodes().ToList();
updateType |= SavePremiereDate(item, episodes);
updateType |= SaveIsMissing(item, episodes);
}
return updateType; return updateType;
} }
@ -38,5 +46,38 @@ namespace MediaBrowser.Providers.TV
{ {
ProviderUtils.MergeBaseItemData(source, target, lockedFields, replaceData, mergeMetadataSettings); ProviderUtils.MergeBaseItemData(source, target, lockedFields, replaceData, mergeMetadataSettings);
} }
private ItemUpdateType SavePremiereDate(Season item, List<Episode> episodes)
{
var dates = episodes.Where(i => i.PremiereDate.HasValue).Select(i => i.PremiereDate.Value).ToList();
DateTime? premiereDate = null;
if (dates.Count > 0)
{
premiereDate = dates.Min();
}
if (item.PremiereDate != premiereDate)
{
item.PremiereDate = premiereDate;
return ItemUpdateType.MetadataEdit;
}
return ItemUpdateType.None;
}
private ItemUpdateType SaveIsMissing(Season item, List<Episode> episodes)
{
var isMissing = item.LocationType == LocationType.Virtual && episodes.All(i => i.IsMissingEpisode);
if (item.IsMissingSeason != isMissing)
{
item.IsMissingSeason = isMissing;
return ItemUpdateType.MetadataEdit;
}
return ItemUpdateType.None;
}
} }
} }

View File

@ -617,9 +617,12 @@ namespace MediaBrowser.Server.Implementations.Dto
{ {
if (!string.IsNullOrEmpty(item.Album)) if (!string.IsNullOrEmpty(item.Album))
{ {
var parentAlbum = _libraryManager.RootFolder var parentAlbum = _libraryManager.GetItemList(new InternalItemsQuery
.GetRecursiveChildren(i => i is MusicAlbum && string.Equals(i.Name, item.Album, StringComparison.OrdinalIgnoreCase)) {
.FirstOrDefault(); IncludeItemTypes = new[] { typeof(MusicAlbum).Name },
Name = item.Album
}).FirstOrDefault();
if (parentAlbum != null) if (parentAlbum != null)
{ {

View File

@ -140,6 +140,54 @@ namespace MediaBrowser.Server.Implementations.Library
return Repository.GetAllUserData(userId); return Repository.GetAllUserData(userId);
} }
public UserItemData GetUserData(Guid userId, List<string> keys)
{
if (userId == Guid.Empty)
{
throw new ArgumentNullException("userId");
}
if (keys == null)
{
throw new ArgumentNullException("keys");
}
lock (_userData)
{
foreach (var key in keys)
{
var cacheKey = GetCacheKey(userId, key);
UserItemData value;
if (_userData.TryGetValue(cacheKey, out value))
{
return value;
}
value = Repository.GetUserData(userId, key);
if (value != null)
{
_userData[cacheKey] = value;
return value;
}
}
if (keys.Count > 0)
{
var key = keys[0];
var cacheKey = GetCacheKey(userId, key);
var userdata = new UserItemData
{
UserId = userId,
Key = key
};
_userData[cacheKey] = userdata;
return userdata;
}
return null;
}
}
/// <summary> /// <summary>
/// Gets the user data. /// Gets the user data.
/// </summary> /// </summary>
@ -166,27 +214,22 @@ namespace MediaBrowser.Server.Implementations.Library
return value; return value;
} }
value = GetUserDataFromRepository(userId, key); value = Repository.GetUserData(userId, key);
if (value == null)
{
value = new UserItemData
{
UserId = userId,
Key = key
};
}
_userData[cacheKey] = value; _userData[cacheKey] = value;
return value; return value;
} }
} }
private UserItemData GetUserDataFromRepository(Guid userId, string key)
{
var data = Repository.GetUserData(userId, key);
if (data == null)
{
data = new UserItemData
{
UserId = userId,
Key = key
};
}
return data;
}
/// <summary> /// <summary>
/// Gets the internal key. /// Gets the internal key.
/// </summary> /// </summary>
@ -200,22 +243,22 @@ namespace MediaBrowser.Server.Implementations.Library
public UserItemData GetUserData(IHasUserData user, IHasUserData item) public UserItemData GetUserData(IHasUserData user, IHasUserData item)
{ {
return GetUserData(user.Id, item.GetUserDataKeys().First()); return GetUserData(user.Id, item);
} }
public UserItemData GetUserData(string userId, IHasUserData item) public UserItemData GetUserData(string userId, IHasUserData item)
{ {
return GetUserData(userId, item.GetUserDataKeys().First()); return GetUserData(new Guid(userId), item);
} }
public UserItemData GetUserData(Guid userId, IHasUserData item) public UserItemData GetUserData(Guid userId, IHasUserData item)
{ {
return GetUserData(userId, item.GetUserDataKeys().First()); return GetUserData(userId, item.GetUserDataKeys());
} }
public UserItemDataDto GetUserDataDto(IHasUserData item, User user) public UserItemDataDto GetUserDataDto(IHasUserData item, User user)
{ {
var userData = GetUserData(user.Id, item.GetUserDataKeys().First()); var userData = GetUserData(user.Id, item);
var dto = GetUserItemDataDto(userData); var dto = GetUserItemDataDto(userData);
item.FillUserDataDtoValues(dto, userData, user); item.FillUserDataDtoValues(dto, userData, user);
@ -302,10 +345,5 @@ namespace MediaBrowser.Server.Implementations.Library
return playedToCompletion; return playedToCompletion;
} }
public UserItemData GetUserData(string userId, string key)
{
return GetUserData(new Guid(userId), key);
}
} }
} }

View File

@ -2,6 +2,7 @@
using MediaBrowser.Controller.Library; using MediaBrowser.Controller.Library;
using MediaBrowser.Model.Logging; using MediaBrowser.Model.Logging;
using System; using System;
using System.Collections.Generic;
using System.Linq; using System.Linq;
using System.Threading; using System.Threading;
using System.Threading.Tasks; using System.Threading.Tasks;
@ -34,20 +35,25 @@ namespace MediaBrowser.Server.Implementations.Library.Validators
/// <returns>Task.</returns> /// <returns>Task.</returns>
public async Task Run(IProgress<double> progress, CancellationToken cancellationToken) public async Task Run(IProgress<double> progress, CancellationToken cancellationToken)
{ {
var items = _libraryManager.GetItemList(new InternalItemsQuery var items = _libraryManager.RootFolder.GetRecursiveChildren(i => true)
{ .SelectMany(i => i.Studios)
IncludeItemTypes = new[] { typeof(Studio).Name } .DistinctNames()
.ToList();
}).ToList();
var numComplete = 0; var numComplete = 0;
var count = items.Count; var count = items.Count;
foreach (var item in items) var validIds = new List<Guid>();
foreach (var name in items)
{ {
try try
{ {
await item.RefreshMetadata(cancellationToken).ConfigureAwait(false); var itemByName = _libraryManager.GetStudio(name);
validIds.Add(itemByName.Id);
await itemByName.RefreshMetadata(cancellationToken).ConfigureAwait(false);
} }
catch (OperationCanceledException) catch (OperationCanceledException)
{ {
@ -56,7 +62,7 @@ namespace MediaBrowser.Server.Implementations.Library.Validators
} }
catch (Exception ex) catch (Exception ex)
{ {
_logger.ErrorException("Error refreshing {0}", ex, item.Name); _logger.ErrorException("Error refreshing {0}", ex, name);
} }
numComplete++; numComplete++;

View File

@ -1870,9 +1870,9 @@ namespace MediaBrowser.Server.Implementations.Persistence
using (var reader = cmd.ExecuteReader(CommandBehavior.SequentialAccess | CommandBehavior.SingleResult)) using (var reader = cmd.ExecuteReader(CommandBehavior.SequentialAccess | CommandBehavior.SingleResult))
{ {
Logger.Debug("GetItemIdsList query time: {0}ms. Query: {1}", //Logger.Debug("GetItemIdsList query time: {0}ms. Query: {1}",
Convert.ToInt32((DateTime.UtcNow - now).TotalMilliseconds), // Convert.ToInt32((DateTime.UtcNow - now).TotalMilliseconds),
cmd.CommandText); // cmd.CommandText);
while (reader.Read()) while (reader.Read())
{ {