pull/1425/head
Jamie.Rees 8 years ago
parent 596008b06c
commit 5b49d03f85

@ -17,7 +17,7 @@ namespace Ombi.Api
{
private TraktClient Client { get; }
private static readonly string Encrypted = "z/56wM/oEkkCWEvSIZCrzQyUvvqmafQ3njqf0UNK5xuKbNYh5Wz8ocoG2QDa5y1DBkozLaKsGxORmAB1XUvwbnom8DVNo9gE++9GTuwxmGlLDD318PXpRmYmpKqNwFSKRZgF6ewiY9qR4t3iG0pGQwPA08FK3+H7kpOKAGJNR9RMDP9wwB6Vl4DuOiZb9/DETjzZ+/zId0ZqimrbN+PLrg==";
private static readonly string Encrypted = "134e568350f7427511e257a6534026660480cf9b93c77f7378f340603b67381d";
private readonly string _apiKey = StringCipher.Decrypt(Encrypted, "ApiKey");
public TraktApi()
{

@ -0,0 +1,16 @@
//using System.Collections.Generic;
//using System.Threading.Tasks;
//using TraktApiSharp.Enums;
//using TraktApiSharp.Objects.Get.Shows;
//using TraktApiSharp.Objects.Get.Shows.Common;
//namespace Ombi.Api.Trakt
//{
// public interface ITraktApi
// {
// Task<IEnumerable<TraktMostAnticipatedShow>> GetAnticipatedShows(int? page = default(int?), int? limitPerPage = default(int?));
// Task<IEnumerable<TraktMostWatchedShow>> GetMostWatchesShows(TraktTimePeriod period = null, int? page = default(int?), int? limitPerPage = default(int?));
// Task<IEnumerable<TraktShow>> GetPopularShows(int? page = default(int?), int? limitPerPage = default(int?));
// Task<IEnumerable<TraktTrendingShow>> GetTrendingShows(int? page = default(int?), int? limitPerPage = default(int?));
// }
//}

@ -0,0 +1,12 @@
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<TargetFramework>netstandard1.6</TargetFramework>
</PropertyGroup>
<ItemGroup>
<ProjectReference Include="..\Ombi.Api\Ombi.Api.csproj" />
<ProjectReference Include="..\Ombi.Helpers\Ombi.Helpers.csproj" />
</ItemGroup>
</Project>

@ -0,0 +1,49 @@
//using System;
//using System.Collections.Generic;
//using System.Threading.Tasks;
//using Ombi.Helpers;
//using TraktApiSharp;
//using TraktApiSharp.Enums;
//using TraktApiSharp.Objects.Get.Shows;
//using TraktApiSharp.Objects.Get.Shows.Common;
//using TraktApiSharp.Requests.Parameters;
//namespace Ombi.Api.Trakt
//{
// public class TraktApi : ITraktApi
// {
// private TraktClient Client { get; }
// private static readonly string Encrypted = "MTM0ZTU2ODM1MGY3NDI3NTExZTI1N2E2NTM0MDI2NjYwNDgwY2Y5YjkzYzc3ZjczNzhmMzQwNjAzYjY3MzgxZA==";
// private readonly string _apiKey = StringCipher.DecryptString(Encrypted, "ApiKey");
// public TraktApi()
// {
// Client = new TraktClient(_apiKey);
// }
// public async Task<IEnumerable<TraktShow>> GetPopularShows(int? page = null, int? limitPerPage = null)
// {
// var popular = await Client.Shows.GetPopularShowsAsync(new TraktExtendedInfo { Full = true }, null, page ?? 1, limitPerPage ?? 10);
// return popular.Value;
// }
// public async Task<IEnumerable<TraktTrendingShow>> GetTrendingShows(int? page = null, int? limitPerPage = null)
// {
// var trendingShowsTop10 = await Client.Shows.GetTrendingShowsAsync(new TraktExtendedInfo { Full = true }, null, page ?? 1, limitPerPage ?? 10);
// return trendingShowsTop10.Value;
// }
// public async Task<IEnumerable<TraktMostAnticipatedShow>> GetAnticipatedShows(int? page = null, int? limitPerPage = null)
// {
// var anticipatedShows = await Client.Shows.GetMostAnticipatedShowsAsync(new TraktExtendedInfo { Full = true }, null, page ?? 1, limitPerPage ?? 10);
// return anticipatedShows.Value;
// }
// public async Task<IEnumerable<TraktMostWatchedShow>> GetMostWatchesShows(TraktTimePeriod period = null, int? page = null, int? limitPerPage = null)
// {
// var anticipatedShows = await Client.Shows.GetMostWatchedShowsAsync(period ?? TraktTimePeriod.Monthly, new TraktExtendedInfo { Full = true }, null, page ?? 1, limitPerPage ?? 10);
// return anticipatedShows.Value;
// }
// }
//}

@ -20,7 +20,6 @@ namespace Ombi.Api.TvMaze
var request = new Request("search/shows", Uri, HttpMethod.Get);
request.AddQueryString("q", searchTerm);
//request.ContentHeaders.Add("Content-Type", "application/json");
request.ContentHeaders.Add(new KeyValuePair<string, string>("Content-Type","application/json"));
return await Api.Request<List<TvMazeSearch>>(request);

@ -5,76 +5,52 @@ using System.Security.Principal;
using System.Threading.Tasks;
using Ombi.Core.Claims;
using Ombi.Core.Engine.Interfaces;
using Ombi.Core.IdentityResolver;
using Ombi.Core.Models.Requests;
using Ombi.Core.Requests.Models;
using Ombi.Helpers;
using Ombi.Store.Entities;
namespace Ombi.Core.Engine
{
public abstract class BaseMediaEngine : BaseEngine
{
protected BaseMediaEngine(IPrincipal identity, IRequestService service) : base(identity)
protected BaseMediaEngine(IPrincipal identity, IRequestServiceMain requestService) : base(identity)
{
RequestService = service;
RequestService = requestService;
}
protected IRequestService RequestService { get; }
protected IRequestServiceMain RequestService { get; }
protected IRequestService<MovieRequestModel> MovieRequestService => RequestService.MovieRequestService;
protected IRequestService<TvRequestModel> TvRequestService => RequestService.TvRequestService;
private long _dbMovieCacheTime = 0;
private Dictionary<int, RequestModel> _dbMovies;
protected async Task<Dictionary<int, RequestModel>> GetRequests(RequestType type)
private long _cacheTime = 0;
private Dictionary<int, MovieRequestModel> _dbMovies;
private Dictionary<int, TvRequestModel> _dbTv;
protected async Task<Dictionary<int, MovieRequestModel>> GetMovieRequests()
{
long now = DateTime.Now.Ticks;
if (_dbMovies == null || (now - _dbMovieCacheTime) > 10000)
if (_dbMovies == null || (now - _cacheTime) > 10000)
{
var allResults = await RequestService.GetAllAsync();
allResults = allResults.Where(x => x.Type == type);
var allResults = await MovieRequestService.GetAllAsync();
var distinctResults = allResults.DistinctBy(x => x.ProviderId);
_dbMovies = distinctResults.ToDictionary(x => x.ProviderId);
_dbMovieCacheTime = now;
_cacheTime = now;
}
return _dbMovies;
}
public async Task<IEnumerable<RequestViewModel>> GetRequests()
protected async Task<Dictionary<int, TvRequestModel>> GetTvRequests()
{
var allRequests = await RequestService.GetAllAsync();
var viewModel = MapToVm(allRequests);
return viewModel;
}
protected IEnumerable<RequestViewModel> MapToVm(IEnumerable<RequestModel> model)
{
return model.Select(movie => new RequestViewModel
long now = DateTime.Now.Ticks;
if (_dbTv == null || (now - _cacheTime) > 10000)
{
ProviderId = movie.ProviderId,
Type = movie.Type,
Status = movie.Status,
ImdbId = movie.ImdbId,
Id = movie.Id,
PosterPath = movie.PosterPath,
ReleaseDate = movie.ReleaseDate,
RequestedDate = movie.RequestedDate,
Released = DateTime.Now > movie.ReleaseDate,
Approved = movie.Available || movie.Approved,
Title = movie.Title,
Overview = movie.Overview,
RequestedUsers = movie.AllUsers.ToArray(),
ReleaseYear = movie.ReleaseDate.Year.ToString(),
Available = movie.Available,
Admin = HasRole(OmbiClaims.Admin),
IssueId = movie.IssueId,
Denied = movie.Denied,
DeniedReason = movie.DeniedReason,
//Qualities = qualities.ToArray(),
//HasRootFolders = rootFolders.Any(),
//RootFolders = rootFolders.ToArray(),
//CurrentRootPath = radarr.Enabled ? GetRootPath(movie.RootFolderSelected, radarr).Result : null
}).ToList();
var allResults = await TvRequestService.GetAllAsync();
var distinctResults = allResults.DistinctBy(x => x.ProviderId);
_dbTv = distinctResults.ToDictionary(x => x.ProviderId);
_cacheTime = now;
}
return _dbTv;
}
}
}

@ -10,10 +10,9 @@ namespace Ombi.Core.Engine
{
Task<RequestEngineResult> RequestMovie(SearchMovieViewModel model);
bool ShouldAutoApprove(RequestType requestType);
Task<IEnumerable<RequestViewModel>> GetRequests();
Task<IEnumerable<RequestViewModel>> GetRequests(int count, int position);
Task<IEnumerable<RequestViewModel>> SearchRequest(string search);
Task RemoveRequest(int requestId);
Task<RequestViewModel> UpdateRequest(RequestViewModel request);
Task<IEnumerable<MovieRequestModel>> GetMovieRequests(int count, int position);
Task<IEnumerable<MovieRequestModel>> SearchMovieRequest(string search);
Task RemoveMovieRequest(int requestId);
Task<MovieRequestModel> UpdateMovieRequest(MovieRequestModel request);
}
}

