mirror of
https://github.com/lidarr/lidarr.git
synced 2025-08-23 06:45:19 -07:00
Add Ability to set RootFolderPath for Net Import List
Fixed other things. Finished command to automatically add a movie.
This commit is contained in:
parent
93d6505f85
commit
82f29cdc70
13 changed files with 157 additions and 9 deletions
|
@ -20,7 +20,7 @@ namespace NzbDrone.Api.NetImport
|
||||||
resource.Enabled = definition.Enabled;
|
resource.Enabled = definition.Enabled;
|
||||||
resource.EnableAuto = definition.EnableAuto;
|
resource.EnableAuto = definition.EnableAuto;
|
||||||
resource.ProfileId = definition.ProfileId;
|
resource.ProfileId = definition.ProfileId;
|
||||||
|
resource.RootFolderPath = definition.RootFolderPath;
|
||||||
}
|
}
|
||||||
|
|
||||||
protected override void MapToModel(NetImportDefinition definition, NetImportResource resource)
|
protected override void MapToModel(NetImportDefinition definition, NetImportResource resource)
|
||||||
|
@ -30,6 +30,7 @@ namespace NzbDrone.Api.NetImport
|
||||||
definition.Enabled = resource.Enabled;
|
definition.Enabled = resource.Enabled;
|
||||||
definition.EnableAuto = resource.EnableAuto;
|
definition.EnableAuto = resource.EnableAuto;
|
||||||
definition.ProfileId = resource.ProfileId;
|
definition.ProfileId = resource.ProfileId;
|
||||||
|
definition.RootFolderPath = resource.RootFolderPath;
|
||||||
}
|
}
|
||||||
|
|
||||||
protected override void Validate(NetImportDefinition definition, bool includeWarnings)
|
protected override void Validate(NetImportDefinition definition, bool includeWarnings)
|
||||||
|
|
|
@ -6,6 +6,7 @@ namespace NzbDrone.Api.NetImport
|
||||||
{
|
{
|
||||||
public bool Enabled { get; set; }
|
public bool Enabled { get; set; }
|
||||||
public bool EnableAuto { get; set; }
|
public bool EnableAuto { get; set; }
|
||||||
|
public string RootFolderPath { get; set; }
|
||||||
public int ProfileId { get; set; }
|
public int ProfileId { get; set; }
|
||||||
}
|
}
|
||||||
}
|
}
|
|
@ -1,4 +1,5 @@
|
||||||
using FluentMigrator;
|
using FluentMigrator;
|
||||||
|
using FluentMigrator.Expressions;
|
||||||
using NzbDrone.Core.Datastore.Migration.Framework;
|
using NzbDrone.Core.Datastore.Migration.Framework;
|
||||||
|
|
||||||
namespace NzbDrone.Core.Datastore.Migration
|
namespace NzbDrone.Core.Datastore.Migration
|
||||||
|
@ -17,6 +18,7 @@ namespace NzbDrone.Core.Datastore.Migration
|
||||||
.WithColumn("ConfigContract").AsString().Nullable()
|
.WithColumn("ConfigContract").AsString().Nullable()
|
||||||
.WithColumn("Settings").AsString().Nullable()
|
.WithColumn("Settings").AsString().Nullable()
|
||||||
.WithColumn("EnableAuto").AsInt32()
|
.WithColumn("EnableAuto").AsInt32()
|
||||||
|
.WithColumn("RootFolderPath").AsString()
|
||||||
.WithColumn("ProfileId").AsInt32();
|
.WithColumn("ProfileId").AsInt32();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -6,5 +6,7 @@ namespace NzbDrone.Core.MetadataSource
|
||||||
public interface ISearchForNewMovie
|
public interface ISearchForNewMovie
|
||||||
{
|
{
|
||||||
List<Movie> SearchForNewMovie(string title);
|
List<Movie> SearchForNewMovie(string title);
|
||||||
|
|
||||||
|
Movie MapMovieToTmdbMovie(Movie movie);
|
||||||
}
|
}
|
||||||
}
|
}
|
|
@ -561,5 +561,40 @@ namespace NzbDrone.Core.MetadataSource.SkyHook
|
||||||
|
|
||||||
return value;
|
return value;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public Movie MapMovieToTmdbMovie(Movie movie)
|
||||||
|
{
|
||||||
|
Movie newMovie = movie;
|
||||||
|
if (movie.TmdbId > 0)
|
||||||
|
{
|
||||||
|
return newMovie;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (movie.ImdbId.IsNotNullOrWhiteSpace())
|
||||||
|
{
|
||||||
|
newMovie = GetMovieInfo(movie.ImdbId);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
var yearStr = "";
|
||||||
|
if (movie.Year > 1900)
|
||||||
|
{
|
||||||
|
yearStr = $" {movie.Year}";
|
||||||
|
}
|
||||||
|
newMovie = SearchForNewMovie(movie.Title + yearStr).FirstOrDefault();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (newMovie == null)
|
||||||
|
{
|
||||||
|
_logger.Warn("Couldn't map movie {0} to a movie on The Movie DB.");
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
newMovie.Path = movie.Path;
|
||||||
|
newMovie.RootFolderPath = movie.RootFolderPath;
|
||||||
|
newMovie.ProfileId = movie.ProfileId;
|
||||||
|
|
||||||
|
return newMovie;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -27,7 +27,14 @@ namespace NzbDrone.Core.NetImport.CouchPotato
|
||||||
urlBase = Settings.UrlBase.StartsWith("/") ? Settings.UrlBase : $"/{Settings.UrlBase}";
|
urlBase = Settings.UrlBase.StartsWith("/") ? Settings.UrlBase : $"/{Settings.UrlBase}";
|
||||||
}
|
}
|
||||||
|
|
||||||
var request = new NetImportRequest($"{Settings.Link.Trim()}:{Settings.Port}{urlBase}/api/{Settings.ApiKey}/movie.list/?status=active", HttpAccept.Json);
|
var status = "";
|
||||||
|
|
||||||
|
if (Settings.OnlyActive)
|
||||||
|
{
|
||||||
|
status = "?status=active";
|
||||||
|
}
|
||||||
|
|
||||||
|
var request = new NetImportRequest($"{Settings.Link.Trim()}:{Settings.Port}{urlBase}/api/{Settings.ApiKey}/movie.list/{status}", HttpAccept.Json);
|
||||||
yield return request;
|
yield return request;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -14,6 +14,7 @@ namespace NzbDrone.Core.NetImport.CouchPotato
|
||||||
Link = "http://localhost";
|
Link = "http://localhost";
|
||||||
Port = 5050;
|
Port = 5050;
|
||||||
UrlBase = "";
|
UrlBase = "";
|
||||||
|
OnlyActive = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
[FieldDefinition(0, Label = "CouchPotato URL", HelpText = "Link to your CoouchPootato.")]
|
[FieldDefinition(0, Label = "CouchPotato URL", HelpText = "Link to your CoouchPootato.")]
|
||||||
|
@ -22,10 +23,16 @@ namespace NzbDrone.Core.NetImport.CouchPotato
|
||||||
[FieldDefinition(1, Label = "CouchPotato Port", HelpText = "Port your CoouchPootato uses.")]
|
[FieldDefinition(1, Label = "CouchPotato Port", HelpText = "Port your CoouchPootato uses.")]
|
||||||
public int Port { get; set; }
|
public int Port { get; set; }
|
||||||
|
|
||||||
[FieldDefinition(2, Label = "CouchPotato Url Base", HelpText = "UrlBase your CoouchPootato uses, leave blank for none")]
|
[FieldDefinition(2, Label = "CouchPotato Url Base",
|
||||||
|
HelpText = "UrlBase your CoouchPootato uses, leave blank for none")]
|
||||||
public string UrlBase { get; set; }
|
public string UrlBase { get; set; }
|
||||||
|
|
||||||
[FieldDefinition(3, Label = "CouchPotato API Key", HelpText = "CoouchPootato API Key.")]
|
[FieldDefinition(3, Label = "CouchPotato API Key", HelpText = "CoouchPootato API Key.")]
|
||||||
public string ApiKey { get; set; }
|
public string ApiKey { get; set; }
|
||||||
|
|
||||||
|
[FieldDefinition(4, Label = "Only Active", HelpText = "Should only active (not yet downloaded) movies be fetched")]
|
||||||
|
public bool OnlyActive { get; set; }
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -214,7 +214,12 @@ namespace NzbDrone.Core.NetImport
|
||||||
{
|
{
|
||||||
var response = FetchIndexerResponse(request);
|
var response = FetchIndexerResponse(request);
|
||||||
|
|
||||||
return parser.ParseResponse(response).ToList();
|
return parser.ParseResponse(response).ToList().Select(m =>
|
||||||
|
{
|
||||||
|
m.RootFolderPath = ((NetImportDefinition) Definition).RootFolderPath;
|
||||||
|
m.ProfileId = ((NetImportDefinition) Definition).ProfileId;
|
||||||
|
return m;
|
||||||
|
}).ToList();
|
||||||
}
|
}
|
||||||
|
|
||||||
protected virtual NetImportResponse FetchIndexerResponse(NetImportRequest request)
|
protected virtual NetImportResponse FetchIndexerResponse(NetImportRequest request)
|
||||||
|
|
|
@ -10,6 +10,7 @@ namespace NzbDrone.Core.NetImport
|
||||||
public bool EnableAuto { get; set; }
|
public bool EnableAuto { get; set; }
|
||||||
public int ProfileId { get; set; }
|
public int ProfileId { get; set; }
|
||||||
public LazyLoaded<Profile> Profile { get; set; }
|
public LazyLoaded<Profile> Profile { get; set; }
|
||||||
|
public string RootFolderPath { get; set; }
|
||||||
public override bool Enable => Enabled;
|
public override bool Enable => Enabled;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -3,8 +3,11 @@ using System.Collections.Generic;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
using System.Text;
|
using System.Text;
|
||||||
using NLog;
|
using NLog;
|
||||||
|
using NzbDrone.Common.Extensions;
|
||||||
using NzbDrone.Core.Messaging.Commands;
|
using NzbDrone.Core.Messaging.Commands;
|
||||||
using NzbDrone.Core.Messaging.Events;
|
using NzbDrone.Core.Messaging.Events;
|
||||||
|
using NzbDrone.Core.MetadataSource;
|
||||||
|
using NzbDrone.Core.RootFolders;
|
||||||
using NzbDrone.Core.Tv;
|
using NzbDrone.Core.Tv;
|
||||||
|
|
||||||
namespace NzbDrone.Core.NetImport
|
namespace NzbDrone.Core.NetImport
|
||||||
|
@ -20,14 +23,26 @@ namespace NzbDrone.Core.NetImport
|
||||||
private readonly Logger _logger;
|
private readonly Logger _logger;
|
||||||
private readonly INetImportFactory _netImportFactory;
|
private readonly INetImportFactory _netImportFactory;
|
||||||
private readonly IMovieService _movieService;
|
private readonly IMovieService _movieService;
|
||||||
|
private readonly ISearchForNewMovie _movieSearch;
|
||||||
|
private readonly IRootFolderService _rootFolder;
|
||||||
|
private string defaultRootFolder;
|
||||||
|
|
||||||
public NetImportSearchService(INetImportFactory netImportFactory, IMovieService movieService, Logger logger)
|
public NetImportSearchService(INetImportFactory netImportFactory, IMovieService movieService,
|
||||||
|
ISearchForNewMovie movieSearch, IRootFolderService rootFolder, Logger logger)
|
||||||
{
|
{
|
||||||
_netImportFactory = netImportFactory;
|
_netImportFactory = netImportFactory;
|
||||||
_movieService = movieService;
|
_movieService = movieService;
|
||||||
|
_movieSearch = movieSearch;
|
||||||
|
_rootFolder = rootFolder;
|
||||||
|
var folder = _rootFolder.All().FirstOrDefault();
|
||||||
|
if (folder != null)
|
||||||
|
{
|
||||||
|
defaultRootFolder = folder.Path;
|
||||||
|
}
|
||||||
_logger = logger;
|
_logger = logger;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
public List<Movie> Fetch(int listId, bool onlyEnableAuto = false)
|
public List<Movie> Fetch(int listId, bool onlyEnableAuto = false)
|
||||||
{
|
{
|
||||||
return MovieListSearch(listId, onlyEnableAuto);
|
return MovieListSearch(listId, onlyEnableAuto);
|
||||||
|
@ -65,9 +80,19 @@ namespace NzbDrone.Core.NetImport
|
||||||
|
|
||||||
public void Execute(NetImportSyncCommand message)
|
public void Execute(NetImportSyncCommand message)
|
||||||
{
|
{
|
||||||
var movies = FetchAndFilter(2, false);
|
var movies = FetchAndFilter(0, true);
|
||||||
|
|
||||||
_logger.Debug("Found {0} movies on your lists not in your library", movies.Count);
|
_logger.Debug("Found {0} movies on your auto enabled lists not in your library", movies.Count);
|
||||||
|
|
||||||
|
foreach (var movie in movies)
|
||||||
|
{
|
||||||
|
var mapped = _movieSearch.MapMovieToTmdbMovie(movie);
|
||||||
|
|
||||||
|
if (mapped != null)
|
||||||
|
{
|
||||||
|
_movieService.AddMovie(mapped);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -7,6 +7,9 @@ var Profiles = require('../../../Profile/ProfileCollection');
|
||||||
var AsModelBoundView = require('../../../Mixins/AsModelBoundView');
|
var AsModelBoundView = require('../../../Mixins/AsModelBoundView');
|
||||||
var AsValidatedView = require('../../../Mixins/AsValidatedView');
|
var AsValidatedView = require('../../../Mixins/AsValidatedView');
|
||||||
var AsEditModalView = require('../../../Mixins/AsEditModalView');
|
var AsEditModalView = require('../../../Mixins/AsEditModalView');
|
||||||
|
var RootFolders = require('../../../AddMovies/RootFolders/RootFolderCollection');
|
||||||
|
var RootFolderLayout = require('../../../AddMovies/RootFolders/RootFolderLayout');
|
||||||
|
var Config = require('../../../Config');
|
||||||
require('../../../Form/FormBuilder');
|
require('../../../Form/FormBuilder');
|
||||||
require('../../../Mixins/AutoComplete');
|
require('../../../Mixins/AutoComplete');
|
||||||
require('bootstrap');
|
require('bootstrap');
|
||||||
|
@ -14,9 +17,15 @@ require('bootstrap');
|
||||||
var view = Marionette.ItemView.extend({
|
var view = Marionette.ItemView.extend({
|
||||||
template : 'Settings/NetImport/Edit/NetImportEditViewTemplate',
|
template : 'Settings/NetImport/Edit/NetImportEditViewTemplate',
|
||||||
|
|
||||||
|
ui : {
|
||||||
|
profile : '.x-profile',
|
||||||
|
rootFolder : '.x-root-folder',
|
||||||
|
},
|
||||||
|
|
||||||
events : {
|
events : {
|
||||||
'click .x-back' : '_back',
|
'click .x-back' : '_back',
|
||||||
'click .x-captcha-refresh' : '_onRefreshCaptcha'
|
'click .x-captcha-refresh' : '_onRefreshCaptcha',
|
||||||
|
'change .x-root-folder' : '_rootFolderChanged',
|
||||||
},
|
},
|
||||||
|
|
||||||
_deleteView : DeleteView,
|
_deleteView : DeleteView,
|
||||||
|
@ -24,7 +33,26 @@ var view = Marionette.ItemView.extend({
|
||||||
initialize : function(options) {
|
initialize : function(options) {
|
||||||
this.targetCollection = options.targetCollection;
|
this.targetCollection = options.targetCollection;
|
||||||
this.templateHelpers = {};
|
this.templateHelpers = {};
|
||||||
this.templateHelpers.profiles = Profiles.toJSON();
|
|
||||||
|
this._configureTemplateHelpers();
|
||||||
|
this.listenTo(this.model, 'change', this.render);
|
||||||
|
this.listenTo(RootFolders, 'all', this._rootFoldersUpdated);
|
||||||
|
},
|
||||||
|
|
||||||
|
onRender : function() {
|
||||||
|
var defaultRoot = Config.getValue(Config.Keys.DefaultRootFolderId);
|
||||||
|
if (RootFolders.get(defaultRoot)) {
|
||||||
|
this.ui.rootFolder.val(defaultRoot);
|
||||||
|
}
|
||||||
|
},
|
||||||
|
|
||||||
|
_onBeforeSave : function() {
|
||||||
|
var profile = this.ui.profile.val();
|
||||||
|
var rootFolderPath = this.ui.rootFolder.children(':selected').text();
|
||||||
|
this.model.set({
|
||||||
|
profileId : profile,
|
||||||
|
rootFolderPath : rootFolderPath,
|
||||||
|
})
|
||||||
},
|
},
|
||||||
|
|
||||||
_onAfterSave : function() {
|
_onAfterSave : function() {
|
||||||
|
@ -46,6 +74,28 @@ var view = Marionette.ItemView.extend({
|
||||||
require('../Add/NetImportSchemaModal').open(this.targetCollection);
|
require('../Add/NetImportSchemaModal').open(this.targetCollection);
|
||||||
},
|
},
|
||||||
|
|
||||||
|
_configureTemplateHelpers : function() {
|
||||||
|
this.templateHelpers.profiles = Profiles.toJSON();
|
||||||
|
this.templateHelpers.rootFolders = RootFolders.toJSON();
|
||||||
|
},
|
||||||
|
|
||||||
|
_rootFolderChanged : function() {
|
||||||
|
var rootFolderValue = this.ui.rootFolder.val();
|
||||||
|
if (rootFolderValue === 'addNew') {
|
||||||
|
var rootFolderLayout = new RootFolderLayout();
|
||||||
|
this.listenToOnce(rootFolderLayout, 'folderSelected', this._setRootFolder);
|
||||||
|
AppLayout.modalRegion.show(rootFolderLayout);
|
||||||
|
} else {
|
||||||
|
Config.setValue(Config.Keys.DefaultRootFolderId, rootFolderValue);
|
||||||
|
}
|
||||||
|
},
|
||||||
|
|
||||||
|
_rootFoldersUpdated : function() {
|
||||||
|
this._configureTemplateHelpers();
|
||||||
|
debugger;
|
||||||
|
this.render();
|
||||||
|
},
|
||||||
|
|
||||||
_onRefreshCaptcha : function(event) {
|
_onRefreshCaptcha : function(event) {
|
||||||
var self = this;
|
var self = this;
|
||||||
|
|
||||||
|
|
|
@ -48,6 +48,14 @@
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<div class="form-group">
|
||||||
|
<label class="col-sm-3 control-label">Folder</label>
|
||||||
|
|
||||||
|
<div class="col-sm-5">
|
||||||
|
{{> RootFolderSelectionPartial rootFolders}}
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
{{formBuilder}}
|
{{formBuilder}}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
|
@ -2,6 +2,7 @@ var Marionette = require('marionette');
|
||||||
var NetImportCollection = require('./NetImportCollection');
|
var NetImportCollection = require('./NetImportCollection');
|
||||||
var CollectionView = require('./NetImportCollectionView');
|
var CollectionView = require('./NetImportCollectionView');
|
||||||
var OptionsView = require('./Options/NetImportOptionsView');
|
var OptionsView = require('./Options/NetImportOptionsView');
|
||||||
|
var RootFolderCollection = require('../../AddMovies/RootFolders/RootFolderCollection');
|
||||||
|
|
||||||
module.exports = Marionette.Layout.extend({
|
module.exports = Marionette.Layout.extend({
|
||||||
template : 'Settings/NetImport/NetImportLayoutTemplate',
|
template : 'Settings/NetImport/NetImportLayoutTemplate',
|
||||||
|
@ -14,6 +15,9 @@ module.exports = Marionette.Layout.extend({
|
||||||
initialize : function() {
|
initialize : function() {
|
||||||
this.indexersCollection = new NetImportCollection();
|
this.indexersCollection = new NetImportCollection();
|
||||||
this.indexersCollection.fetch();
|
this.indexersCollection.fetch();
|
||||||
|
RootFolderCollection.fetch().done(function() {
|
||||||
|
RootFolderCollection.synced = true;
|
||||||
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
onShow : function() {
|
onShow : function() {
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue