You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
Ombi/src/Ombi.Core/Engine/MovieSearchEngine.cs

181 lines
6.6 KiB

using System;
using AutoMapper;
using Microsoft.Extensions.Logging;
7 years ago
using Ombi.Api.TheMovieDb;
using Ombi.Api.TheMovieDb.Models;
using Ombi.Core.Models.Requests;
using Ombi.Core.Models.Search;
using System.Collections.Generic;
using System.Linq;
using System.Security.Principal;
using System.Threading.Tasks;
using Ombi.Core.Rule.Interfaces;
using Microsoft.Extensions.Caching.Memory;
using Ombi.Core.Authentication;
using Ombi.Helpers;
namespace Ombi.Core.Engine
{
7 years ago
public class MovieSearchEngine : BaseMediaEngine, IMovieEngine
{
public MovieSearchEngine(IPrincipal identity, IRequestServiceMain service, IMovieDbApi movApi, IMapper mapper,
ILogger<MovieSearchEngine> logger, IRuleEvaluator r, OmbiUserManager um, IMemoryCache mem)
: base(identity, service, r, um)
{
7 years ago
MovieApi = movApi;
7 years ago
Mapper = mapper;
Logger = logger;
MemCache = mem;
}
7 years ago
7 years ago
private IMovieDbApi MovieApi { get; }
7 years ago
private IMapper Mapper { get; }
private ILogger<MovieSearchEngine> Logger { get; }
private IMemoryCache MemCache { get; }
/// <summary>
/// Lookups the imdb information.
/// </summary>
/// <param name="theMovieDbId">The movie database identifier.</param>
/// <returns></returns>
public async Task<SearchMovieViewModel> LookupImdbInformation(int theMovieDbId)
{
var movieInfo = await MovieApi.GetMovieInformationWithVideo(theMovieDbId);
var viewMovie = Mapper.Map<SearchMovieViewModel>(movieInfo);
return await ProcessSingleMovie(viewMovie, true);
}
/// <summary>
/// Searches the specified movie.
/// </summary>
/// <param name="search">The search.</param>
/// <returns></returns>
public async Task<IEnumerable<SearchMovieViewModel>> Search(string search)
{
var result = await MovieApi.SearchMovie(search);
if (result != null)
{
Logger.LogDebug("Search Result: {result}", result);
return await TransformMovieResultsToResponse(result.Take(10)); // Take 10 to stop us overloading the API
}
return null;
}
/// <summary>
/// Gets popular movies.
/// </summary>
/// <returns></returns>
public async Task<IEnumerable<SearchMovieViewModel>> PopularMovies()
{
var result = await MemCache.GetOrCreateAsync(CacheKeys.PopularMovies, async entry =>
{
entry.AbsoluteExpiration = DateTimeOffset.Now.AddHours(12);
return await MovieApi.PopularMovies();
});
if (result != null)
{
Logger.LogDebug("Search Result: {result}", result);
return await TransformMovieResultsToResponse(result.Take(10)); // Take 10 to stop us overloading the API
}
return null;
}
/// <summary>
/// Gets top rated movies.
/// </summary>
/// <returns></returns>
public async Task<IEnumerable<SearchMovieViewModel>> TopRatedMovies()
{
var result = await MemCache.GetOrCreateAsync(CacheKeys.TopRatedMovies, async entry =>
{
entry.AbsoluteExpiration = DateTimeOffset.Now.AddHours(12);
return await MovieApi.TopRated();
});
if (result != null)
{
Logger.LogDebug("Search Result: {result}", result);
return await TransformMovieResultsToResponse(result.Take(10)); // Take 10 to stop us overloading the API
}
return null;
}
/// <summary>
/// Gets upcoming movies.
/// </summary>
/// <returns></returns>
public async Task<IEnumerable<SearchMovieViewModel>> UpcomingMovies()
{
var result = await MemCache.GetOrCreateAsync(CacheKeys.UpcomingMovies, async entry =>
{
entry.AbsoluteExpiration = DateTimeOffset.Now.AddHours(12);
return await MovieApi.Upcoming();
});
if (result != null)
{
Logger.LogDebug("Search Result: {result}", result);
return await TransformMovieResultsToResponse(result.Take(10)); // Take 10 to stop us overloading the API
}
return null;
}
/// <summary>
/// Gets now playing movies.
/// </summary>
/// <returns></returns>
public async Task<IEnumerable<SearchMovieViewModel>> NowPlayingMovies()
{
var result = await MemCache.GetOrCreateAsync(CacheKeys.NowPlayingMovies, async entry =>
{
entry.AbsoluteExpiration = DateTimeOffset.Now.AddHours(12);
return await MovieApi.NowPlaying();
});
if (result != null)
{
Logger.LogDebug("Search Result: {result}", result);
return await TransformMovieResultsToResponse(result.Take(10)); // Take 10 to stop us overloading the API
}
return null;
}
private async Task<List<SearchMovieViewModel>> TransformMovieResultsToResponse(
IEnumerable<MovieSearchResult> movies)
{
var viewMovies = new List<SearchMovieViewModel>();
foreach (var movie in movies)
{
viewMovies.Add(await ProcessSingleMovie(movie));
}
7 years ago
return viewMovies;
}
private async Task<SearchMovieViewModel> ProcessSingleMovie(SearchMovieViewModel viewMovie, bool lookupExtraInfo = false)
{
if (lookupExtraInfo)
7 years ago
{
var showInfo = await MovieApi.GetMovieInformation(viewMovie.Id);
viewMovie.Id = showInfo.Id; // TheMovieDbId
viewMovie.ImdbId = showInfo.ImdbId;
7 years ago
}
// So when we run the rule to check if it's available in Plex we need the ImdbId
// But we only pass down the SearchViewModel that doesn't contain this
// So set the ImdbId to viewMovie.Id and then set it back afterwards
var oldId = viewMovie.Id;
viewMovie.TheMovieDbId = viewMovie.TheMovieDbId;
7 years ago
await RunSearchRules(viewMovie);
viewMovie.Id = oldId;
7 years ago
return viewMovie;
}
private async Task<SearchMovieViewModel> ProcessSingleMovie(MovieSearchResult movie)
7 years ago
{
var viewMovie = Mapper.Map<SearchMovieViewModel>(movie);
return await ProcessSingleMovie(viewMovie);
}
}
}