@ -7,5 +7,9 @@ namespace Ombi.Core.Engine
public interface ITvSearchEngine
{
Task<IEnumerable<SearchTvShowViewModel>> Search(string searchTerm);
//Task<IEnumerable<SearchTvShowViewModel>> Popular();
//Task<IEnumerable<SearchTvShowViewModel>> Anticipated();
//Task<IEnumerable<SearchTvShowViewModel>> MostWatches();
//Task<IEnumerable<SearchTvShowViewModel>> Trending();
}
}

@ -19,7 +19,7 @@ namespace Ombi.Core.Engine
public class MovieSearchEngine : BaseMediaEngine, IMovieEngine
{
public MovieSearchEngine(IPrincipal identity, IRequestService service, IMovieDbApi movApi, IMapper mapper, ISettingsService<PlexSettings> plexSettings, ISettingsService<EmbySettings> embySettings,
public MovieSearchEngine(IPrincipal identity, IRequestServiceMain service, IMovieDbApi movApi, IMapper mapper, ISettingsService<PlexSettings> plexSettings, ISettingsService<EmbySettings> embySettings,
ILogger<MovieSearchEngine> logger)
: base(identity, service)
{
@ -46,7 +46,7 @@ namespace Ombi.Core.Engine
}
var retVal = new List<SearchMovieViewModel>();
Dictionary<int, RequestModel> dbMovies = await GetRequests(RequestType.Movie);
Dictionary<int, MovieRequestModel> dbMovies = await GetMovieRequests();
var plexSettings = await PlexSettings.GetSettingsAsync();
@ -120,7 +120,7 @@ namespace Ombi.Core.Engine
private async Task<List<SearchMovieViewModel>> TransformMovieResultsToResponse(IEnumerable<MovieSearchResult> movies)
{
var viewMovies = new List<SearchMovieViewModel>();
Dictionary<int, RequestModel> dbMovies = await GetRequests(RequestType.Movie);
Dictionary<int, MovieRequestModel> dbMovies = await GetMovieRequests();
var plexSettings = await PlexSettings.GetSettingsAsync();
var embySettings = await EmbySettings.GetSettingsAsync();
@ -134,7 +134,7 @@ namespace Ombi.Core.Engine
}
private async Task<SearchMovieViewModel> ProcessSingleMovie(SearchMovieViewModel viewMovie,
Dictionary<int, RequestModel> existingRequests, PlexSettings plexSettings, EmbySettings embySettings)
Dictionary<int, MovieRequestModel> existingRequests, PlexSettings plexSettings, EmbySettings embySettings)
{
if (plexSettings.Enable)
{
@ -176,7 +176,7 @@ namespace Ombi.Core.Engine
return viewMovie;
}
private async Task<SearchMovieViewModel> ProcessSingleMovie(MovieSearchResult movie, Dictionary<int, RequestModel> existingRequests, PlexSettings plexSettings, EmbySettings embySettings)
private async Task<SearchMovieViewModel> ProcessSingleMovie(MovieSearchResult movie, Dictionary<int, MovieRequestModel> existingRequests, PlexSettings plexSettings, EmbySettings embySettings)
{
var viewMovie = Mapper.Map<SearchMovieViewModel>(movie);
return await ProcessSingleMovie(viewMovie, existingRequests, plexSettings, embySettings);

@ -6,6 +6,7 @@ using System.Security.Principal;
using System.Threading.Tasks;
using Hangfire;
using Ombi.Api.TheMovieDb;
using Ombi.Api.TvMaze;
using Ombi.Core.Models.Requests;
using Ombi.Core.Models.Search;
using Ombi.Core.Requests.Models;
@ -18,13 +19,15 @@ namespace Ombi.Core.Engine
{
public class RequestEngine : BaseMediaEngine, IRequestEngine
{
public RequestEngine(IMovieDbApi movieApi, IRequestService requestService, IPrincipal user, INotificationService notificationService) : base(user, requestService)
public RequestEngine(IMovieDbApi movieApi, ITvMazeApi tvApi, IRequestServiceMain requestService, IPrincipal user, INotificationService notificationService) : base(user, requestService)
{
MovieApi = movieApi;
TvApi = tvApi;
NotificationService = notificationService;
}
private IMovieDbApi MovieApi { get; }
private INotificationService NotificationService { get; }
private ITvMazeApi TvApi { get; }
public async Task<RequestEngineResult> RequestMovie(SearchMovieViewModel model)
{
var movieInfo = await MovieApi.GetMovieInformation(model.Id);
@ -40,7 +43,7 @@ namespace Ombi.Core.Engine
var fullMovieName =
$"{movieInfo.Title}{(!string.IsNullOrEmpty(movieInfo.ReleaseDate) ? $" ({DateTime.Parse(movieInfo.ReleaseDate).Year})" : string.Empty)}";
var existingRequest = await RequestService.CheckRequestAsync(model.Id);
var existingRequest = await MovieRequestService.CheckRequestAsync(model.Id);
if (existingRequest != null)
{
return new RequestEngineResult
@ -78,7 +81,7 @@ namespace Ombi.Core.Engine
// });
//}
var requestModel = new RequestModel
var requestModel = new MovieRequestModel
{
ProviderId = movieInfo.Id,
Type = RequestType.Movie,
@ -130,9 +133,9 @@ namespace Ombi.Core.Engine
}
return await AddRequest(requestModel, /*settings,*/
return await AddMovieRequest(requestModel, /*settings,*/
$"{fullMovieName} has been successfully added!");
}
catch (Exception e)
{
@ -147,7 +150,7 @@ namespace Ombi.Core.Engine
NotificationType = NotificationType.ItemAddedToFaultQueue
};
BackgroundJob.Enqueue(() => NotificationService.Publish(notification).Wait());
//return Response.AsJson(new JsonResponseModel
//{
// Result = true,
@ -158,10 +161,58 @@ namespace Ombi.Core.Engine
return null;
}
public async Task<RequestEngineResult> RequestTvShow(SearchTvShowViewModel tv)
{
var showInfo = await TvApi.ShowLookupByTheTvDbId(tv.Id);
DateTime.TryParse(showInfo.premiered, out DateTime firstAir);
string fullShowName = $"{showInfo.name} ({firstAir.Year})";
// For some reason the poster path is always http
var posterPath = showInfo.image?.medium.Replace("http:", "https:");
var model = new TvRequestModel
{
Type = RequestType.TvShow,
Overview = showInfo.summary.RemoveHtml(),
PosterPath = posterPath,
Title = showInfo.name,
ReleaseDate = firstAir,
Status = showInfo.status,
RequestedDate = DateTime.UtcNow,
Approved = false,
RequestedUsers = new List<string> { Username },
Issues = IssueState.None,
ImdbId = showInfo.externals?.imdb ?? string.Empty,
TvDbId = tv.Id.ToString(),
ProviderId = tv.Id,
SeasonsNumbersRequested = tv.SeasonNumbersRequested,
RequestAll = tv.RequestAll
};
private async Task<RequestEngineResult> AddRequest(RequestModel model, string message)
var existingRequest = await TvRequestService.CheckRequestAsync(model.Id);
existingRequest?.ChildRequests.Add(model);
return null;
}
private IEnumerable<EpisodesModel> GetListDifferences(IEnumerable<EpisodesModel> existing, IEnumerable<EpisodesModel> request)
{
await RequestService.AddRequestAsync(model);
var newRequest = request
.Select(r =>
new EpisodesModel
{
SeasonNumber = r.SeasonNumber,
EpisodeNumber = r.EpisodeNumber
}).ToList();
return newRequest.Except(existing);
}
private async Task<RequestEngineResult> AddMovieRequest(MovieRequestModel model, string message)
{
await MovieRequestService.AddRequestAsync(model);
if (ShouldSendNotification(model.Type))
{
@ -196,53 +247,46 @@ namespace Ombi.Core.Engine
// await RequestLimitRepo.UpdateAsync(usersLimit);
//}
return new RequestEngineResult{RequestAdded = true};
return new RequestEngineResult { RequestAdded = true };
}
public async Task<IEnumerable<RequestViewModel>> GetRequests(int count, int position)
public async Task<IEnumerable<MovieRequestModel>> GetMovieRequests(int count, int position)
{
var allRequests = await RequestService.GetAllAsync(count, position);
var viewModel = MapToVm(allRequests);
return viewModel;
var allRequests = await MovieRequestService.GetAllAsync(count, position);
return allRequests;
}
public async Task<IEnumerable<RequestViewModel>> SearchRequest(string search)
public async Task<IEnumerable<MovieRequestModel>> SearchMovieRequest(string search)
{
var allRequests = await RequestService.GetAllAsync();
var allRequests = await MovieRequestService.GetAllAsync();
var results = allRequests.Where(x => x.Title.Contains(search, CompareOptions.IgnoreCase));
var viewModel = MapToVm(results);
return viewModel;
return results;
}
public async Task<RequestViewModel> UpdateRequest(RequestViewModel request)
public async Task<MovieRequestModel> UpdateMovieRequest(MovieRequestModel request)
{
var allRequests = await RequestService.GetAllAsync();
var allRequests = await MovieRequestService.GetAllAsync();
var results = allRequests.FirstOrDefault(x => x.Id == request.Id);
results.Approved = request.Approved;
results.Available = request.Available;
results.Denied = request.Denied;
results.DeniedReason = request.DeniedReason;
//results.AdminNote = request.AdminNote;
results.AdminNote = request.AdminNote;
results.ImdbId = request.ImdbId;
results.Episodes = request.Episodes?.ToList() ?? new List<EpisodesModel>();
results.IssueId = request.IssueId;
//results.Issues = request.Issues;
//results.OtherMessage = request.OtherMessage;
results.Issues = request.Issues;
results.OtherMessage = request.OtherMessage;
results.Overview = request.Overview;
results.PosterPath = request.PosterPath;
results.RequestedUsers = request.RequestedUsers?.ToList() ?? new List<string>();
//results.RootFolderSelected = request.RootFolderSelected;
var model = RequestService.UpdateRequest(results);
return MapToVm(new List<RequestModel>{model}).FirstOrDefault();
var model = MovieRequestService.UpdateRequest(results);
return model;
}
public async Task RemoveRequest(int requestId)
public async Task RemoveMovieRequest(int requestId)
{
await RequestService.DeleteRequestAsync(requestId);
await MovieRequestService.DeleteRequestAsync(requestId);
}
}
}

@ -3,8 +3,8 @@ using System.Linq;
using System.Security.Principal;
using System.Threading.Tasks;
using AutoMapper;
//using Ombi.Api.Trakt;
using Ombi.Api.TvMaze;
using Ombi.Api.TvMaze.Models;
using Ombi.Core.Models.Requests;
using Ombi.Core.Models.Search;
using Ombi.Core.Requests.Models;
@ -17,19 +17,22 @@ namespace Ombi.Core.Engine
public class TvSearchEngine : BaseMediaEngine, ITvSearchEngine
{
public TvSearchEngine(IPrincipal identity, IRequestService service, ITvMazeApi tvMaze, IMapper mapper, ISettingsService<PlexSettings> plexSettings, ISettingsService<EmbySettings> embySettings)
public TvSearchEngine(IPrincipal identity, IRequestServiceMain service, ITvMazeApi tvMaze, IMapper mapper, ISettingsService<PlexSettings> plexSettings,
ISettingsService<EmbySettings> embySettings/*, ITraktApi trakt*/)
: base(identity, service)
{
TvMazeApi = tvMaze;
Mapper = mapper;
PlexSettings = plexSettings;
EmbySettings = embySettings;
//TraktApi = trakt;
}
private ITvMazeApi TvMazeApi { get; }
private IMapper Mapper { get; }
private ISettingsService<PlexSettings> PlexSettings { get; }
private ISettingsService<EmbySettings> EmbySettings { get; }
//private ITraktApi TraktApi { get; }
public async Task<IEnumerable<SearchTvShowViewModel>> Search(string searchTerm)
@ -43,9 +46,31 @@ namespace Ombi.Core.Engine
return null;
}
private async Task<IEnumerable<SearchTvShowViewModel>> ProcessResults(IEnumerable<TvMazeSearch> items)
//public async Task<IEnumerable<SearchTvShowViewModel>> Popular()
//{
// var result = await TraktApi.GetPopularShows();
// return await ProcessResults(result);
//}
//public async Task<IEnumerable<SearchTvShowViewModel>> Anticipated()
//{
// var result = await TraktApi.GetAnticipatedShows();
// return await ProcessResults(result);
//}
//public async Task<IEnumerable<SearchTvShowViewModel>> MostWatches()
//{
// var result = await TraktApi.GetMostWatchesShows();
// return await ProcessResults(result);
//}
//public async Task<IEnumerable<SearchTvShowViewModel>> Trending()
//{
// var result = await TraktApi.GetTrendingShows();
// return await ProcessResults(result);
//}
private async Task<IEnumerable<SearchTvShowViewModel>> ProcessResults<T>(IEnumerable<T> items)
{
var existingRequests = await GetRequests(RequestType.TvShow);
var existingRequests = await GetTvRequests();
var plexSettings = await PlexSettings.GetSettingsAsync();
var embySettings = await EmbySettings.GetSettingsAsync();
@ -53,14 +78,14 @@ namespace Ombi.Core.Engine
var retVal = new List<SearchTvShowViewModel>();
foreach (var tvMazeSearch in items)
{
retVal.Add(ProcessResult(tvMazeSearch, existingRequests, plexSettings, embySettings));
var viewT = Mapper.Map<SearchTvShowViewModel>(tvMazeSearch);
retVal.Add(ProcessResult(viewT, existingRequests, plexSettings, embySettings));
}
return retVal;
}
private SearchTvShowViewModel ProcessResult(TvMazeSearch item, Dictionary<int, RequestModel> existingRequests, PlexSettings plexSettings, EmbySettings embySettings)
private SearchTvShowViewModel ProcessResult(SearchTvShowViewModel item, Dictionary<int, TvRequestModel> existingRequests, PlexSettings plexSettings, EmbySettings embySettings)
{
var viewT = Mapper.Map<SearchTvShowViewModel>(item);
if (embySettings.Enable)
{
//var embyShow = EmbyChecker.GetTvShow(embyCached.ToArray(), t.show.name, t.show.premiered?.Substring(0, 4), providerId);
@ -80,25 +105,25 @@ namespace Ombi.Core.Engine
//}
}
if (item.show?.externals?.thetvdb != null && !viewT.Available)
if (item.Id > 0 && item.Available)
{
var tvdbid = (int)item.show.externals.thetvdb;
var tvdbid = item.Id;
if (existingRequests.ContainsKey(tvdbid))
{
var dbt = existingRequests[tvdbid];
viewT.Requested = true;
viewT.Episodes = dbt.Episodes.ToList();
viewT.Approved = dbt.Approved;
item.Requested = true;
item.EpisodesRequested = dbt.Episodes.ToList();
item.Approved = dbt.Approved;
}
//if (sonarrCached.Select(x => x.TvdbId).Contains(tvdbid) || sickRageCache.Contains(tvdbid))
// // compare to the sonarr/sickrage db
//{
// viewT.Requested = true;
// item.Requested = true;
//}
}
return viewT;
return item;
}
}
}

@ -0,0 +1,59 @@
using System;
using System.Collections.Generic;
using System.Linq;
using Newtonsoft.Json;
using Ombi.Store.Entities;
namespace Ombi.Core.Models.Requests
{
public class BaseRequestModel : Entity
{
public BaseRequestModel()
{
RequestedUsers = new List<string>();
}
public int ProviderId { get; set; }
public string Overview { get; set; }
public string Title { get; set; }
public string PosterPath { get; set; }
public DateTime ReleaseDate { get; set; }
public RequestType Type { get; set; }
public string Status { get; set; }
public bool Approved { get; set; }
public bool Admin { get; set; }
public DateTime RequestedDate { get; set; }
public bool Available { get; set; }
public IssueState Issues { get; set; }
public string OtherMessage { get; set; }
public string AdminNote { get; set; }
public List<string> RequestedUsers { get; set; }
public int IssueId { get; set; }
public bool Denied { get; set; }
public string DeniedReason { get; set; }
[JsonIgnore]
public bool Released => DateTime.UtcNow > ReleaseDate;
[JsonIgnore]
public IEnumerable<string> AllUsers
{
get
{
var u = new List<string>();
if (RequestedUsers != null && RequestedUsers.Any())
{
u.AddRange(RequestedUsers);
}
return u;
}
}
[JsonIgnore]
public bool CanApprove => !Approved && !Available;
public bool UserHasRequested(string username)
{
return AllUsers.Any(x => x.Equals(username, StringComparison.OrdinalIgnoreCase));
}
}
}

@ -5,24 +5,24 @@ using Ombi.Store.Entities;
namespace Ombi.Core.Requests.Models
{
public interface IRequestService
public interface IRequestService<T> where T : BaseRequestModel
{
int AddRequest(RequestModel model);
Task<int> AddRequestAsync(RequestModel model);
void BatchDelete(IEnumerable<RequestModel> model);
void BatchUpdate(IEnumerable<RequestModel> model);
RequestModel CheckRequest(int providerId);
RequestModel CheckRequest(string musicId);
Task<RequestModel> CheckRequestAsync(int providerId);
Task<RequestModel> CheckRequestAsync(string musicId);
void DeleteRequest(RequestModel request);
int AddRequest(T model);
Task<int> AddRequestAsync(T model);
void BatchDelete(IEnumerable<T> model);
void BatchUpdate(IEnumerable<T> model);
T CheckRequest(int providerId);
T CheckRequest(string musicId);
Task<T> CheckRequestAsync(int providerId);
Task<T> CheckRequestAsync(string musicId);
void DeleteRequest(T request);
Task DeleteRequestAsync(int request);
Task DeleteRequestAsync(RequestModel request);
RequestModel Get(int id);
IEnumerable<RequestModel> GetAll();
Task<IEnumerable<RequestModel>> GetAllAsync();
Task<IEnumerable<RequestModel>> GetAllAsync(int count, int position);
Task<RequestModel> GetAsync(int id);
RequestModel UpdateRequest(RequestModel model);
Task DeleteRequestAsync(T request);
T Get(int id);
IEnumerable<T> GetAll();
Task<IEnumerable<T>> GetAllAsync();
Task<IEnumerable<T>> GetAllAsync(int count, int position);
Task<T> GetAsync(int id);
T UpdateRequest(T model);
}
}

@ -8,14 +8,14 @@ using Ombi.Store.Repository;
namespace Ombi.Core.Models.Requests
{
public class JsonRequestService : IRequestService
public class JsonRequestService<T> : IRequestService<T> where T:BaseRequestModel
{
public JsonRequestService(IRequestRepository repo)
{
Repo = repo;
}
private IRequestRepository Repo { get; }
public int AddRequest(RequestModel model)
public int AddRequest(T model)
{
var entity = new RequestBlobs { Type = model.Type, Content = ByteConverterHelper.ReturnBytes(model), ProviderId = model.ProviderId };
var id = Repo.Insert(entity);
@ -23,7 +23,7 @@ namespace Ombi.Core.Models.Requests
return id.Id;
}
public async Task<int> AddRequestAsync(RequestModel model)
public async Task<int> AddRequestAsync(T model)
{
var entity = new RequestBlobs { Type = model.Type, Content = ByteConverterHelper.ReturnBytes(model), ProviderId = model.ProviderId };
var id = await Repo.InsertAsync(entity).ConfigureAwait(false);
@ -31,43 +31,43 @@ namespace Ombi.Core.Models.Requests
return id.Id;
}
public RequestModel CheckRequest(int providerId)
public T CheckRequest(int providerId)
{
var blobs = Repo.GetAll();
var blob = blobs.FirstOrDefault(x => x.ProviderId == providerId); if (blob == null)
{
return null;
}
var model = ByteConverterHelper.ReturnObject<RequestModel>(blob.Content);
var model = ByteConverterHelper.ReturnObject<T>(blob.Content);
model.Id = blob.Id;
return model;
}
public async Task<RequestModel> CheckRequestAsync(int providerId)
public async Task<T> CheckRequestAsync(int providerId)
{
var blobs = await Repo.GetAllAsync().ConfigureAwait(false);
var blob = blobs.FirstOrDefault(x => x.ProviderId == providerId); if (blob == null)
{
return null;
}
var model = ByteConverterHelper.ReturnObject<RequestModel>(blob.Content);
var model = ByteConverterHelper.ReturnObject<T>(blob.Content);
model.Id = blob.Id;
return model;
}
public RequestModel CheckRequest(string musicId)
public T CheckRequest(string musicId)
{
var blobs = Repo.GetAll();
var blob = blobs.FirstOrDefault(x => x.MusicId == musicId); if (blob == null)
{
return null;
}
var model = ByteConverterHelper.ReturnObject<RequestModel>(blob.Content);
var model = ByteConverterHelper.ReturnObject<T>(blob.Content);
model.Id = blob.Id;
return model;
}
public async Task<RequestModel> CheckRequestAsync(string musicId)
public async Task<T> CheckRequestAsync(string musicId)
{
var blobs = await Repo.GetAllAsync().ConfigureAwait(false);
var blob = blobs.FirstOrDefault(x => x.MusicId == musicId);
@ -76,18 +76,18 @@ namespace Ombi.Core.Models.Requests
{
return null;
}
var model = ByteConverterHelper.ReturnObject<RequestModel>(blob.Content);
var model = ByteConverterHelper.ReturnObject<T>(blob.Content);
model.Id = blob.Id;
return model;
}
public void DeleteRequest(RequestModel request)
public void DeleteRequest(T request)
{
var blob = Repo.Get(request.Id);
Repo.Delete(blob);
}
public async Task DeleteRequestAsync(RequestModel request)
public async Task DeleteRequestAsync(T request)
{
var blob = await Repo.GetAsync(request.Id).ConfigureAwait(false);
Repo.Delete(blob);
@ -98,7 +98,7 @@ namespace Ombi.Core.Models.Requests
Repo.Delete(blob);
}
public RequestModel UpdateRequest(RequestModel model)
public T UpdateRequest(T model)
{
var b = Repo.Get(model.Id);
b.Content = ByteConverterHelper.ReturnBytes(model);
@ -107,34 +107,34 @@ namespace Ombi.Core.Models.Requests
}
public RequestModel Get(int id)
public T Get(int id)
{
var blob = Repo.Get(id);
if (blob == null)
{
return new RequestModel();
return default(T);
}
var model = ByteConverterHelper.ReturnObject<RequestModel>(blob.Content);
var model = ByteConverterHelper.ReturnObject<T>(blob.Content);
model.Id = blob.Id; // They should always be the same, but for somereason a user didn't have it in the db https://github.com/tidusjar/Ombi/issues/862#issuecomment-269743847
return model;
}
public async Task<RequestModel> GetAsync(int id)
public async Task<T> GetAsync(int id)
{
var blob = await Repo.GetAsync(id).ConfigureAwait(false);
if (blob == null)
{
return new RequestModel();
return default(T);
}
var model = ByteConverterHelper.ReturnObject<RequestModel>(blob.Content);
var model = ByteConverterHelper.ReturnObject<T>(blob.Content);
model.Id = blob.Id;
return model;
}
public IEnumerable<RequestModel> GetAll()
public IEnumerable<T> GetAll()
{
var blobs = Repo.GetAll().ToList();
var retVal = new List<RequestModel>();
var retVal = new List<T>();
foreach (var b in blobs)
{
@ -142,17 +142,17 @@ namespace Ombi.Core.Models.Requests
{
continue;
}
var model = ByteConverterHelper.ReturnObject<RequestModel>(b.Content);
var model = ByteConverterHelper.ReturnObject<T>(b.Content);
model.Id = b.Id;
retVal.Add(model);
}
return retVal;
}
public async Task<IEnumerable<RequestModel>> GetAllAsync()
public async Task<IEnumerable<T>> GetAllAsync()
{
var blobs = await Repo.GetAllAsync().ConfigureAwait(false);
var retVal = new List<RequestModel>();
var retVal = new List<T>();
foreach (var b in blobs)
{
@ -160,17 +160,17 @@ namespace Ombi.Core.Models.Requests
{
continue;
}
var model = ByteConverterHelper.ReturnObject<RequestModel>(b.Content);
var model = ByteConverterHelper.ReturnObject<T>(b.Content);
model.Id = b.Id;
retVal.Add(model);
}
return retVal;
}
public async Task<IEnumerable<RequestModel>> GetAllAsync(int count, int position)
public async Task<IEnumerable<T>> GetAllAsync(int count, int position)
{
var blobs = await Repo.GetAllAsync(count, position).ConfigureAwait(false);
var retVal = new List<RequestModel>();
var retVal = new List<T>();
foreach (var b in blobs)
{
@ -178,20 +178,20 @@ namespace Ombi.Core.Models.Requests
{
continue;
}
var model = ByteConverterHelper.ReturnObject<RequestModel>(b.Content);
var model = ByteConverterHelper.ReturnObject<T>(b.Content);
model.Id = b.Id;
retVal.Add(model);
}
return retVal;
}
public void BatchUpdate(IEnumerable<RequestModel> model)
public void BatchUpdate(IEnumerable<T> model)
{
var entities = model.Select(m => new RequestBlobs { Type = m.Type, Content = ByteConverterHelper.ReturnBytes(m), ProviderId = m.ProviderId, Id = m.Id }).ToList();
Repo.UpdateAll(entities);
}
public void BatchDelete(IEnumerable<RequestModel> model)
public void BatchDelete(IEnumerable<T> model)
{
var entities = model.Select(m => new RequestBlobs { Type = m.Type, Content = ByteConverterHelper.ReturnBytes(m), ProviderId = m.ProviderId, Id = m.Id }).ToList();
Repo.DeleteAll(entities);

@ -0,0 +1,15 @@
using System;
using System.Collections.Generic;
using System.Linq;
using Newtonsoft.Json;
using Ombi.Store.Entities;
namespace Ombi.Core.Models.Requests
{
public class MovieRequestModel : BaseRequestModel
{
public string ImdbId { get; set; }
}
}

@ -1,78 +1,8 @@
using System;
using System.Collections.Generic;
using System.Linq;
using Newtonsoft.Json;
using Ombi.Store.Entities;
namespace Ombi.Core.Models.Requests
{
public class RequestModel : Entity
{
public RequestModel()
{
RequestedUsers = new List<string>();
Episodes = new List<EpisodesModel>();
}
public int ProviderId { get; set; }
public string ImdbId { get; set; }
public string TvDbId { get; set; }
public string Overview { get; set; }
public string Title { get; set; }
public string PosterPath { get; set; }
public DateTime ReleaseDate { get; set; }
public RequestType Type { get; set; }
public string Status { get; set; }
public bool Approved { get; set; }
public DateTime RequestedDate { get; set; }
public bool Available { get; set; }
public IssueState Issues { get; set; }
public string OtherMessage { get; set; }
public string AdminNote { get; set; }
public int[] SeasonList { get; set; }
public int SeasonCount { get; set; }
public string SeasonsRequested { get; set; }
public List<string> RequestedUsers { get; set; }
public int IssueId { get; set; }
public List<EpisodesModel> Episodes { get; set; }
public bool Denied { get; set; }
public string DeniedReason { get; set; }
/// <summary>
/// For TV Shows with a custom root folder
/// </summary>
/// <value>
/// The root folder selected.
/// </value>
public int RootFolderSelected { get; set; }
[JsonIgnore]
public List<string> AllUsers
{
get
{
var u = new List<string>();
if (RequestedUsers != null && RequestedUsers.Any())
{
u.AddRange(RequestedUsers);
}
return u;
}
}
[JsonIgnore]
public bool CanApprove => !Approved && !Available;
public string ReleaseId { get; set; }
public bool UserHasRequested(string username)
{
return AllUsers.Any(x => x.Equals(username, StringComparison.OrdinalIgnoreCase));
}
}
public static class RequestTypeDisplay
{
public static string GetString(this RequestType type)

@ -0,0 +1,16 @@
using Ombi.Core.Requests.Models;
namespace Ombi.Core.Models.Requests
{
public class RequestService : IRequestServiceMain
{
public RequestService(IRequestService<TvRequestModel> tv, IRequestService<MovieRequestModel> movie)
{
TvRequestService = tv;
MovieRequestService = movie;
}
public IRequestService<TvRequestModel> TvRequestService { get; }
public IRequestService<MovieRequestModel> MovieRequestService { get; }
}
}

@ -0,0 +1,35 @@
using System.Collections.Generic;
namespace Ombi.Core.Models.Requests
{
public class TvRequestModel : BaseRequestModel
{
public TvRequestModel()
{
Episodes = new List<EpisodesModel>();
ChildRequests = new List<TvRequestModel>();
}
public string ImdbId { get; set; }
public string TvDbId { get; set; }
public bool RequestAll { get; set; }
public List<int> SeasonsNumbersRequested { get; set; }
public List<EpisodesModel> Episodes { get; set; }
/// <summary>
/// This is for TV requests, If there is more than 1 request for a show then it should be a child
/// e.g. Request 1 is for Season 1, Request 2 is for season 5. There should be two child items.
/// </summary>
public List<TvRequestModel> ChildRequests { get; set; }
public bool HasChildRequests => ChildRequests.Count > 0;
/// <summary>
/// For TV Shows with a custom root folder
/// </summary>
/// <value>
/// The root folder selected.
/// </value>
public int RootFolderSelected { get; set; }
}
}

@ -5,10 +5,6 @@ namespace Ombi.Core.Models.Search
{
public class SearchTvShowViewModel : SearchViewModel
{
public SearchTvShowViewModel()
{
Episodes = new List<EpisodesModel>();
}
public int Id { get; set; }
public string SeriesName { get; set; }
public List<string> Aliases { get; set; }
@ -27,7 +23,6 @@ namespace Ombi.Core.Models.Search
public string Rating { get; set; }
public string ImdbId { get; set; }
public int SiteRating { get; set; }
public List<EpisodesModel> Episodes { get; set; }
/// <summary>
/// This is used from the Trakt API
@ -43,5 +38,23 @@ namespace Ombi.Core.Models.Search
/// The trailer.
/// </value>
public string Homepage { get; set; }
/// <summary>
/// This is for when the users requests multiple seasons or a single season
/// </summary>
public List<int> SeasonNumbersRequested { get; set; } = new List<int>();
/// <summary>
/// If we have requested some episodes
/// </summary>
public List<EpisodesModel> EpisodesRequested { get; set; } = new List<EpisodesModel>();
/// <summary>
/// If we are requesting the entire series
/// </summary>
public bool RequestAll { get; set; }
public bool SpecificSeasonsRequested => SeasonNumbersRequested.Count > 0;
public bool SpecificEpisodesRequested => EpisodesRequested.Count > 0;
}
}

@ -17,6 +17,7 @@
<ItemGroup>
<ProjectReference Include="..\Ombi.Api.Plex\Ombi.Api.Plex.csproj" />
<ProjectReference Include="..\Ombi.Api.Trakt\Ombi.Api.Trakt.csproj" />
<ProjectReference Include="..\Ombi.Api.TvMaze\Ombi.Api.TvMaze.csproj" />
<ProjectReference Include="..\Ombi.Helpers\Ombi.Helpers.csproj" />
<ProjectReference Include="..\Ombi.Notifications\Ombi.Notifications.csproj" />

@ -0,0 +1,10 @@
using Ombi.Core.Requests.Models;
namespace Ombi.Core.Models.Requests
{
public interface IRequestServiceMain
{
IRequestService<MovieRequestModel> MovieRequestService { get; }
IRequestService<TvRequestModel> TvRequestService { get; }
}
}

@ -10,6 +10,7 @@ using Ombi.Api.Emby;
using Ombi.Api.Plex;
using Ombi.Api.Sonarr;
using Ombi.Api.TheMovieDb;
//using Ombi.Api.Trakt;
using Ombi.Api.TvMaze;
using Ombi.Core;
using Ombi.Core.Engine;
@ -57,6 +58,7 @@ namespace Ombi.DependencyInjection
services.AddTransient<IEmbyApi, EmbyApi>();
services.AddTransient<ISonarrApi, SonarrApi>();
services.AddTransient<ITvMazeApi, TvMazeApi>();
//services.AddTransient<ITraktApi, TraktApi>();
return services;
}
@ -74,7 +76,9 @@ namespace Ombi.DependencyInjection
}
public static IServiceCollection RegisterServices(this IServiceCollection services)
{
services.AddTransient<IRequestService, JsonRequestService>();
services.AddTransient<IRequestServiceMain, RequestService>();
services.AddTransient(typeof(IRequestService<>), typeof(JsonRequestService<>));
services.AddSingleton<INotificationService, NotificationService>();
return services;

@ -14,6 +14,7 @@
<ProjectReference Include="..\Ombi.Api.Emby\Ombi.Api.Emby.csproj" />
<ProjectReference Include="..\Ombi.Api.Plex\Ombi.Api.Plex.csproj" />
<ProjectReference Include="..\Ombi.Api.Sonarr\Ombi.Api.Sonarr.csproj" />
<ProjectReference Include="..\Ombi.Api.Trakt\Ombi.Api.Trakt.csproj" />
<ProjectReference Include="..\Ombi.Api.TvMaze\Ombi.Api.TvMaze.csproj" />
<ProjectReference Include="..\Ombi.Core\Ombi.Core.csproj" />
<ProjectReference Include="..\Ombi.Notifications\Ombi.Notifications.csproj" />

@ -1,8 +1,11 @@
using System.Globalization;
using System;
using System.Globalization;
using AutoMapper;
using Ombi.Api.TvMaze.Models;
using Ombi.Core.Models.Search;
using Ombi.Helpers;
//using TraktApiSharp.Objects.Get.Shows;
//using TraktApiSharp.Objects.Get.Shows.Common;
namespace Ombi.Mapping.Profiles
{
@ -23,6 +26,58 @@ namespace Ombi.Mapping.Profiles
.ForMember(dest => dest.SeriesName, opts => opts.MapFrom(src => src.show.name))
.ForMember(dest => dest.Banner, opts => opts.MapFrom(src => !string.IsNullOrEmpty(src.show.image.medium) ? src.show.image.medium.Replace("http","https") : string.Empty))
.ForMember(dest => dest.Status, opts => opts.MapFrom(src => src.show.status));
//CreateMap<TraktShow, SearchTvShowViewModel>()
// .ForMember(dest => dest.Id, opts => opts.MapFrom(src => Convert.ToInt32(src.Ids.Tvdb.ToString())))
// .ForMember(dest => dest.FirstAired, opts => opts.MapFrom(src => src.FirstAired.HasValue ? src.FirstAired.Value.ToString("yyyy-MM-ddTHH:mm:ss") : string.Empty))
// .ForMember(dest => dest.ImdbId, opts => opts.MapFrom(src => src.Ids.Imdb))
// .ForMember(dest => dest.Network, opts => opts.MapFrom(src => src.Network))
// .ForMember(dest => dest.Overview, opts => opts.MapFrom(src => src.Overview.RemoveHtml()))
// .ForMember(dest => dest.Rating, opts => opts.MapFrom(src => src.Rating.ToString()))
// .ForMember(dest => dest.Runtime, opts => opts.MapFrom(src => src.Runtime.ToString()))
// .ForMember(dest => dest.SeriesName, opts => opts.MapFrom(src => src.Title))
// .ForMember(dest => dest.Status, opts => opts.MapFrom(src => src.Status.DisplayName))
// .ForMember(dest => dest.Trailer, opts => opts.MapFrom(src => src.Trailer))
// .ForMember(dest => dest.Homepage, opts => opts.MapFrom(src => src.Homepage));
//CreateMap<TraktTrendingShow, SearchTvShowViewModel>()
// .ForMember(dest => dest.Id, opts => opts.MapFrom(src => Convert.ToInt32(src.Show.Ids.Tvdb.ToString())))
// .ForMember(dest => dest.FirstAired, opts => opts.MapFrom(src => src.Show.FirstAired.HasValue ? src.Show.FirstAired.Value.ToString("yyyy-MM-ddTHH:mm:ss") : string.Empty))
// .ForMember(dest => dest.ImdbId, opts => opts.MapFrom(src => src.Show.Ids.Imdb))
// .ForMember(dest => dest.Network, opts => opts.MapFrom(src => src.Show.Network))
// .ForMember(dest => dest.Overview, opts => opts.MapFrom(src => src.Show.Overview.RemoveHtml()))
// .ForMember(dest => dest.Rating, opts => opts.MapFrom(src => src.Show.Rating.ToString()))
// .ForMember(dest => dest.Runtime, opts => opts.MapFrom(src => src.Show.Runtime.ToString()))
// .ForMember(dest => dest.SeriesName, opts => opts.MapFrom(src => src.Show.Title))
// .ForMember(dest => dest.Status, opts => opts.MapFrom(src => src.Show.Status.DisplayName))
// .ForMember(dest => dest.Trailer, opts => opts.MapFrom(src => src.Show.Trailer))
// .ForMember(dest => dest.Homepage, opts => opts.MapFrom(src => src.Show.Homepage));
//CreateMap<TraktMostAnticipatedShow, SearchTvShowViewModel>()
// .ForMember(dest => dest.Id, opts => opts.MapFrom(src => Convert.ToInt32(src.Show.Ids.Tvdb.ToString())))
// .ForMember(dest => dest.FirstAired, opts => opts.MapFrom(src => src.Show.FirstAired.HasValue ? src.Show.FirstAired.Value.ToString("yyyy-MM-ddTHH:mm:ss") : string.Empty))
// .ForMember(dest => dest.ImdbId, opts => opts.MapFrom(src => src.Show.Ids.Imdb))
// .ForMember(dest => dest.Network, opts => opts.MapFrom(src => src.Show.Network))
// .ForMember(dest => dest.Overview, opts => opts.MapFrom(src => src.Show.Overview.RemoveHtml()))
// .ForMember(dest => dest.Rating, opts => opts.MapFrom(src => src.Show.Rating.ToString()))
// .ForMember(dest => dest.Runtime, opts => opts.MapFrom(src => src.Show.Runtime.ToString()))
// .ForMember(dest => dest.SeriesName, opts => opts.MapFrom(src => src.Show.Title))
// .ForMember(dest => dest.Status, opts => opts.MapFrom(src => src.Show.Status.DisplayName))
// .ForMember(dest => dest.Trailer, opts => opts.MapFrom(src => src.Show.Trailer))
// .ForMember(dest => dest.Homepage, opts => opts.MapFrom(src => src.Show.Homepage));
//CreateMap<TraktMostWatchedShow, SearchTvShowViewModel>()
// .ForMember(dest => dest.Id, opts => opts.MapFrom(src => Convert.ToInt32(src.Show.Ids.Tvdb.ToString())))
// .ForMember(dest => dest.FirstAired, opts => opts.MapFrom(src => src.Show.FirstAired.HasValue ? src.Show.FirstAired.Value.ToString("yyyy-MM-ddTHH:mm:ss") : string.Empty))
// .ForMember(dest => dest.ImdbId, opts => opts.MapFrom(src => src.Show.Ids.Imdb))
// .ForMember(dest => dest.Network, opts => opts.MapFrom(src => src.Show.Network))
// .ForMember(dest => dest.Overview, opts => opts.MapFrom(src => src.Show.Overview.RemoveHtml()))
// .ForMember(dest => dest.Rating, opts => opts.MapFrom(src => src.Show.Rating.ToString()))
// .ForMember(dest => dest.Runtime, opts => opts.MapFrom(src => src.Show.Runtime.ToString()))
// .ForMember(dest => dest.SeriesName, opts => opts.MapFrom(src => src.Show.Title))
// .ForMember(dest => dest.Status, opts => opts.MapFrom(src => src.Show.Status.DisplayName))
// .ForMember(dest => dest.Trailer, opts => opts.MapFrom(src => src.Show.Trailer))
// .ForMember(dest => dest.Homepage, opts => opts.MapFrom(src => src.Show.Homepage));
}
}
}

@ -56,6 +56,8 @@ Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Ombi.Tests.Core", "Ombi.Tes
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Ombi.Settings", "Ombi.Settings\Ombi.Settings.csproj", "{AE3AA23D-5B66-42AF-B44E-B9B4D8856C6F}"
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Ombi.Api.Trakt", "Ombi.Api.Trakt\Ombi.Api.Trakt.csproj", "{3880375C-1A7E-4D75-96EC-63B954C42FEA}"
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
@ -134,6 +136,10 @@ Global
{AE3AA23D-5B66-42AF-B44E-B9B4D8856C6F}.Debug|Any CPU.Build.0 = Debug|Any CPU
{AE3AA23D-5B66-42AF-B44E-B9B4D8856C6F}.Release|Any CPU.ActiveCfg = Release|Any CPU
{AE3AA23D-5B66-42AF-B44E-B9B4D8856C6F}.Release|Any CPU.Build.0 = Release|Any CPU
{3880375C-1A7E-4D75-96EC-63B954C42FEA}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{3880375C-1A7E-4D75-96EC-63B954C42FEA}.Debug|Any CPU.Build.0 = Debug|Any CPU
{3880375C-1A7E-4D75-96EC-63B954C42FEA}.Release|Any CPU.ActiveCfg = Release|Any CPU
{3880375C-1A7E-4D75-96EC-63B954C42FEA}.Release|Any CPU.Build.0 = Release|Any CPU
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
@ -151,5 +157,6 @@ Global
{72DB97D7-2D60-4B96-8C57-6C0E20E892EB} = {EA30DD15-6280-4687-B370-2956EC2E54E5}
{6EE01B17-0966-4E11-8BC1-A5318A92AB1D} = {EA30DD15-6280-4687-B370-2956EC2E54E5}
{627A27A7-8879-4851-8140-38F8F5ADD6CD} = {6F42AB98-9196-44C4-B888-D5E409F415A1}
{3880375C-1A7E-4D75-96EC-63B954C42FEA} = {9293CA11-360A-4C20-A674-B9E794431BF5}
EndGlobalSection
EndGlobal

@ -31,7 +31,7 @@ namespace Ombi.Auth
/// The expiration time for the generated tokens.
/// </summary>
/// <remarks>The default is 7 Days.</remarks>
public TimeSpan Expiration { get; set; } = TimeSpan.FromDays(7);
public TimeSpan Expiration { get; set; } = TimeSpan.FromDays(1);
/// <summary>
/// The signing key to use when generating tokens.

@ -27,9 +27,9 @@ namespace Ombi.Controllers
private IMapper Mapper { get; }
[HttpGet]
public async Task<UserDto> GetUser()
public async Task<UserViewModel> GetUser()
{
return await IdentityManager.GetUser(this.HttpContext.User.Identity.Name);
return Mapper.Map<UserViewModel>(await IdentityManager.GetUser(this.HttpContext.User.Identity.Name));
}

@ -17,17 +17,12 @@ namespace Ombi.Controllers
}
private IRequestEngine RequestEngine { get; }
[HttpGet]
public async Task<IEnumerable<RequestViewModel>> GetRequests()
[HttpGet("movie/{count:int}/{position:int}", Name = "GetRequestsByCount")]
public async Task<IEnumerable<MovieRequestModel>> GetRequests(int count, int position)
{
return await RequestEngine.GetRequests();
}
[HttpGet("{count:int}/{position:int}", Name = "GetRequestsByCount")]
public async Task<IEnumerable<RequestViewModel>> GetRequests(int count, int position)
{
return await RequestEngine.GetRequests(count, position);
return await RequestEngine.GetMovieRequests(count, position);
}
[HttpPost("movie")]
@ -36,23 +31,29 @@ namespace Ombi.Controllers
return await RequestEngine.RequestMovie(movie);
}
[HttpGet("search/{searchTerm}")]
public async Task<IEnumerable<RequestViewModel>> Search(string searchTerm)
//[HttpPost("tv")]
//public async Task<RequestEngineResult> RequestTv([FromBody]SearchTvShowViewModel tv)
//{
// return await RequestEngine.RequestMovie();
//}
[HttpGet("movie/search/{searchTerm}")]
public async Task<IEnumerable<MovieRequestModel>> Search(string searchTerm)
{
return await RequestEngine.SearchRequest(searchTerm);
return await RequestEngine.SearchMovieRequest(searchTerm);
}
[HttpDelete("{requestId:int}")]
[HttpDelete("movie/{requestId:int}")]
public async Task DeleteRequest(int requestId)
{
await RequestEngine.RemoveRequest(requestId);
await RequestEngine.RemoveMovieRequest(requestId);
}
[HttpPost]
public async Task<RequestViewModel> UpdateRequest([FromBody]RequestViewModel model)
[HttpPut("movie")]
public async Task<MovieRequestModel> UpdateRequest([FromBody]MovieRequestModel model)
{
return await RequestEngine.UpdateRequest(model);
return await RequestEngine.UpdateMovieRequest(model);
}
}
}

@ -64,5 +64,26 @@ namespace Ombi.Controllers
{
return await TvEngine.Search(searchTerm);
}
//[HttpGet("tv/popular")]
//public async Task<IEnumerable<SearchTvShowViewModel>> PopularTv()
//{
// return await TvEngine.Popular();
//}
//[HttpGet("tv/anticiplated")]
//public async Task<IEnumerable<SearchTvShowViewModel>> AnticiplatedTv()
//{
// return await TvEngine.Anticipated();
//}
//[HttpGet("tv/mostwatched")]
//public async Task<IEnumerable<SearchTvShowViewModel>> MostWatched()
//{
// return await TvEngine.MostWatches();
//}
//[HttpGet("tv/trending")]
//public async Task<IEnumerable<SearchTvShowViewModel>> Trending()
//{
// return await TvEngine.Trending();
//}
}
}

