mirror of
https://github.com/Ombi-app/Ombi.git
synced 2025-07-14 01:02:57 -07:00
!wip started the searching process
This commit is contained in:
parent
26d620cf01
commit
9156673f88
20 changed files with 151 additions and 106 deletions
|
@ -22,7 +22,7 @@ namespace Ombi.Api.Lidarr
|
||||||
|
|
||||||
public Task<List<LidarrProfile>> GetProfiles(string apiKey, string baseUrl)
|
public Task<List<LidarrProfile>> GetProfiles(string apiKey, string baseUrl)
|
||||||
{
|
{
|
||||||
var request = new Request($"{ApiVersion}/profile", baseUrl, HttpMethod.Get);
|
var request = new Request($"{ApiVersion}/qualityprofile", baseUrl, HttpMethod.Get);
|
||||||
|
|
||||||
AddHeaders(request, apiKey);
|
AddHeaders(request, apiKey);
|
||||||
return Api.Request<List<LidarrProfile>>(request);
|
return Api.Request<List<LidarrProfile>>(request);
|
||||||
|
|
|
@ -2,12 +2,6 @@
|
||||||
|
|
||||||
namespace Ombi.Api.Lidarr.Models
|
namespace Ombi.Api.Lidarr.Models
|
||||||
{
|
{
|
||||||
public class Cutoff
|
|
||||||
{
|
|
||||||
public int id { get; set; }
|
|
||||||
public string name { get; set; }
|
|
||||||
}
|
|
||||||
|
|
||||||
public class Quality
|
public class Quality
|
||||||
{
|
{
|
||||||
public int id { get; set; }
|
public int id { get; set; }
|
||||||
|
@ -23,9 +17,7 @@ namespace Ombi.Api.Lidarr.Models
|
||||||
public class LidarrProfile
|
public class LidarrProfile
|
||||||
{
|
{
|
||||||
public string name { get; set; }
|
public string name { get; set; }
|
||||||
public Cutoff cutoff { get; set; }
|
|
||||||
public List<Item> items { get; set; }
|
public List<Item> items { get; set; }
|
||||||
public string language { get; set; }
|
|
||||||
public int id { get; set; }
|
public int id { get; set; }
|
||||||
}
|
}
|
||||||
}
|
}
|
|
@ -7,6 +7,6 @@
|
||||||
public int trackCount { get; set; }
|
public int trackCount { get; set; }
|
||||||
public int totalTrackCount { get; set; }
|
public int totalTrackCount { get; set; }
|
||||||
public int sizeOnDisk { get; set; }
|
public int sizeOnDisk { get; set; }
|
||||||
public int percentOfTracks { get; set; }
|
public decimal percentOfTracks { get; set; }
|
||||||
}
|
}
|
||||||
}
|
}
|
16
src/Ombi.Core/Engine/Interfaces/IMusicSearchEngine.cs
Normal file
16
src/Ombi.Core/Engine/Interfaces/IMusicSearchEngine.cs
Normal file
|
@ -0,0 +1,16 @@
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
using Ombi.Api.Lidarr.Models;
|
||||||
|
using Ombi.Core.Models.Search;
|
||||||
|
|
||||||
|
namespace Ombi.Core.Engine
|
||||||
|
{
|
||||||
|
public interface IMusicSearchEngine
|
||||||
|
{
|
||||||
|
Task<ArtistResult> GetAlbumArtist(string foreignArtistId);
|
||||||
|
Task<ArtistResult> GetArtist(int artistId);
|
||||||
|
Task<ArtistResult> GetArtistAlbums(string foreignArtistId);
|
||||||
|
Task<IEnumerable<AlbumLookup>> SearchAlbum(string search);
|
||||||
|
Task<IEnumerable<SearchArtistViewModel>> SearchArtist(string search);
|
||||||
|
}
|
||||||
|
}
|
|
@ -24,7 +24,7 @@ using Ombi.Store.Repository;
|
||||||
|
|
||||||
namespace Ombi.Core.Engine
|
namespace Ombi.Core.Engine
|
||||||
{
|
{
|
||||||
public class MusicSearchEngine : BaseMediaEngine
|
public class MusicSearchEngine : BaseMediaEngine, IMusicSearchEngine
|
||||||
{
|
{
|
||||||
public MusicSearchEngine(IPrincipal identity, IRequestServiceMain service, ILidarrApi lidarrApi, IMapper mapper,
|
public MusicSearchEngine(IPrincipal identity, IRequestServiceMain service, ILidarrApi lidarrApi, IMapper mapper,
|
||||||
ILogger<MusicSearchEngine> logger, IRuleEvaluator r, OmbiUserManager um, ICacheService mem, ISettingsService<OmbiSettings> s, IRepository<RequestSubscription> sub,
|
ILogger<MusicSearchEngine> logger, IRuleEvaluator r, OmbiUserManager um, ICacheService mem, ISettingsService<OmbiSettings> s, IRepository<RequestSubscription> sub,
|
||||||
|
@ -60,12 +60,42 @@ namespace Ombi.Core.Engine
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="search">The search.</param>
|
/// <param name="search">The search.</param>
|
||||||
/// <returns></returns>
|
/// <returns></returns>
|
||||||
public async Task<IEnumerable<ArtistLookup>> SearchArtist(string search)
|
public async Task<IEnumerable<SearchArtistViewModel>> SearchArtist(string search)
|
||||||
{
|
{
|
||||||
var settings = await GetSettings();
|
var settings = await GetSettings();
|
||||||
var result = await _lidarrApi.ArtistLookup(search, settings.ApiKey, settings.FullUri);
|
var result = await _lidarrApi.ArtistLookup(search, settings.ApiKey, settings.FullUri);
|
||||||
|
|
||||||
return result;
|
var vm = new List<SearchArtistViewModel>();
|
||||||
|
foreach (var r in result)
|
||||||
|
{
|
||||||
|
vm.Add(MapIntoArtistVm(r));
|
||||||
|
}
|
||||||
|
|
||||||
|
return vm;
|
||||||
|
}
|
||||||
|
|
||||||
|
private SearchArtistViewModel MapIntoArtistVm(ArtistLookup a)
|
||||||
|
{
|
||||||
|
var vm = new SearchArtistViewModel
|
||||||
|
{
|
||||||
|
ArtistName = a.artistName,
|
||||||
|
ArtistType = a.artistType,
|
||||||
|
Banner = a.images?.FirstOrDefault(x => x.coverType.Equals("banner"))?.url,
|
||||||
|
Logo = a.images?.FirstOrDefault(x => x.coverType.Equals("logo"))?.url,
|
||||||
|
CleanName = a.cleanName,
|
||||||
|
Disambiguation = a.disambiguation,
|
||||||
|
ForignArtistId = a.foreignArtistId,
|
||||||
|
Links = a.links,
|
||||||
|
Overview = a.overview,
|
||||||
|
};
|
||||||
|
|
||||||
|
var poster = a.images?.FirstOrDefault(x => x.coverType.Equals("poaster"));
|
||||||
|
if (poster == null)
|
||||||
|
{
|
||||||
|
vm.Poster = a.remotePoster;
|
||||||
|
}
|
||||||
|
|
||||||
|
return vm;
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
@ -73,7 +103,7 @@ namespace Ombi.Core.Engine
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="artistId"></param>
|
/// <param name="artistId"></param>
|
||||||
/// <returns></returns>
|
/// <returns></returns>
|
||||||
public async Task GetArtistAlbums(string foreignArtistId)
|
public async Task<ArtistResult> GetArtistAlbums(string foreignArtistId)
|
||||||
{
|
{
|
||||||
var settings = await GetSettings();
|
var settings = await GetSettings();
|
||||||
return await _lidarrApi.GetArtistByForignId(foreignArtistId, settings.ApiKey, settings.FullUri);
|
return await _lidarrApi.GetArtistByForignId(foreignArtistId, settings.ApiKey, settings.FullUri);
|
||||||
|
@ -82,11 +112,12 @@ namespace Ombi.Core.Engine
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Returns the artist that produced the album
|
/// Returns the artist that produced the album
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="albumId"></param>
|
/// <param name="foreignArtistId"></param>
|
||||||
/// <returns></returns>
|
/// <returns></returns>
|
||||||
public async Task GetAlbumArtist(string foreignArtistId)
|
public async Task<ArtistResult> GetAlbumArtist(string foreignArtistId)
|
||||||
{
|
{
|
||||||
throw new NotImplementedException();
|
var settings = await GetSettings();
|
||||||
|
return await _lidarrApi.GetArtistByForignId(foreignArtistId, settings.ApiKey, settings.FullUri);
|
||||||
}
|
}
|
||||||
|
|
||||||
public async Task<ArtistResult> GetArtist(int artistId)
|
public async Task<ArtistResult> GetArtist(int artistId)
|
||||||
|
|
21
src/Ombi.Core/Models/Search/SearchArtistViewModel.cs
Normal file
21
src/Ombi.Core/Models/Search/SearchArtistViewModel.cs
Normal file
|
@ -0,0 +1,21 @@
|
||||||
|
using Ombi.Api.Lidarr.Models;
|
||||||
|
|
||||||
|
namespace Ombi.Core.Models.Search
|
||||||
|
{
|
||||||
|
public class SearchArtistViewModel
|
||||||
|
{
|
||||||
|
public string ArtistName { get; set; }
|
||||||
|
public string ForignArtistId { get; set; }
|
||||||
|
public string Overview { get; set; }
|
||||||
|
public string Disambiguation { get; set; }
|
||||||
|
public string Banner { get; set; }
|
||||||
|
public string Poster { get; set; }
|
||||||
|
public string Logo { get; set; }
|
||||||
|
public bool Monitored { get; set; }
|
||||||
|
public bool Available { get; set; }
|
||||||
|
public bool Requested { get; set; }
|
||||||
|
public string ArtistType { get; set; }
|
||||||
|
public string CleanName { get; set; }
|
||||||
|
public Link[] Links { get; set; } // Couldn't be bothered to map it
|
||||||
|
}
|
||||||
|
}
|
|
@ -83,6 +83,7 @@ namespace Ombi.DependencyInjection
|
||||||
services.AddTransient<IUserStatsEngine, UserStatsEngine>();
|
services.AddTransient<IUserStatsEngine, UserStatsEngine>();
|
||||||
services.AddTransient<IMovieSender, MovieSender>();
|
services.AddTransient<IMovieSender, MovieSender>();
|
||||||
services.AddTransient<IRecentlyAddedEngine, RecentlyAddedEngine>();
|
services.AddTransient<IRecentlyAddedEngine, RecentlyAddedEngine>();
|
||||||
|
services.AddTransient<IMusicSearchEngine, MusicSearchEngine>();
|
||||||
services.AddTransient<ITvSender, TvSender>();
|
services.AddTransient<ITvSender, TvSender>();
|
||||||
services.AddTransient<IMassEmailSender, MassEmailSender>();
|
services.AddTransient<IMassEmailSender, MassEmailSender>();
|
||||||
services.AddTransient<IPlexOAuthManager, PlexOAuthManager>();
|
services.AddTransient<IPlexOAuthManager, PlexOAuthManager>();
|
||||||
|
|
|
@ -83,7 +83,7 @@
|
||||||
<ng-template #notRequestedBtn>
|
<ng-template #notRequestedBtn>
|
||||||
<button id="{{result.id}}" style="text-align: right" class="btn btn-primary-outline" (click)="request(result)">
|
<button id="{{result.id}}" style="text-align: right" class="btn btn-primary-outline" (click)="request(result)">
|
||||||
<i *ngIf="result.requestProcessing" class="fa fa-circle-o-notch fa-spin fa-fw"></i> <i *ngIf="!result.requestProcessing && !result.processed" class="fa fa-plus"></i>
|
<i *ngIf="result.requestProcessing" class="fa fa-circle-o-notch fa-spin fa-fw"></i> <i *ngIf="!result.requestProcessing && !result.processed" class="fa fa-plus"></i>
|
||||||
<i *ngIf="result.processed && !result.requestProcessing" class="fa fa-check"></i>{{ 'Common.Request' | translate }}</button>
|
<i *ngIf="result.processed && !result.requestProcessing" class="fa fa-check"></i> {{ 'Common.Request' | translate }}</button>
|
||||||
</ng-template>
|
</ng-template>
|
||||||
</div>
|
</div>
|
||||||
<button style="text-align: right" class="btn btn-sm btn-info-outline" (click)="similarMovies(result.id)"> <i class="fa fa-eye"></i> {{ 'Search.Similar' | translate }}</button>
|
<button style="text-align: right" class="btn btn-sm btn-info-outline" (click)="similarMovies(result.id)"> <i class="fa fa-eye"></i> {{ 'Search.Similar' | translate }}</button>
|
||||||
|
|
|
@ -4,13 +4,13 @@ import { TranslateService } from "@ngx-translate/core";
|
||||||
import { Subject } from "rxjs";
|
import { Subject } from "rxjs";
|
||||||
import { debounceTime, distinctUntilChanged } from "rxjs/operators";
|
import { debounceTime, distinctUntilChanged } from "rxjs/operators";
|
||||||
|
|
||||||
import { AuthService } from "../auth/auth.service";
|
import { AuthService } from "../../auth/auth.service";
|
||||||
import { IIssueCategory, IRequestEngineResult, ISearchMovieResult } from "../interfaces";
|
import { IIssueCategory, IRequestEngineResult, ISearchMovieResult } from "../../interfaces";
|
||||||
import { NotificationService, RequestService, SearchService } from "../services";
|
import { NotificationService, RequestService, SearchService } from "../../services";
|
||||||
|
|
||||||
@Component({
|
@Component({
|
||||||
selector: "music-search",
|
selector: "music-search",
|
||||||
templateUrl: "./music.component.html",
|
templateUrl: "./musicsearch.component.html",
|
||||||
})
|
})
|
||||||
export class MusicSearchComponent implements OnInit {
|
export class MusicSearchComponent implements OnInit {
|
||||||
|
|
||||||
|
@ -19,6 +19,7 @@ export class MusicSearchComponent implements OnInit {
|
||||||
public movieResults: ISearchMovieResult[];
|
public movieResults: ISearchMovieResult[];
|
||||||
public result: IRequestEngineResult;
|
public result: IRequestEngineResult;
|
||||||
public searchApplied = false;
|
public searchApplied = false;
|
||||||
|
public searchArtist: boolean;
|
||||||
|
|
||||||
@Input() public issueCategories: IIssueCategory[];
|
@Input() public issueCategories: IIssueCategory[];
|
||||||
@Input() public issuesEnabled: boolean;
|
@Input() public issuesEnabled: boolean;
|
||||||
|
@ -44,11 +45,20 @@ export class MusicSearchComponent implements OnInit {
|
||||||
this.clearResults();
|
this.clearResults();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
this.searchService.searchMusic(this.searchText)
|
if(this.searchArtist) {
|
||||||
|
this.searchService.searchArtist(this.searchText)
|
||||||
.subscribe(x => {
|
.subscribe(x => {
|
||||||
this.movieResults = x;
|
this.movieResults = x;
|
||||||
this.searchApplied = true;
|
this.searchApplied = true;
|
||||||
});
|
});
|
||||||
|
} else {
|
||||||
|
this.searchService.searchAlbum(this.searchText)
|
||||||
|
.subscribe(x => {
|
||||||
|
this.movieResults = x;
|
||||||
|
this.searchApplied = true;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
});
|
});
|
||||||
this.defaultPoster = "../../../images/default_movie_poster.png";
|
this.defaultPoster = "../../../images/default_movie_poster.png";
|
||||||
const base = this.platformLocation.getBaseHrefFromDOM();
|
const base = this.platformLocation.getBaseHrefFromDOM();
|
||||||
|
@ -65,7 +75,6 @@ export class MusicSearchComponent implements OnInit {
|
||||||
result: false,
|
result: false,
|
||||||
errorMessage: "",
|
errorMessage: "",
|
||||||
};
|
};
|
||||||
this.popularMovies();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public search(text: any) {
|
public search(text: any) {
|
||||||
|
@ -111,77 +120,6 @@ export class MusicSearchComponent implements OnInit {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public popularMovies() {
|
|
||||||
this.clearResults();
|
|
||||||
this.searchService.popularMovies()
|
|
||||||
.subscribe(x => {
|
|
||||||
this.movieResults = x;
|
|
||||||
});
|
|
||||||
}
|
|
||||||
public nowPlayingMovies() {
|
|
||||||
this.clearResults();
|
|
||||||
this.searchService.nowPlayingMovies()
|
|
||||||
.subscribe(x => {
|
|
||||||
this.movieResults = x;
|
|
||||||
});
|
|
||||||
}
|
|
||||||
public topRatedMovies() {
|
|
||||||
this.clearResults();
|
|
||||||
this.searchService.topRatedMovies()
|
|
||||||
.subscribe(x => {
|
|
||||||
this.movieResults = x;
|
|
||||||
});
|
|
||||||
}
|
|
||||||
public upcomingMovies() {
|
|
||||||
this.clearResults();
|
|
||||||
this.searchService.upcomingMovies()
|
|
||||||
.subscribe(x => {
|
|
||||||
this.movieResults = x;
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
public reportIssue(catId: IIssueCategory, req: ISearchMovieResult) {
|
|
||||||
this.issueRequestId = req.id;
|
|
||||||
this.issueRequestTitle = req.title + `(${req.releaseDate.getFullYear})`;
|
|
||||||
this.issueCategorySelected = catId;
|
|
||||||
this.issuesBarVisible = true;
|
|
||||||
this.issueProviderId = req.id.toString();
|
|
||||||
}
|
|
||||||
|
|
||||||
public similarMovies(theMovieDbId: number) {
|
|
||||||
this.clearResults();
|
|
||||||
this.searchService.similarMovies(theMovieDbId)
|
|
||||||
.subscribe(x => {
|
|
||||||
this.movieResults = x;
|
|
||||||
this.getExtraInfo();
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
public subscribe(r: ISearchMovieResult) {
|
|
||||||
r.subscribed = true;
|
|
||||||
this.requestService.subscribeToMovie(r.requestId)
|
|
||||||
.subscribe(x => {
|
|
||||||
this.notificationService.success("Subscribed To Movie!");
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
public unSubscribe(r: ISearchMovieResult) {
|
|
||||||
r.subscribed = false;
|
|
||||||
this.requestService.unSubscribeToMovie(r.requestId)
|
|
||||||
.subscribe(x => {
|
|
||||||
this.notificationService.success("Unsubscribed Movie!");
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
private updateItem(key: ISearchMovieResult, updated: ISearchMovieResult) {
|
|
||||||
const index = this.movieResults.indexOf(key, 0);
|
|
||||||
if (index > -1) {
|
|
||||||
const copy = { ...this.movieResults[index] };
|
|
||||||
this.movieResults[index] = updated;
|
|
||||||
this.movieResults[index].background = copy.background;
|
|
||||||
this.movieResults[index].posterPath = copy.posterPath;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
private clearResults() {
|
private clearResults() {
|
||||||
this.movieResults = [];
|
this.movieResults = [];
|
||||||
this.searchApplied = false;
|
this.searchApplied = false;
|
||||||
|
|
|
@ -13,6 +13,9 @@
|
||||||
<li role="presentation">
|
<li role="presentation">
|
||||||
<a id="tvTabButton" href="#TvShowTab" aria-controls="profile" role="tab" data-toggle="tab" (click)="selectTvTab()"><i class="fa fa-television"></i> {{ 'Search.TvTab' | translate }}</a>
|
<a id="tvTabButton" href="#TvShowTab" aria-controls="profile" role="tab" data-toggle="tab" (click)="selectTvTab()"><i class="fa fa-television"></i> {{ 'Search.TvTab' | translate }}</a>
|
||||||
</li>
|
</li>
|
||||||
|
<li role="presentation" *ngIf="musicEnabled">
|
||||||
|
<a id="tvTabButton" href="#MusicTab" aria-controls="profile" role="tab" data-toggle="tab" (click)="selectMusicTab()"><i class="fa fa-music"></i> {{ 'Search.MusicTab' | translate }}</a>
|
||||||
|
</li>
|
||||||
</ul>
|
</ul>
|
||||||
|
|
||||||
<!-- Tab panes -->
|
<!-- Tab panes -->
|
||||||
|
@ -25,6 +28,9 @@
|
||||||
<div [hidden]="!showTv">
|
<div [hidden]="!showTv">
|
||||||
<tv-search [issueCategories]="issueCategories" [issuesEnabled]="issuesEnabled"></tv-search>
|
<tv-search [issueCategories]="issueCategories" [issuesEnabled]="issuesEnabled"></tv-search>
|
||||||
</div>
|
</div>
|
||||||
|
<div [hidden]="!showMusic">
|
||||||
|
<music-search></music-search>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -9,8 +9,10 @@ import { IssuesService, SettingsService } from "../services";
|
||||||
export class SearchComponent implements OnInit {
|
export class SearchComponent implements OnInit {
|
||||||
public showTv: boolean;
|
public showTv: boolean;
|
||||||
public showMovie: boolean;
|
public showMovie: boolean;
|
||||||
|
public showMusic: boolean;
|
||||||
public issueCategories: IIssueCategory[];
|
public issueCategories: IIssueCategory[];
|
||||||
public issuesEnabled = false;
|
public issuesEnabled = false;
|
||||||
|
public musicEnabled: boolean;
|
||||||
|
|
||||||
constructor(private issuesService: IssuesService,
|
constructor(private issuesService: IssuesService,
|
||||||
private settingsService: SettingsService) {
|
private settingsService: SettingsService) {
|
||||||
|
@ -18,8 +20,10 @@ export class SearchComponent implements OnInit {
|
||||||
}
|
}
|
||||||
|
|
||||||
public ngOnInit() {
|
public ngOnInit() {
|
||||||
|
this.settingsService.getLidarr().subscribe(x => this.musicEnabled = x.enabled);
|
||||||
this.showMovie = true;
|
this.showMovie = true;
|
||||||
this.showTv = false;
|
this.showTv = false;
|
||||||
|
this.showMusic = false;
|
||||||
this.issuesService.getCategories().subscribe(x => this.issueCategories = x);
|
this.issuesService.getCategories().subscribe(x => this.issueCategories = x);
|
||||||
this.settingsService.getIssueSettings().subscribe(x => this.issuesEnabled = x.enabled);
|
this.settingsService.getIssueSettings().subscribe(x => this.issuesEnabled = x.enabled);
|
||||||
}
|
}
|
||||||
|
@ -27,10 +31,17 @@ export class SearchComponent implements OnInit {
|
||||||
public selectMovieTab() {
|
public selectMovieTab() {
|
||||||
this.showMovie = true;
|
this.showMovie = true;
|
||||||
this.showTv = false;
|
this.showTv = false;
|
||||||
|
this.showMusic = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
public selectTvTab() {
|
public selectTvTab() {
|
||||||
this.showMovie = false;
|
this.showMovie = false;
|
||||||
this.showTv = true;
|
this.showTv = true;
|
||||||
|
this.showMusic = false;
|
||||||
|
}
|
||||||
|
public selectMusicTab() {
|
||||||
|
this.showMovie = false;
|
||||||
|
this.showTv = false;
|
||||||
|
this.showMusic = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -7,6 +7,7 @@ import { NgbModule } from "@ng-bootstrap/ng-bootstrap";
|
||||||
|
|
||||||
import { MovieSearchComponent } from "./moviesearch.component";
|
import { MovieSearchComponent } from "./moviesearch.component";
|
||||||
import { MovieSearchGridComponent } from "./moviesearchgrid.component";
|
import { MovieSearchGridComponent } from "./moviesearchgrid.component";
|
||||||
|
import { MusicSearchComponent } from "./music/musicsearch.component";
|
||||||
import { SearchComponent } from "./search.component";
|
import { SearchComponent } from "./search.component";
|
||||||
import { SeriesInformationComponent } from "./seriesinformation.component";
|
import { SeriesInformationComponent } from "./seriesinformation.component";
|
||||||
import { TvSearchComponent } from "./tvsearch.component";
|
import { TvSearchComponent } from "./tvsearch.component";
|
||||||
|
@ -41,6 +42,7 @@ const routes: Routes = [
|
||||||
TvSearchComponent,
|
TvSearchComponent,
|
||||||
SeriesInformationComponent,
|
SeriesInformationComponent,
|
||||||
MovieSearchGridComponent,
|
MovieSearchGridComponent,
|
||||||
|
MusicSearchComponent,
|
||||||
],
|
],
|
||||||
exports: [
|
exports: [
|
||||||
RouterModule,
|
RouterModule,
|
||||||
|
|
|
@ -69,7 +69,10 @@ export class SearchService extends ServiceHelpers {
|
||||||
return this.http.get<ISearchTvResult[]>(`${this.url}/Tv/trending`, {headers: this.headers});
|
return this.http.get<ISearchTvResult[]>(`${this.url}/Tv/trending`, {headers: this.headers});
|
||||||
}
|
}
|
||||||
// Music
|
// Music
|
||||||
public searchMusic(searchTerm: string): Observable<ISearchMovieResult[]> {
|
public searchArtist(searchTerm: string): Observable<any> {
|
||||||
return this.http.get<ISearchMovieResult[]>(`${this.url}/Music/` + searchTerm);
|
return this.http.get<any>(`${this.url}/Music/Artist/` + searchTerm);
|
||||||
|
}
|
||||||
|
public searchAlbum(searchTerm: string): Observable<any> {
|
||||||
|
return this.http.get<any>(`${this.url}/Music/Album/` + searchTerm);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -3,8 +3,7 @@ import { FormBuilder, FormGroup, Validators } from "@angular/forms";
|
||||||
|
|
||||||
import { ILidarrSettings, IMinimumAvailability, IRadarrProfile, IRadarrRootFolder } from "../../interfaces";
|
import { ILidarrSettings, IMinimumAvailability, IRadarrProfile, IRadarrRootFolder } from "../../interfaces";
|
||||||
import { IRadarrSettings } from "../../interfaces";
|
import { IRadarrSettings } from "../../interfaces";
|
||||||
import { RadarrService } from "../../services";
|
import { LidarrService, TesterService } from "../../services";
|
||||||
import { TesterService } from "../../services";
|
|
||||||
import { NotificationService } from "../../services";
|
import { NotificationService } from "../../services";
|
||||||
import { SettingsService } from "../../services";
|
import { SettingsService } from "../../services";
|
||||||
|
|
||||||
|
@ -22,7 +21,7 @@ export class LidarrComponent implements OnInit {
|
||||||
public form: FormGroup;
|
public form: FormGroup;
|
||||||
|
|
||||||
constructor(private settingsService: SettingsService,
|
constructor(private settingsService: SettingsService,
|
||||||
private radarrService: RadarrService,
|
private lidarrService: LidarrService,
|
||||||
private notificationService: NotificationService,
|
private notificationService: NotificationService,
|
||||||
private fb: FormBuilder,
|
private fb: FormBuilder,
|
||||||
private testerService: TesterService) { }
|
private testerService: TesterService) { }
|
||||||
|
@ -59,7 +58,7 @@ export class LidarrComponent implements OnInit {
|
||||||
|
|
||||||
public getProfiles(form: FormGroup) {
|
public getProfiles(form: FormGroup) {
|
||||||
this.profilesRunning = true;
|
this.profilesRunning = true;
|
||||||
this.radarrService.getQualityProfiles(form.value).subscribe(x => {
|
this.lidarrService.getQualityProfiles(form.value).subscribe(x => {
|
||||||
this.qualities = x;
|
this.qualities = x;
|
||||||
this.qualities.unshift({ name: "Please Select", id: -1 });
|
this.qualities.unshift({ name: "Please Select", id: -1 });
|
||||||
|
|
||||||
|
@ -70,7 +69,7 @@ export class LidarrComponent implements OnInit {
|
||||||
|
|
||||||
public getRootFolders(form: FormGroup) {
|
public getRootFolders(form: FormGroup) {
|
||||||
this.rootFoldersRunning = true;
|
this.rootFoldersRunning = true;
|
||||||
this.radarrService.getRootFolders(form.value).subscribe(x => {
|
this.lidarrService.getRootFolders(form.value).subscribe(x => {
|
||||||
this.rootFolders = x;
|
this.rootFolders = x;
|
||||||
this.rootFolders.unshift({ path: "Please Select", id: -1 });
|
this.rootFolders.unshift({ path: "Please Select", id: -1 });
|
||||||
|
|
||||||
|
|
|
@ -50,7 +50,7 @@
|
||||||
|
|
||||||
<li class="dropdown" [routerLinkActive]="['active']">
|
<li class="dropdown" [routerLinkActive]="['active']">
|
||||||
<a href="ignore($event)" class="dropdown-toggle" data-toggle="dropdown">
|
<a href="ignore($event)" class="dropdown-toggle" data-toggle="dropdown">
|
||||||
<i class="fa fa-film" aria-hidden="true"></i> Music <span class="caret"></span>
|
<i class="fa fa-music" aria-hidden="true"></i> Music <span class="caret"></span>
|
||||||
</a>
|
</a>
|
||||||
<ul class="dropdown-menu">
|
<ul class="dropdown-menu">
|
||||||
<li [routerLinkActive]="['active']"><a [routerLink]="['/Settings/Lidarr']">Lidarr</a></li>
|
<li [routerLinkActive]="['active']"><a [routerLink]="['/Settings/Lidarr']">Lidarr</a></li>
|
||||||
|
|
|
@ -4,7 +4,7 @@ using System.Threading.Tasks;
|
||||||
using Microsoft.AspNetCore.Authorization;
|
using Microsoft.AspNetCore.Authorization;
|
||||||
using Microsoft.AspNetCore.Mvc;
|
using Microsoft.AspNetCore.Mvc;
|
||||||
using Microsoft.Extensions.Logging;
|
using Microsoft.Extensions.Logging;
|
||||||
|
using Ombi.Api.Lidarr.Models;
|
||||||
using Ombi.Core;
|
using Ombi.Core;
|
||||||
using Ombi.Core.Engine;
|
using Ombi.Core.Engine;
|
||||||
using Ombi.Core.Engine.Interfaces;
|
using Ombi.Core.Engine.Interfaces;
|
||||||
|
@ -18,16 +18,18 @@ namespace Ombi.Controllers
|
||||||
[Produces("application/json")]
|
[Produces("application/json")]
|
||||||
public class SearchController : Controller
|
public class SearchController : Controller
|
||||||
{
|
{
|
||||||
public SearchController(IMovieEngine movie, ITvSearchEngine tvEngine, ILogger<SearchController> logger)
|
public SearchController(IMovieEngine movie, ITvSearchEngine tvEngine, ILogger<SearchController> logger, IMusicSearchEngine music)
|
||||||
{
|
{
|
||||||
MovieEngine = movie;
|
MovieEngine = movie;
|
||||||
TvEngine = tvEngine;
|
TvEngine = tvEngine;
|
||||||
Logger = logger;
|
Logger = logger;
|
||||||
|
MusicEngine = music;
|
||||||
}
|
}
|
||||||
private ILogger<SearchController> Logger { get; }
|
private ILogger<SearchController> Logger { get; }
|
||||||
|
|
||||||
private IMovieEngine MovieEngine { get; }
|
private IMovieEngine MovieEngine { get; }
|
||||||
private ITvSearchEngine TvEngine { get; }
|
private ITvSearchEngine TvEngine { get; }
|
||||||
|
private IMusicSearchEngine MusicEngine { get; }
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Searches for a movie.
|
/// Searches for a movie.
|
||||||
|
@ -182,5 +184,27 @@ namespace Ombi.Controllers
|
||||||
{
|
{
|
||||||
return await TvEngine.Trending();
|
return await TvEngine.Trending();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Returns the artist information we searched for
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>We use Lidarr as the Provider</remarks>
|
||||||
|
/// <returns></returns>
|
||||||
|
[HttpGet("music/artist/{searchTerm}")]
|
||||||
|
public async Task<IEnumerable<SearchArtistViewModel>> SearchArtist(string searchTerm)
|
||||||
|
{
|
||||||
|
return await MusicEngine.SearchArtist(searchTerm);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Returns the album information we searched for
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>We use Lidarr as the Provider</remarks>
|
||||||
|
/// <returns></returns>
|
||||||
|
[HttpGet("music/album/{searchTerm}")]
|
||||||
|
public async Task<IEnumerable<AlbumLookup>> SearchAlbum(string searchTerm)
|
||||||
|
{
|
||||||
|
return await MusicEngine.SearchAlbum(searchTerm);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -333,7 +333,7 @@ namespace Ombi.Controllers
|
||||||
/// </summary>
|
/// </summary>
|
||||||
/// <param name="settings">The settings.</param>
|
/// <param name="settings">The settings.</param>
|
||||||
/// <returns></returns>
|
/// <returns></returns>
|
||||||
[HttpPost("sonarr")]
|
[HttpPost("lidarr")]
|
||||||
public async Task<bool> LidarrSettings([FromBody]LidarrSettings settings)
|
public async Task<bool> LidarrSettings([FromBody]LidarrSettings settings)
|
||||||
{
|
{
|
||||||
return await Save(settings);
|
return await Save(settings);
|
||||||
|
|
|
@ -78,6 +78,7 @@
|
||||||
"Want to watch something that is not currently available? No problem, just search for it below and request it!",
|
"Want to watch something that is not currently available? No problem, just search for it below and request it!",
|
||||||
"MoviesTab": "Movies",
|
"MoviesTab": "Movies",
|
||||||
"TvTab": "TV Shows",
|
"TvTab": "TV Shows",
|
||||||
|
"MusicTab":"Music",
|
||||||
"Suggestions": "Suggestions",
|
"Suggestions": "Suggestions",
|
||||||
"NoResults": "Sorry, we didn't find any results!",
|
"NoResults": "Sorry, we didn't find any results!",
|
||||||
"DigitalDate": "Digital Release: {{date}}",
|
"DigitalDate": "Digital Release: {{date}}",
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue