update dynamic images

This commit is contained in:
Luke Pulverenti 2015-03-15 21:48:25 -04:00
parent 773fd72908
commit 4506d3faa1
12 changed files with 90 additions and 91 deletions

View File

@ -41,6 +41,8 @@ namespace MediaBrowser.Api
public ISessionContext SessionContext { get; set; } public ISessionContext SessionContext { get; set; }
public IAuthorizationContext AuthorizationContext { get; set; } public IAuthorizationContext AuthorizationContext { get; set; }
public IUserManager UserManager { get; set; }
public string GetHeader(string name) public string GetHeader(string name)
{ {
return Request.Headers[name]; return Request.Headers[name];
@ -73,6 +75,29 @@ namespace MediaBrowser.Api
return ResultFactory.GetOptimizedResultUsingCache(Request, cacheKey, lastDateModified, cacheDuration, factoryFn); return ResultFactory.GetOptimizedResultUsingCache(Request, cacheKey, lastDateModified, cacheDuration, factoryFn);
} }
protected void AssertCanUpdateUser(string userId)
{
var auth = AuthorizationContext.GetAuthorizationInfo(Request);
var authenticatedUser = UserManager.GetUserById(auth.UserId);
// If they're going to update the record of another user, they must be an administrator
if (!string.Equals(userId, auth.UserId, StringComparison.OrdinalIgnoreCase))
{
if (!authenticatedUser.Policy.IsAdministrator)
{
throw new SecurityException("Unauthorized access.");
}
}
else
{
if (!authenticatedUser.Policy.EnableUserPreferenceAccess)
{
throw new SecurityException("Unauthorized access.");
}
}
}
/// <summary> /// <summary>
/// To the optimized serialized result using cache. /// To the optimized serialized result using cache.
/// </summary> /// </summary>

View File