@ -16,7 +16,7 @@
"@angular/router": "^4.1.0",
"@types/jquery": "^2.0.33",
"@types/systemjs": "^0.20.2",
"angular2-jwt": "0.2.0",
"angular2-jwt": "^0.2.0",
"angular2-moment": "^1.3.3",
"bootstrap": "3.3.6",
"core-js": "^2.4.1",

@ -9,10 +9,11 @@
<span class="icon-bar"></span>
<span class="icon-bar"></span>
</button>
<div *ngIf="customizationSettings.applicationName; then aplicationNameBlock; else ombiBlock"></div>
<ng-template #aplicationNameBlock><a class="navbar-brand" [routerLink]="['/']">{{customizationSettings.applicationName}}</a></ng-template>
<ng-template #ombiBlock><a class="navbar-brand" [routerLink]="['/']">Ombi</a></ng-template>
<div *ngIf="customizationSettings">
<div *ngIf="customizationSettings.applicationName; then aplicationNameBlock; else ombiBlock"></div>
<ng-template #aplicationNameBlock><a class="navbar-brand" [routerLink]="['/']">{{customizationSettings.applicationName}}</a></ng-template>
<ng-template #ombiBlock><a class="navbar-brand" [routerLink]="['/']">Ombi</a></ng-template>
</div>
</div>
@ -26,7 +27,7 @@
<ul class="nav navbar-nav navbar-right">
<li [routerLinkActive]="['active']"><a [routerLink]="['/Settings/Ombi']"><i class="fa fa-cog"></i> Settings</a></li>
<li *ngIf="isAdmin" [routerLinkActive]="['active']"><a [routerLink]="['/Settings/Ombi']"><i class="fa fa-cog"></i> Settings</a></li>
<li [routerLinkActive]="['active']" class="dropdown">
<a href="#" class="dropdown-toggle" data-toggle="dropdown" role="button" aria-expanded="false"><i class="fa fa-user"></i> Welcome {{username}} <span class="caret"></span></a>
<ul class="dropdown-menu" role="menu">