@ -56,7 +56,7 @@ namespace MediaBrowser.Api.Images
/// Class UpdateItemImageIndex /// Class UpdateItemImageIndex
/// </summary> /// </summary>
[Route("/Items/{Id}/Images/{Type}/{Index}/Index", "POST", Summary = "Updates the index for an item image")] [Route("/Items/{Id}/Images/{Type}/{Index}/Index", "POST", Summary = "Updates the index for an item image")]
[Authenticated] [Authenticated(Roles = "admin")]
public class UpdateItemImageIndex : IReturnVoid public class UpdateItemImageIndex : IReturnVoid
{ {
/// <summary> /// <summary>
@ -64,7 +64,7 @@ namespace MediaBrowser.Api.Images
/// </summary> /// </summary>
/// <value>The id.</value> /// <value>The id.</value>
[ApiMember(Name = "Id", Description = "Item Id", IsRequired = true, DataType = "string", ParameterType = "path", Verb = "GET")] [ApiMember(Name = "Id", Description = "Item Id", IsRequired = true, DataType = "string", ParameterType = "path", Verb = "GET")]
public Guid Id { get; set; } public string Id { get; set; }
/// <summary> /// <summary>
/// Gets or sets the type of the image. /// Gets or sets the type of the image.
@ -143,7 +143,7 @@ namespace MediaBrowser.Api.Images
/// </summary> /// </summary>
/// <value>The id.</value> /// <value>The id.</value>
[ApiMember(Name = "Id", Description = "User Id", IsRequired = true, DataType = "string", ParameterType = "path", Verb = "GET")] [ApiMember(Name = "Id", Description = "User Id", IsRequired = true, DataType = "string", ParameterType = "path", Verb = "GET")]
public Guid Id { get; set; } public string Id { get; set; }
} }
/// <summary> /// <summary>
@ -151,7 +151,7 @@ namespace MediaBrowser.Api.Images
/// </summary> /// </summary>
[Route("/Items/{Id}/Images/{Type}", "DELETE")] [Route("/Items/{Id}/Images/{Type}", "DELETE")]
[Route("/Items/{Id}/Images/{Type}/{Index}", "DELETE")] [Route("/Items/{Id}/Images/{Type}/{Index}", "DELETE")]
[Authenticated] [Authenticated(Roles = "admin")]
public class DeleteItemImage : DeleteImageRequest, IReturnVoid public class DeleteItemImage : DeleteImageRequest, IReturnVoid
{ {
/// <summary> /// <summary>
@ -159,7 +159,7 @@ namespace MediaBrowser.Api.Images
/// </summary> /// </summary>
/// <value>The id.</value> /// <value>The id.</value>
[ApiMember(Name = "Id", Description = "Item Id", IsRequired = true, DataType = "string", ParameterType = "path", Verb = "DELETE")] [ApiMember(Name = "Id", Description = "Item Id", IsRequired = true, DataType = "string", ParameterType = "path", Verb = "DELETE")]
public Guid Id { get; set; } public string Id { get; set; }
} }
/// <summary> /// <summary>
@ -175,7 +175,7 @@ namespace MediaBrowser.Api.Images
/// </summary> /// </summary>
/// <value>The id.</value> /// <value>The id.</value>
[ApiMember(Name = "Id", Description = "User Id", IsRequired = true, DataType = "string", ParameterType = "path", Verb = "DELETE")] [ApiMember(Name = "Id", Description = "User Id", IsRequired = true, DataType = "string", ParameterType = "path", Verb = "DELETE")]
public Guid Id { get; set; } public string Id { get; set; }
} }
/// <summary> /// <summary>
@ -191,7 +191,7 @@ namespace MediaBrowser.Api.Images
/// </summary> /// </summary>
/// <value>The id.</value> /// <value>The id.</value>
[ApiMember(Name = "Id", Description = "User Id", IsRequired = true, DataType = "string", ParameterType = "path", Verb = "POST")] [ApiMember(Name = "Id", Description = "User Id", IsRequired = true, DataType = "string", ParameterType = "path", Verb = "POST")]
public Guid Id { get; set; } public string Id { get; set; }
/// <summary> /// <summary>
/// The raw Http Request Input Stream /// The raw Http Request Input Stream
@ -206,7 +206,7 @@ namespace MediaBrowser.Api.Images
[Route("/Items/{Id}/Images/{Type}", "POST")] [Route("/Items/{Id}/Images/{Type}", "POST")]
[Route("/Items/{Id}/Images/{Type}/{Index}", "POST")] [Route("/Items/{Id}/Images/{Type}/{Index}", "POST")]
[Api(Description = "Posts an item image")] [Api(Description = "Posts an item image")]
[Authenticated] [Authenticated(Roles = "admin")]
public class PostItemImage : DeleteImageRequest, IRequiresRequestStream, IReturnVoid public class PostItemImage : DeleteImageRequest, IRequiresRequestStream, IReturnVoid
{ {
/// <summary> /// <summary>
@ -417,11 +417,12 @@ namespace MediaBrowser.Api.Images
/// <param name="request">The request.</param> /// <param name="request">The request.</param>
public void Post(PostUserImage request) public void Post(PostUserImage request)
{ {
var id = new Guid(GetPathValue(1)); var userId = GetPathValue(1);
AssertCanUpdateUser(userId);
request.Type = (ImageType)Enum.Parse(typeof(ImageType), GetPathValue(3), true); request.Type = (ImageType)Enum.Parse(typeof(ImageType), GetPathValue(3), true);
var item = _userManager.GetUserById(id); var item = _userManager.GetUserById(userId);
var task = PostImage(item, request.RequestStream, request.Type, Request.ContentType); var task = PostImage(item, request.RequestStream, request.Type, Request.ContentType);
@ -434,7 +435,7 @@ namespace MediaBrowser.Api.Images
/// <param name="request">The request.</param> /// <param name="request">The request.</param>
public void Post(PostItemImage request) public void Post(PostItemImage request)
{ {
var id = new Guid(GetPathValue(1)); var id = GetPathValue(1);
request.Type = (ImageType)Enum.Parse(typeof(ImageType), GetPathValue(3), true); request.Type = (ImageType)Enum.Parse(typeof(ImageType), GetPathValue(3), true);
@ -451,7 +452,10 @@ namespace MediaBrowser.Api.Images
/// <param name="request">The request.</param> /// <param name="request">The request.</param>
public void Delete(DeleteUserImage request) public void Delete(DeleteUserImage request)
{ {
var item = _userManager.GetUserById(request.Id); var userId = request.Id;
AssertCanUpdateUser(userId);
var item = _userManager.GetUserById(userId);
var task = item.DeleteImage(request.Type, request.Index ?? 0); var task = item.DeleteImage(request.Type, request.Index ?? 0);
@ -492,7 +496,6 @@ namespace MediaBrowser.Api.Images
/// <param name="currentIndex">Index of the current.</param> /// <param name="currentIndex">Index of the current.</param>
/// <param name="newIndex">The new index.</param> /// <param name="newIndex">The new index.</param>
/// <returns>Task.</returns> /// <returns>Task.</returns>
/// <exception cref="System.ArgumentException">The change index operation is only applicable to backdrops and screenshots</exception>
private Task UpdateItemIndex(IHasImages item, ImageType type, int currentIndex, int newIndex) private Task UpdateItemIndex(IHasImages item, ImageType type, int currentIndex, int newIndex)
{ {
return item.SwapImages(type, currentIndex, newIndex); return item.SwapImages(type, currentIndex, newIndex);

View File

@ -41,8 +41,8 @@ namespace MediaBrowser.Api
[ApiMember(Name = "ContentType", Description = "The content type of the item", IsRequired = true, DataType = "string", ParameterType = "query", Verb = "POST")] [ApiMember(Name = "ContentType", Description = "The content type of the item", IsRequired = true, DataType = "string", ParameterType = "query", Verb = "POST")]
public string ContentType { get; set; } public string ContentType { get; set; }
} }
[Authenticated] [Authenticated(Roles = "admin")]
public class ItemUpdateService : BaseApiService public class ItemUpdateService : BaseApiService
{ {
private readonly ILibraryManager _libraryManager; private readonly ILibraryManager _libraryManager;
@ -61,7 +61,7 @@ namespace MediaBrowser.Api
public object Get(GetMetadataEditorInfo request) public object Get(GetMetadataEditorInfo request)
{ {
var item = _libraryManager.GetItemById(request.ItemId); var item = _libraryManager.GetItemById(request.ItemId);
var info = new MetadataEditorInfo var info = new MetadataEditorInfo
{ {
ParentalRatingOptions = _localizationManager.GetParentalRatings().ToList(), ParentalRatingOptions = _localizationManager.GetParentalRatings().ToList(),
@ -131,7 +131,7 @@ namespace MediaBrowser.Api
Value = "" Value = ""
}); });
} }
list.Add(new NameValuePair list.Add(new NameValuePair
{ {
Name = "FolderTypeMovies", Name = "FolderTypeMovies",
@ -406,7 +406,7 @@ namespace MediaBrowser.Api
.Select(i => i.Name) .Select(i => i.Name)
.ToList(); .ToList();
} }
var song = item as Audio; var song = item as Audio;
if (song != null) if (song != null)
{ {

View File

@ -253,18 +253,14 @@ namespace MediaBrowser.Api
/// The _user manager /// The _user manager
/// </summary> /// </summary>
private readonly IUserManager _userManager; private readonly IUserManager _userManager;
private readonly IDtoService _dtoService;
private readonly ISessionManager _sessionMananger; private readonly ISessionManager _sessionMananger;
private readonly IServerConfigurationManager _config; private readonly IServerConfigurationManager _config;
private readonly INetworkManager _networkManager; private readonly INetworkManager _networkManager;
private readonly IDeviceManager _deviceManager; private readonly IDeviceManager _deviceManager;
public IAuthorizationContext AuthorizationContext { get; set; } public UserService(IUserManager userManager, ISessionManager sessionMananger, IServerConfigurationManager config, INetworkManager networkManager, IDeviceManager deviceManager)
public UserService(IUserManager userManager, IDtoService dtoService, ISessionManager sessionMananger, IServerConfigurationManager config, INetworkManager networkManager, IDeviceManager deviceManager)
{ {
_userManager = userManager; _userManager = userManager;
_dtoService = dtoService;
_sessionMananger = sessionMananger; _sessionMananger = sessionMananger;
_config = config; _config = config;
_networkManager = networkManager; _networkManager = networkManager;
@ -591,22 +587,6 @@ namespace MediaBrowser.Api
Task.WaitAll(task); Task.WaitAll(task);
} }
private void AssertCanUpdateUser(string userId)
{
var auth = AuthorizationContext.GetAuthorizationInfo(Request);
// If they're going to update the record of another user, they must be an administrator
if (!string.Equals(userId, auth.UserId, StringComparison.OrdinalIgnoreCase))
{
var authenticatedUser = _userManager.GetUserById(auth.UserId);
if (!authenticatedUser.Policy.IsAdministrator)
{
throw new SecurityException("Unauthorized access.");
}
}
}
public void Post(UpdateUserPolicy request) public void Post(UpdateUserPolicy request)
{ {
var task = UpdateUserPolicy(request); var task = UpdateUserPolicy(request);

View File

@ -25,19 +25,14 @@ namespace MediaBrowser.Model.Dlna
{ {
ValidateAudioInput(options); ValidateAudioInput(options);
List<MediaSourceInfo> mediaSources = options.MediaSources; List<MediaSourceInfo> mediaSources = new List<MediaSourceInfo>();
foreach (MediaSourceInfo i in options.MediaSources)
// If the client wants a specific media source, filter now
if (!string.IsNullOrEmpty(options.MediaSourceId))
{ {
List<MediaSourceInfo> newMediaSources = new List<MediaSourceInfo>(); if (!string.IsNullOrEmpty(options.MediaSourceId) ||
foreach (MediaSourceInfo i in mediaSources) StringHelper.EqualsIgnoreCase(i.Id, options.MediaSourceId))
{ {
if (StringHelper.EqualsIgnoreCase(i.Id, options.MediaSourceId)) mediaSources.Add(i);
newMediaSources.Add(i);
} }
mediaSources = newMediaSources;
} }
List<StreamInfo> streams = new List<StreamInfo>(); List<StreamInfo> streams = new List<StreamInfo>();
@ -63,19 +58,14 @@ namespace MediaBrowser.Model.Dlna
{ {
ValidateInput(options); ValidateInput(options);
List<MediaSourceInfo> mediaSources = options.MediaSources; List<MediaSourceInfo> mediaSources = new List<MediaSourceInfo>();
foreach (MediaSourceInfo i in options.MediaSources)
// If the client wants a specific media source, filter now
if (!string.IsNullOrEmpty(options.MediaSourceId))
{ {
List<MediaSourceInfo> newMediaSources = new List<MediaSourceInfo>(); if (!string.IsNullOrEmpty(options.MediaSourceId) ||
foreach (MediaSourceInfo i in mediaSources) StringHelper.EqualsIgnoreCase(i.Id, options.MediaSourceId))
{ {
if (StringHelper.EqualsIgnoreCase(i.Id, options.MediaSourceId)) mediaSources.Add(i);
newMediaSources.Add(i);
} }
mediaSources = newMediaSources;
} }
List<StreamInfo> streams = new List<StreamInfo>(); List<StreamInfo> streams = new List<StreamInfo>();

View File

@ -77,35 +77,35 @@ namespace MediaBrowser.Providers.FolderImages
if (string.Equals(viewType, CollectionType.Books, StringComparison.OrdinalIgnoreCase)) if (string.Equals(viewType, CollectionType.Books, StringComparison.OrdinalIgnoreCase))
{ {
return urlPrefix + "books.png"; return null;
} }
if (string.Equals(viewType, CollectionType.Games, StringComparison.OrdinalIgnoreCase)) if (string.Equals(viewType, CollectionType.Games, StringComparison.OrdinalIgnoreCase))
{ {
return urlPrefix + "games.png"; return null;
} }
if (string.Equals(viewType, CollectionType.Music, StringComparison.OrdinalIgnoreCase)) if (string.Equals(viewType, CollectionType.Music, StringComparison.OrdinalIgnoreCase))
{ {
return urlPrefix + "music.png"; return null;
} }
if (string.Equals(viewType, CollectionType.Photos, StringComparison.OrdinalIgnoreCase)) if (string.Equals(viewType, CollectionType.Photos, StringComparison.OrdinalIgnoreCase))
{ {
return urlPrefix + "photos.png"; return null;
} }
if (string.Equals(viewType, CollectionType.TvShows, StringComparison.OrdinalIgnoreCase)) if (string.Equals(viewType, CollectionType.TvShows, StringComparison.OrdinalIgnoreCase))
{ {
return urlPrefix + "tv.png"; return null;
} }
if (string.Equals(viewType, CollectionType.Channels, StringComparison.OrdinalIgnoreCase)) if (string.Equals(viewType, CollectionType.Channels, StringComparison.OrdinalIgnoreCase))
{ {
return urlPrefix + "channels.png"; return null;
} }
if (string.Equals(viewType, CollectionType.LiveTv, StringComparison.OrdinalIgnoreCase)) if (string.Equals(viewType, CollectionType.LiveTv, StringComparison.OrdinalIgnoreCase))
{ {
return urlPrefix + "livetv.png"; return null;
} }
if (string.Equals(viewType, CollectionType.Movies, StringComparison.OrdinalIgnoreCase)) if (string.Equals(viewType, CollectionType.Movies, StringComparison.OrdinalIgnoreCase))
{ {
return urlPrefix + "movies.png"; return null;
} }
if (isSubView) if (isSubView)

View File

@ -2,14 +2,13 @@
using MediaBrowser.Controller.LiveTv; using MediaBrowser.Controller.LiveTv;
using MediaBrowser.Controller.Providers; using MediaBrowser.Controller.Providers;
using MediaBrowser.Model.Providers; using MediaBrowser.Model.Providers;
using System;
using System.Collections.Generic; using System.Collections.Generic;
using System.Threading; using System.Threading;
using System.Threading.Tasks; using System.Threading.Tasks;
namespace MediaBrowser.Providers.Movies namespace MediaBrowser.Providers.Movies
{ {
public class LiveTvMovieDbProvider : IRemoteMetadataProvider<LiveTvProgram, LiveTvProgramLookupInfo>, IDisposable, IHasOrder public class LiveTvMovieDbProvider : IRemoteMetadataProvider<LiveTvProgram, LiveTvProgramLookupInfo>, IHasOrder
{ {
public Task<IEnumerable<RemoteSearchResult>> GetSearchResults(LiveTvProgramLookupInfo searchInfo, CancellationToken cancellationToken) public Task<IEnumerable<RemoteSearchResult>> GetSearchResults(LiveTvProgramLookupInfo searchInfo, CancellationToken cancellationToken)
{ {
@ -31,10 +30,6 @@ namespace MediaBrowser.Providers.Movies
return MovieDbProvider.Current.GetImageResponse(url, cancellationToken); return MovieDbProvider.Current.GetImageResponse(url, cancellationToken);
} }
public void Dispose()
{
}
public int Order public int Order
{ {
get { return 1; } get { return 1; }

View File

@ -61,9 +61,7 @@ namespace MediaBrowser.Providers.Movies
public IEnumerable<ImageType> GetSupportedImages(IHasImages item) public IEnumerable<ImageType> GetSupportedImages(IHasImages item)
{ {
var channelItem = item as ChannelVideoItem; if (item is ChannelVideoItem || item is LiveTvProgram)
if (channelItem != null)
{ {
// Too many channel items to allow backdrops here // Too many channel items to allow backdrops here
return new List<ImageType> return new List<ImageType>

View File

@ -37,7 +37,6 @@ namespace MediaBrowser.Server.Implementations.LiveTv
public class LiveTvManager : ILiveTvManager, IDisposable public class LiveTvManager : ILiveTvManager, IDisposable
{ {
private readonly IServerConfigurationManager _config; private readonly IServerConfigurationManager _config;
private readonly IFileSystem _fileSystem;
private readonly ILogger _logger; private readonly ILogger _logger;
private readonly IItemRepository _itemRepo; private readonly IItemRepository _itemRepo;
private readonly IUserManager _userManager; private readonly IUserManager _userManager;
@ -63,10 +62,9 @@ namespace MediaBrowser.Server.Implementations.LiveTv
private readonly SemaphoreSlim _refreshSemaphore = new SemaphoreSlim(1, 1); private readonly SemaphoreSlim _refreshSemaphore = new SemaphoreSlim(1, 1);
public LiveTvManager(IApplicationHost appHost, IServerConfigurationManager config, IFileSystem fileSystem, ILogger logger, IItemRepository itemRepo, IImageProcessor imageProcessor, IUserDataManager userDataManager, IDtoService dtoService, IUserManager userManager, ILibraryManager libraryManager, ITaskManager taskManager, ILocalizationManager localization, IJsonSerializer jsonSerializer, IProviderManager providerManager) public LiveTvManager(IApplicationHost appHost, IServerConfigurationManager config, ILogger logger, IItemRepository itemRepo, IImageProcessor imageProcessor, IUserDataManager userDataManager, IDtoService dtoService, IUserManager userManager, ILibraryManager libraryManager, ITaskManager taskManager, ILocalizationManager localization, IJsonSerializer jsonSerializer, IProviderManager providerManager)
{ {
_config = config; _config = config;
_fileSystem = fileSystem;
_logger = logger; _logger = logger;
_itemRepo = itemRepo; _itemRepo = itemRepo;
_userManager = userManager; _userManager = userManager;
@ -474,11 +472,11 @@ namespace MediaBrowser.Server.Implementations.LiveTv
return item; return item;
} }
private LiveTvProgram GetProgram(ProgramInfo info, ChannelType channelType, string serviceName, CancellationToken cancellationToken) private async Task<LiveTvProgram> GetProgram(ProgramInfo info, ChannelType channelType, string serviceName, CancellationToken cancellationToken)
{ {
var id = _tvDtoService.GetInternalProgramId(serviceName, info.Id); var id = _tvDtoService.GetInternalProgramId(serviceName, info.Id);
var item = _itemRepo.RetrieveItem(id) as LiveTvProgram; var item = _libraryManager.GetItemById(id) as LiveTvProgram;
if (item == null) if (item == null)
{ {
@ -521,6 +519,8 @@ namespace MediaBrowser.Server.Implementations.LiveTv
item.StartDate = info.StartDate; item.StartDate = info.StartDate;
item.ProductionYear = info.ProductionYear; item.ProductionYear = info.ProductionYear;
await item.UpdateToRepository(ItemUpdateType.MetadataImport, cancellationToken).ConfigureAwait(false);
return item; return item;
} }
@ -992,9 +992,10 @@ namespace MediaBrowser.Server.Implementations.LiveTv
var channelPrograms = await service.GetProgramsAsync(currentChannel.ExternalId, start, end, cancellationToken).ConfigureAwait(false); var channelPrograms = await service.GetProgramsAsync(currentChannel.ExternalId, start, end, cancellationToken).ConfigureAwait(false);
var programEntities = channelPrograms.Select(program => GetProgram(program, currentChannel.ChannelType, service.Name, cancellationToken)); foreach (var program in channelPrograms)
{
programs.AddRange(programEntities); programs.Add(await GetProgram(program, currentChannel.ChannelType, service.Name, cancellationToken).ConfigureAwait(false));
}
} }
catch (OperationCanceledException) catch (OperationCanceledException)
{ {

View File

@ -60,7 +60,7 @@ namespace MediaBrowser.Server.Implementations.Photos
protected async Task<ItemUpdateType> FetchAsync(IHasImages item, ImageType imageType, MetadataRefreshOptions options, CancellationToken cancellationToken) protected async Task<ItemUpdateType> FetchAsync(IHasImages item, ImageType imageType, MetadataRefreshOptions options, CancellationToken cancellationToken)
{ {
var items = await GetItemsWithImages(item).ConfigureAwait(false); var items = await GetItemsWithImages(item).ConfigureAwait(false);
var cacheKey = GetConfigurationCacheKey(items); var cacheKey = GetConfigurationCacheKey(items, item.Name);
if (!HasChanged(item, imageType, cacheKey)) if (!HasChanged(item, imageType, cacheKey))
{ {
@ -110,7 +110,7 @@ namespace MediaBrowser.Server.Implementations.Photos
public async Task<DynamicImageResponse> GetImage(IHasImages item, ImageType type, CancellationToken cancellationToken) public async Task<DynamicImageResponse> GetImage(IHasImages item, ImageType type, CancellationToken cancellationToken)
{ {
var items = await GetItemsWithImages(item).ConfigureAwait(false); var items = await GetItemsWithImages(item).ConfigureAwait(false);
var cacheKey = GetConfigurationCacheKey(items); var cacheKey = GetConfigurationCacheKey(items, item.Name);
var result = await CreateImageAsync(item, items, type, 0).ConfigureAwait(false); var result = await CreateImageAsync(item, items, type, 0).ConfigureAwait(false);
@ -126,9 +126,9 @@ namespace MediaBrowser.Server.Implementations.Photos
protected abstract Task<List<BaseItem>> GetItemsWithImages(IHasImages item); protected abstract Task<List<BaseItem>> GetItemsWithImages(IHasImages item);
private const string Version = "3"; private const string Version = "3";
protected string GetConfigurationCacheKey(List<BaseItem> items) protected string GetConfigurationCacheKey(List<BaseItem> items, string itemName)
{ {
return (Version + "_" + string.Join(",", items.Select(i => i.Id.ToString("N")).ToArray())).GetMD5().ToString("N"); return (Version + "_" + (itemName ?? string.Empty) + "_" + string.Join(",", items.Select(i => i.Id.ToString("N")).ToArray())).GetMD5().ToString("N");
} }
protected Task<Stream> GetThumbCollage(List<BaseItem> items) protected Task<Stream> GetThumbCollage(List<BaseItem> items)
@ -185,7 +185,7 @@ namespace MediaBrowser.Server.Implementations.Photos
} }
var items = GetItemsWithImages(item).Result; var items = GetItemsWithImages(item).Result;
var cacheKey = GetConfigurationCacheKey(items); var cacheKey = GetConfigurationCacheKey(items, item.Name);
return HasChanged(item, ImageType.Primary, cacheKey) || HasChanged(item, ImageType.Thumb, cacheKey); return HasChanged(item, ImageType.Primary, cacheKey) || HasChanged(item, ImageType.Thumb, cacheKey);
} }

View File

@ -227,7 +227,9 @@ namespace MediaBrowser.Server.Implementations.UserViews
CollectionType.BoxSets, CollectionType.BoxSets,
CollectionType.Playlists, CollectionType.Playlists,
CollectionType.Channels, CollectionType.Channels,
CollectionType.LiveTv CollectionType.LiveTv,
CollectionType.Books,
CollectionType.Photos
}; };
return collectionStripViewTypes.Contains(view.ViewType ?? string.Empty); return collectionStripViewTypes.Contains(view.ViewType ?? string.Empty);
@ -235,6 +237,11 @@ namespace MediaBrowser.Server.Implementations.UserViews
protected override Task<Stream> CreateImageAsync(IHasImages item, List<BaseItem> itemsWithImages, ImageType imageType, int imageIndex) protected override Task<Stream> CreateImageAsync(IHasImages item, List<BaseItem> itemsWithImages, ImageType imageType, int imageIndex)
{ {
if (itemsWithImages.Count == 0)
{
return null;
}
var view = (UserView)item; var view = (UserView)item;
if (imageType == ImageType.Primary && IsUsingCollectionStrip(view)) if (imageType == ImageType.Primary && IsUsingCollectionStrip(view))
{ {

View File

@ -495,7 +495,7 @@ namespace MediaBrowser.Server.Startup.Common
PlaylistManager = new PlaylistManager(LibraryManager, FileSystemManager, LibraryMonitor, LogManager.GetLogger("PlaylistManager"), UserManager); PlaylistManager = new PlaylistManager(LibraryManager, FileSystemManager, LibraryMonitor, LogManager.GetLogger("PlaylistManager"), UserManager);
RegisterSingleInstance<IPlaylistManager>(PlaylistManager); RegisterSingleInstance<IPlaylistManager>(PlaylistManager);
LiveTvManager = new LiveTvManager(this, ServerConfigurationManager, FileSystemManager, Logger, ItemRepository, ImageProcessor, UserDataManager, DtoService, UserManager, LibraryManager, TaskManager, LocalizationManager, JsonSerializer, ProviderManager); LiveTvManager = new LiveTvManager(this, ServerConfigurationManager, Logger, ItemRepository, ImageProcessor, UserDataManager, DtoService, UserManager, LibraryManager, TaskManager, LocalizationManager, JsonSerializer, ProviderManager);
RegisterSingleInstance(LiveTvManager); RegisterSingleInstance(LiveTvManager);
UserViewManager = new UserViewManager(LibraryManager, LocalizationManager, UserManager, ChannelManager, LiveTvManager, PlaylistManager, CollectionManager, ServerConfigurationManager); UserViewManager = new UserViewManager(LibraryManager, LocalizationManager, UserManager, ChannelManager, LiveTvManager, PlaylistManager, CollectionManager, ServerConfigurationManager);