@ -3,6 +3,7 @@ import { Router } from '@angular/router';
import { NotificationService } from './services/notification.service';
import { SettingsService } from './services/settings.service';
import { AuthService } from './auth/auth.service';
import { IdentityService } from './services/identity.service';
import { ICustomizationSettings } from './interfaces/ISettings';
@ -13,7 +14,8 @@ import { ICustomizationSettings } from './interfaces/ISettings';
})
export class AppComponent implements OnInit {
constructor(public notificationService: NotificationService, public authService: AuthService, private router: Router, private settingsService : SettingsService) {
constructor(public notificationService: NotificationService, public authService: AuthService, private router: Router, private settingsService: SettingsService
, private identityService: IdentityService) {
}
customizationSettings: ICustomizationSettings;
@ -26,7 +28,8 @@ export class AppComponent implements OnInit {
this.showNav = this.authService.loggedIn();
});
this.isAdmin = this.identityService.hasRole("Admin");
this.isPowerUser = this.identityService.hasRole("PowerUser");
}
@ -36,5 +39,7 @@ export class AppComponent implements OnInit {
}
username:string;
showNav :boolean;
showNav: boolean;
isAdmin: boolean;
isPowerUser:boolean;
}

@ -3,7 +3,11 @@ import { Http, RequestOptions } from '@angular/http';
import { AuthHttp, AuthConfig } from 'angular2-jwt';
export function authHttpServiceFactory(http: Http, options: RequestOptions) {
return new AuthHttp(new AuthConfig(), http, options);
return new AuthHttp(new AuthConfig({
tokenName: 'id_token',
tokenGetter: (() => localStorage.getItem('id_token')),
globalHeaders: [{ 'Content-Type': 'application/json' }],
}), http, options);
}
@NgModule({

@ -23,7 +23,7 @@ export class AuthService extends ServiceHelpers {
}
loggedIn() {
return tokenNotExpired();
return tokenNotExpired('id_token');
}
logout() {

@ -1,24 +1,41 @@
export interface IRequestModel {
import { IEpisodeModel }from "./ISearchTvResult";
export interface IMediaBase {
id: number,
providerId: number,
imdbId: string,
overview: string,
title: string,
overview: string,
posterPath: string,
releaseDate: Date,
released: boolean,
type: RequestType,
status: string,
approved: boolean,
requestedUsers: string[],
requestedDate: Date,
releaseYear: string,
approved: boolean,
type: RequestType,
requested: boolean,
available: boolean,
otherMessage: string,
adminNote: string,
requestedUser: string[],
issueId: number,
denied: boolean,
deniedReason: string,
released:boolean
}
export interface IMovieRequestModel extends IMediaBase {
imdbId: string,
}
export interface ITvRequestModel extends IMediaBase {
imdbId: string,
tvDbId: string,
requestAll: boolean,
seasonNumbersRequested: number[],
episodes: IEpisodeModel[],
childRequests: ITvRequestModel[],
hasChildRequests: boolean,
rootFolderSelected: number,
firstAired:string,
}
export enum RequestType {

@ -19,7 +19,14 @@
siteRating: number,
trailer: string,
homepage:string,
episodes:IEpisodeModel[],
episodesRequested: IEpisodeModel[],
seasonNumbersRequested: number[],
requestAll:boolean,
approved: boolean,
requested: boolean,
available: boolean,
plexUrl: string,
}
export interface IEpisodeModel {

@ -3,6 +3,7 @@ import { Router } from '@angular/router';
import { AuthService } from '../auth/auth.service';
import { StatusService } from '../services/status.service';
import { IdentityService } from '../services/identity.service';
import { NotificationService } from '../services/notification.service';
@Component({
@ -11,7 +12,7 @@ import { NotificationService } from '../services/notification.service';
templateUrl: './login.component.html',
})
export class LoginComponent {
constructor(private authService: AuthService, private router: Router, private notify: NotificationService, private status: StatusService) {
constructor(private authService: AuthService, private router: Router, private notify: NotificationService, private status: StatusService, private identityService: IdentityService) {
this.status.getWizardStatus().subscribe(x => {
if (!x.result) {
this.router.navigate(['Wizard']);
@ -29,12 +30,19 @@ export class LoginComponent {
.subscribe(x => {
localStorage.setItem("id_token", x.access_token);
localStorage.setItem('currentUser', this.username);
this.identityService.getUser().subscribe(r => {
localStorage.setItem("roles", JSON.stringify(r.claims));
localStorage.setItem("user", JSON.stringify(r));
if (this.authService.loggedIn()) {
this.router.navigate(['search']);
} else {
this.notify.error("Could not log in", "Incorrect username or password");
}
}
});
}, err => this.notify.error("Could not log in", "Incorrect username or password"));

@ -13,7 +13,7 @@
(scrolled)="loadMore()">
<div *ngFor="let request of requests">
<div *ngFor="let request of movieRequests">
<div class="row">
@ -62,7 +62,7 @@
{{/if}}
{{/if_eq}}-->
<div *ngIf="request.requestedUsers">Requested By: {{request.requestedUsers}}</div>
<div *ngIf="request.requestedUsers">Requested By: <span *ngFor="let user of request.requestedUsers">{{user}} </span></div>
<div>Requested Date: {{request.requestedDate | date}}</div>
<!--{{#if admin}}
@ -79,7 +79,7 @@
</div>-->
</div>
<div class="col-sm-3 col-sm-push-3">
<div *ngIf="request.admin">
<div *ngIf="isAdmin">
<div *ngIf="!request.approved">
<form>
<input name="requestId" type="text" value="{{request.requestId}}" hidden="hidden" />

@ -10,8 +10,9 @@ import 'rxjs/add/operator/distinctUntilChanged';
import 'rxjs/add/operator/map';
import { RequestService } from '../services/request.service';
import { IdentityService } from '../services/identity.service';
import { IRequestModel } from '../interfaces/IRequestModel';
import { IMovieRequestModel, ITvRequestModel } from '../interfaces/IRequestModel';
@Component({
selector: 'ombi',
@ -19,7 +20,7 @@ import { IRequestModel } from '../interfaces/IRequestModel';
templateUrl: './request.component.html'
})
export class RequestComponent implements OnInit {
constructor(private requestService: RequestService) {
constructor(private requestService: RequestService, private identityService: IdentityService) {
this.searchChanged
.debounceTime(600) // Wait Xms afterthe last event before emitting last event
.distinctUntilChanged() // only emit if value is different from previous value
@ -29,15 +30,18 @@ export class RequestComponent implements OnInit {
this.resetSearch();
return;
}
this.requestService.searchRequests(this.searchText).subscribe(x => this.requests = x);
this.requestService.searchRequests(this.searchText).subscribe(x => this.movieRequests = x);
});
}
requests: IRequestModel[];
movieRequests: IMovieRequestModel[];
tvRequests: ITvRequestModel[];
searchChanged: Subject<string> = new Subject<string>();
searchText: string;
isAdmin : boolean;
private currentlyLoaded: number;
private amountToLoad : number;
@ -47,9 +51,11 @@ export class RequestComponent implements OnInit {
this.loadInit();
}
loadMore() {
this.requestService.getRequests(this.amountToLoad, this.currentlyLoaded + 1).subscribe(x => {
this.requests.push.apply(this.requests, x);
this.movieRequests.push.apply(this.movieRequests, x);
this.currentlyLoaded = this.currentlyLoaded + this.amountToLoad;
});
}
@ -58,35 +64,36 @@ export class RequestComponent implements OnInit {
this.searchChanged.next(text.target.value);
}
removeRequest(request: IRequestModel) {
this.requestService.removeRequest(request).subscribe();
removeRequest(request: IMovieRequestModel) {
this.requestService.removeMovieRequest(request);
this.removeRequestFromUi(request);
}
changeAvailability(request: IRequestModel, available: boolean) {
changeAvailability(request: IMovieRequestModel, available: boolean) {
request.available = available;
this.updateRequest(request);
}
approve(request: IRequestModel) {
approve(request: IMovieRequestModel) {
request.approved = true;
request.denied = false;
this.updateRequest(request);
}
deny(request: IRequestModel) {
deny(request: IMovieRequestModel) {
request.approved = false;
request.denied = true;
this.updateRequest(request);
}
private updateRequest(request: IRequestModel) {
private updateRequest(request: IMovieRequestModel) {
this.requestService.updateRequest(request).subscribe(x => request = x);
}
private loadInit() {
this.requestService.getRequests(this.amountToLoad, 0).subscribe(x => this.requests = x);
this.requestService.getRequests(this.amountToLoad, 0).subscribe(x => this.movieRequests = x);
this.isAdmin = this.identityService.hasRole("Admin");
}
private resetSearch() {
@ -94,10 +101,10 @@ export class RequestComponent implements OnInit {
this.loadInit();
}
private removeRequestFromUi(key : IRequestModel) {
var index = this.requests.indexOf(key, 0);
private removeRequestFromUi(key: IMovieRequestModel) {
var index = this.movieRequests.indexOf(key, 0);
if (index > -1) {
this.requests.splice(index, 1);
this.movieRequests.splice(index, 1);
}
}
}

@ -7,7 +7,7 @@
<ul id="nav-tabs" class="nav nav-tabs" role="tablist">
<li role="presentation" class="active">
<a id="movieTabButton" href="#MoviesTab" aria-controls="home" role="tab" data-toggle="tab" (click)="selectTab('movies')"><i class="fa fa-film"></i> Movies</a>
<a id="movieTabButton" href="#MoviesTab" aria-controls="home" role="tab" data-toggle="tab" (click)="selectTab()"><i class="fa fa-film"></i> Movies</a>
</li>
<!--<li role="presentation">
@ -16,7 +16,7 @@
</li>-->
<li role="presentation">
<a id="tvTabButton" href="#TvShowTab" aria-controls="profile" role="tab" data-toggle="tab" (click)="selectTab('tv')"><i class="fa fa-television"></i> TV Shows</a>
<a id="tvTabButton" href="#TvShowTab" aria-controls="profile" role="tab" data-toggle="tab" (click)="selectTab()"><i class="fa fa-television"></i> TV Shows</a>
</li>
<!--
@ -29,7 +29,7 @@
<!-- Tab panes -->
<div class="tab-content">
<div *ngIf="showMovie">
<div [hidden]="!showMovie">
<movie-search></movie-search>
</div>
@ -52,7 +52,7 @@
</div>-->
<div *ngIf="showTv">
<div [hidden]="!showTv">
<tv-search></tv-search>
</div>

@ -1,131 +1,23 @@
import { Component, OnInit } from '@angular/core';
import { Subject } from 'rxjs/Subject';
import 'rxjs/add/operator/debounceTime';
import 'rxjs/add/operator/distinctUntilChanged';
import 'rxjs/add/operator/map';
import { SearchService } from '../services/search.service';
import { RequestService } from '../services/request.service';
import { NotificationService } from '../services/notification.service';
import { ISearchMovieResult } from '../interfaces/ISearchMovieResult';
import { IRequestEngineResult } from '../interfaces/IRequestEngineResult';
@Component({
selector: 'ombi',
moduleId: module.id,
templateUrl: './search.component.html',
})
export class SearchComponent implements OnInit {
searchText: string;
searchChanged: Subject<string> = new Subject<string>();
movieResults: ISearchMovieResult[];
result: IRequestEngineResult;
tabSelected: string;
showTv: boolean;
showMovie:boolean;
constructor(private searchService: SearchService, private requestService: RequestService, private notificationService : NotificationService) {
this.searchChanged
.debounceTime(600) // Wait Xms afterthe last event before emitting last event
.distinctUntilChanged() // only emit if value is different from previous value
.subscribe(x => {
this.searchText = x as string;
if (this.searchText === "") {
this.clearResults();
return;
}
this.searchService.searchMovie(this.searchText).subscribe(x => {
this.movieResults = x;
// Now let's load some exta info including IMDBId
// This way the search is fast at displaying results.
this.getExtaInfo();
});
});
}
export class SearchComponent implements OnInit {
ngOnInit(): void {
this.selectTab("movies");
this.searchText = "";
this.movieResults = [];
this.result = {
message: "",
requestAdded:false
}
this.showMovie = true;
this.showTv = false;
}
showTv : boolean;
showMovie: boolean;
search(text: any) {
this.searchChanged.next(text.target.value);
}
request(searchResult: ISearchMovieResult) {
searchResult.requested = true;
this.requestService.requestMovie(searchResult).subscribe(x => {
this.result = x;
if (this.result.requestAdded) {
this.notificationService.success("Request Added",
`Request for ${searchResult.title} has been added successfully`);
} else {
this.notificationService.warning("Request Added", this.result.message);
}
});
}
selectTab(tabName: string) {
console.log(tabName);
this.tabSelected = tabName;
if (tabName === 'movies') {
this.showMovie = true;
this.showTv = false;
} else {
this.showMovie = false;
this.showTv = true;
}
}
popularMovies() {
this.clearResults();
this.searchService.popularMovies().subscribe(x => {
this.movieResults = x;
this.getExtaInfo();
});
}
nowPlayingMovies() {
this.clearResults();
this.searchService.nowPlayingMovies().subscribe(x => {
this.movieResults = x;
this.getExtaInfo();
});
}
topRatedMovies() {
this.clearResults();
this.searchService.topRatedMovies().subscribe(x => {
this.movieResults = x;
this.getExtaInfo();
});
}
upcomingMovies() {
this.clearResults();
this.searchService.upcomignMovies().subscribe(x => {
this.movieResults = x;
this.getExtaInfo();
});
}
private getExtaInfo() {
this.searchService.extraInfo(this.movieResults).subscribe(m => this.movieResults = m);
}
private clearResults() {
this.movieResults = [];
selectTab() {
this.showMovie = !this.showMovie;
this.showTv = !this.showTv;
}
}

@ -9,10 +9,10 @@
<i class="fa fa-chevron-down"></i>
</a>
<ul class="dropdown-menu">
<li><a id="popularShows">Popular Shows</a></li>
<li><a id="trendingShows">Trending Shows</a></li>
<li><a id="mostWatchedShows">Most Watched Shows</a></li>
<li><a id="anticipatedShows">Most Anticipated Shows</a></li>
<li><a (click)="popularShows()">Popular Shows</a></li>
<li><a (click)="trendingShows()">Trending Shows</a></li>
<li><a (click)="mostWatchedShows()">Most Watched Shows</a></li>
<li><a (click)="anticipatedShows()">Most Anticipated Shows</a></li>
</ul>
</div><i id="tvSearchButton" class="fa fa-search"></i>
</div>

@ -5,8 +5,8 @@ import 'rxjs/add/operator/distinctUntilChanged';
import 'rxjs/add/operator/map';
import { SearchService } from '../services/search.service';
//import { RequestService } from '../services/request.service';
//import { NotificationService } from '../services/notification.service';
import { RequestService } from '../services/request.service';
import { NotificationService } from '../services/notification.service';
import { ISearchTvResult } from '../interfaces/ISearchTvResult';
import { IRequestEngineResult } from '../interfaces/IRequestEngineResult';
@ -19,11 +19,11 @@ import { IRequestEngineResult } from '../interfaces/IRequestEngineResult';
export class TvSearchComponent implements OnInit {
searchText: string;
searchChanged: Subject<string> = new Subject<string>();
searchChanged = new Subject<string>();
tvResults: ISearchTvResult[];
result: IRequestEngineResult;
constructor(private searchService: SearchService/*, private requestService: RequestService, private notificationService: NotificationService*/) {
constructor(private searchService: SearchService, private requestService: RequestService, private notificationService: NotificationService) {
this.searchChanged
.debounceTime(600) // Wait Xms afterthe last event before emitting last event
.distinctUntilChanged() // only emit if value is different from previous value
@ -52,6 +52,48 @@ export class TvSearchComponent implements OnInit {
this.searchChanged.next(text.target.value);
}
popularShows() {
this.clearResults();
this.searchService.popularTv().subscribe(x => {
this.tvResults = x;
});
}
trendingShows() {
this.clearResults();
this.searchService.trendingTv().subscribe(x => {
this.tvResults = x;
});
}
mostWatchedShows() {
this.clearResults();
this.searchService.mostWatchedTv().subscribe(x => {
this.tvResults = x;
});
}
anticipatedShows() {
this.clearResults();
this.searchService.anticiplatedTv().subscribe(x => {
this.tvResults = x;
});
}
request(searchResult: ISearchTvResult) {
searchResult.requested = true;
this.requestService.requestTv(searchResult).subscribe(x => {
this.result = x;
if (this.result.requestAdded) {
this.notificationService.success("Request Added",
`Request for ${searchResult.seriesName} has been added successfully`);
} else {
this.notificationService.warning("Request Added", this.result.message);
}
});
}
private clearResults() {

@ -4,19 +4,34 @@ import { Http } from '@angular/http';
import { Observable } from 'rxjs/Rx';
import { ServiceAuthHelpers } from './service.helpers';
import {IUser} from '../interfaces/IUser';
import { IUser } from '../interfaces/IUser';
@Injectable()
export class IdentityService extends ServiceAuthHelpers {
constructor(http: AuthHttp, private regularHttp : Http) {
constructor(http: AuthHttp, private regularHttp: Http) {
super(http, '/api/v1/Identity/');
}
createWizardUser(username:string,password:string): Observable<boolean> {
return this.regularHttp.post(`${this.url}/Wizard/`, JSON.stringify({username:username, password:password}), { headers: this.headers }).map(this.extractData);
createWizardUser(username: string, password: string): Observable<boolean> {
return this.regularHttp.post(`${this.url}/Wizard/`, JSON.stringify({ username: username, password: password }), { headers: this.headers }).map(this.extractData);
}
getUser(): Observable<IUser> {
return this.http.get(this.url).map(this.extractData);
}
getUsers(): Observable<IUser[]> {
return this.http.get(`${this.url}/Users`).map(this.extractData);
}
hasRole(role: string): boolean {
var roles = localStorage.getItem("roles") as string[];
if (roles) {
if (roles.indexOf(role) > -1) {
return true;
}
return false;
}
return false;
}
}

@ -5,7 +5,8 @@ import { Observable } from 'rxjs/Rx';
import { ServiceAuthHelpers } from './service.helpers';
import { IRequestEngineResult } from '../interfaces/IRequestEngineResult';
import { ISearchMovieResult } from '../interfaces/ISearchMovieResult';
import { IRequestModel } from '../interfaces/IRequestModel';
import { ISearchTvResult } from '../interfaces/ISearchTvResult';
import { IMovieRequestModel } from '../interfaces/IRequestModel';
@Injectable()
export class RequestService extends ServiceAuthHelpers {
@ -17,23 +18,23 @@ export class RequestService extends ServiceAuthHelpers {
return this.http.post(`${this.url}/Movie/`, JSON.stringify(movie), { headers: this.headers }).map(this.extractData);
}
getAllRequests(): Observable<IRequestModel[]> {
return this.http.get(this.url).map(this.extractData);
requestTv(tv: ISearchTvResult): Observable<IRequestEngineResult> {
return this.http.post(`${this.url}/TV/`, JSON.stringify(tv), { headers: this.headers }).map(this.extractData);
}
getRequests(count: number, position: number): Observable<IRequestModel[]> {
return this.http.get(`${this.url}/${count}/${position}`).map(this.extractData);
getRequests(count: number, position: number): Observable<IMovieRequestModel[]> {
return this.http.get(`${this.url}/movie/${count}/${position}`).map(this.extractData);
}
searchRequests(search: string): Observable<IRequestModel[]> {
return this.http.get(`${this.url}/search/${search}`).map(this.extractData);
searchRequests(search: string): Observable<IMovieRequestModel[]> {
return this.http.get(`${this.url}/movie/search/${search}`).map(this.extractData);
}
removeRequest(request: IRequestModel): Observable<void> {
return this.http.delete(`${this.url}/${request.id}`).map(this.extractData);
removeMovieRequest(request: IMovieRequestModel) {
this.http.delete(`${this.url}/movie/${request.id}`).map(this.extractData).subscribe();
}
updateRequest(request: IRequestModel) : Observable<IRequestModel> {
return this.http.post(`${this.url}/`, JSON.stringify(request), { headers: this.headers }).map(this.extractData);
updateRequest(request: IMovieRequestModel): Observable<IMovieRequestModel> {
return this.http.post(`${this.url}/movie/`, JSON.stringify(request), { headers: this.headers }).map(this.extractData);
}
}

@ -12,6 +12,7 @@ export class SearchService extends ServiceAuthHelpers {
super(http, "/api/v1/search");
}
// Movies
searchMovie(searchTerm: string): Observable<ISearchMovieResult[]> {
return this.http.get(`${this.url}/Movie/` + searchTerm).map(this.extractData);
}
@ -32,7 +33,20 @@ export class SearchService extends ServiceAuthHelpers {
return this.http.post(`${this.url}/Movie/extrainfo`, JSON.stringify(movies), { headers: this.headers }).map(this.extractData);
}
// TV
searchTv(searchTerm: string): Observable<ISearchTvResult[]> {
return this.http.get(`${this.url}/Tv/` + searchTerm).map(this.extractData);
}
popularTv(): Observable<ISearchTvResult[]> {
return this.http.get(`${this.url}/Tv/popular`).map(this.extractData);
}
mostWatchedTv(): Observable<ISearchTvResult[]> {
return this.http.get(`${this.url}/Tv/mostwatched`).map(this.extractData);
}
anticiplatedTv(): Observable<ISearchTvResult[]> {
return this.http.get(`${this.url}/Tv/anticipated`).map(this.extractData);
}
trendingTv(): Observable<ISearchTvResult[]> {
return this.http.get(`${this.url}/Tv/trending`).map(this.extractData);
}
}
Loading…
Cancel
Save