aboutsummaryrefslogtreecommitdiff
path: root/Emby.Server.Implementations/ScheduledTasks/Tasks
diff options
context:
space:
mode:
authorVasily <JustAMan@users.noreply.github.com>2019-02-03 16:42:29 +0300
committerGitHub <noreply@github.com>2019-02-03 16:42:29 +0300
commita50fb922c5f993c96fb0e716f11d6286ad9811da (patch)
treee6076d2c37b3e9930076859ef99448eff6d6ea95 /Emby.Server.Implementations/ScheduledTasks/Tasks
parent32f393d57fd634ed9771078b5fbf87d4466a927c (diff)
parentc118f111b6eb4d0f665886f294114071ebe051a6 (diff)
Merge pull request #774 from dkanada/plugin
reimplement support for plugin repository
Diffstat (limited to 'Emby.Server.Implementations/ScheduledTasks/Tasks')
-rw-r--r--Emby.Server.Implementations/ScheduledTasks/Tasks/ChapterImagesTask.cs176
-rw-r--r--Emby.Server.Implementations/ScheduledTasks/Tasks/DeleteCacheFileTask.cs22
-rw-r--r--Emby.Server.Implementations/ScheduledTasks/Tasks/DeleteLogFileTask.cs22
-rw-r--r--Emby.Server.Implementations/ScheduledTasks/Tasks/PeopleValidationTask.cs75
-rw-r--r--Emby.Server.Implementations/ScheduledTasks/Tasks/PluginUpdateTask.cs119
-rw-r--r--Emby.Server.Implementations/ScheduledTasks/Tasks/RefreshMediaLibraryTask.cs75
6 files changed, 451 insertions, 38 deletions
diff --git a/Emby.Server.Implementations/ScheduledTasks/Tasks/ChapterImagesTask.cs b/Emby.Server.Implementations/ScheduledTasks/Tasks/ChapterImagesTask.cs
new file mode 100644
index 000000000..81fdb96d2
--- /dev/null
+++ b/Emby.Server.Implementations/ScheduledTasks/Tasks/ChapterImagesTask.cs
@@ -0,0 +1,176 @@
+using System;
+using System.Collections.Generic;
+using System.IO;
+using System.Linq;
+using System.Threading;
+using System.Threading.Tasks;
+using MediaBrowser.Common.Configuration;
+using MediaBrowser.Controller.Dto;
+using MediaBrowser.Controller.Entities;
+using MediaBrowser.Controller.Library;
+using MediaBrowser.Controller.MediaEncoding;
+using MediaBrowser.Controller.Persistence;
+using MediaBrowser.Controller.Providers;
+using MediaBrowser.Model.Entities;
+using MediaBrowser.Model.IO;
+using MediaBrowser.Model.Tasks;
+using Microsoft.Extensions.Logging;
+
+namespace Emby.Server.Implementations.ScheduledTasks
+{
+ /// <summary>
+ /// Class ChapterImagesTask
+ /// </summary>
+ class ChapterImagesTask : IScheduledTask
+ {
+ /// <summary>
+ /// The _logger
+ /// </summary>
+ private readonly ILogger _logger;
+ /// <summary>
+ /// The _library manager
+ /// </summary>
+ private readonly ILibraryManager _libraryManager;
+
+ private readonly IItemRepository _itemRepo;
+
+ private readonly IApplicationPaths _appPaths;
+
+ private readonly IEncodingManager _encodingManager;
+ private readonly IFileSystem _fileSystem;
+
+ /// <summary>
+ /// Initializes a new instance of the <see cref="ChapterImagesTask" /> class.
+ /// </summary>
+ public ChapterImagesTask(ILoggerFactory loggerFactory, ILibraryManager libraryManager, IItemRepository itemRepo, IApplicationPaths appPaths, IEncodingManager encodingManager, IFileSystem fileSystem)
+ {
+ _logger = loggerFactory.CreateLogger(GetType().Name);
+ _libraryManager = libraryManager;
+ _itemRepo = itemRepo;
+ _appPaths = appPaths;
+ _encodingManager = encodingManager;
+ _fileSystem = fileSystem;
+ }
+
+ /// <summary>
+ /// Creates the triggers that define when the task will run
+ /// </summary>
+ public IEnumerable<TaskTriggerInfo> GetDefaultTriggers()
+ {
+ return new[] {
+
+ new TaskTriggerInfo
+ {
+ Type = TaskTriggerInfo.TriggerDaily,
+ TimeOfDayTicks = TimeSpan.FromHours(2).Ticks,
+ MaxRuntimeTicks = TimeSpan.FromHours(4).Ticks
+ }
+ };
+ }
+
+ /// <summary>
+ /// Returns the task to be executed
+ /// </summary>
+ /// <param name="cancellationToken">The cancellation token.</param>
+ /// <param name="progress">The progress.</param>
+ /// <returns>Task.</returns>
+ public async Task Execute(CancellationToken cancellationToken, IProgress<double> progress)
+ {
+ var videos = _libraryManager.GetItemList(new InternalItemsQuery
+ {
+ MediaTypes = new[] { MediaType.Video },
+ IsFolder = false,
+ Recursive = true,
+ DtoOptions = new DtoOptions(false)
+ {
+ EnableImages = false
+ },
+ SourceTypes = new SourceType[] { SourceType.Library },
+ HasChapterImages = false,
+ IsVirtualItem = false
+
+ })
+ .OfType<Video>()
+ .ToList();
+
+ var numComplete = 0;
+
+ var failHistoryPath = Path.Combine(_appPaths.CachePath, "chapter-failures.txt");
+
+ List<string> previouslyFailedImages;
+
+ if (File.Exists(failHistoryPath))
+ {
+ try
+ {
+ previouslyFailedImages = File.ReadAllText(failHistoryPath)
+ .Split(new[] { '|' }, StringSplitOptions.RemoveEmptyEntries)
+ .ToList();
+ }
+ catch (IOException)
+ {
+ previouslyFailedImages = new List<string>();
+ }
+ }
+ else
+ {
+ previouslyFailedImages = new List<string>();
+ }
+
+ var directoryService = new DirectoryService(_logger, _fileSystem);
+
+ foreach (var video in videos)
+ {
+ cancellationToken.ThrowIfCancellationRequested();
+
+ var key = video.Path + video.DateModified.Ticks;
+
+ var extract = !previouslyFailedImages.Contains(key, StringComparer.OrdinalIgnoreCase);
+
+ try
+ {
+ var chapters = _itemRepo.GetChapters(video);
+
+ var success = await _encodingManager.RefreshChapterImages(video, directoryService, chapters, extract, true, cancellationToken).ConfigureAwait(false);
+
+ if (!success)
+ {
+ previouslyFailedImages.Add(key);
+
+ var parentPath = Path.GetDirectoryName(failHistoryPath);
+
+ Directory.CreateDirectory(parentPath);
+
+ string text = string.Join("|", previouslyFailedImages);
+ File.WriteAllText(failHistoryPath, text);
+ }
+
+ numComplete++;
+ double percent = numComplete;
+ percent /= videos.Count;
+
+ progress.Report(100 * percent);
+ }
+ catch (ObjectDisposedException)
+ {
+ //TODO Investigate and properly fix.
+ break;
+ }
+ }
+ }
+
+ public string Name => "Chapter image extraction";
+
+ public string Description => "Creates thumbnails for videos that have chapters.";
+
+ public string Category => "Library";
+
+ public string Key => "RefreshChapterImages";
+
+ public bool IsHidden => false;
+
+ public bool IsEnabled => true;
+
+ public bool IsLogged => true;
+ }
+}
diff --git a/Emby.Server.Implementations/ScheduledTasks/Tasks/DeleteCacheFileTask.cs b/Emby.Server.Implementations/ScheduledTasks/Tasks/DeleteCacheFileTask.cs
index 52077b242..6ec83b5c0 100644
--- a/Emby.Server.Implementations/ScheduledTasks/Tasks/DeleteCacheFileTask.cs
+++ b/Emby.Server.Implementations/ScheduledTasks/Tasks/DeleteCacheFileTask.cs
@@ -158,31 +158,15 @@ namespace Emby.Server.Implementations.ScheduledTasks.Tasks
}
}
- /// <summary>
- /// Gets the name of the task
- /// </summary>
- /// <value>The name.</value>
public string Name => "Cache file cleanup";
- public string Key => "DeleteCacheFiles";
-
- /// <summary>
- /// Gets the description.
- /// </summary>
- /// <value>The description.</value>
public string Description => "Deletes cache files no longer needed by the system";
- /// <summary>
- /// Gets the category.
- /// </summary>
- /// <value>The category.</value>
public string Category => "Maintenance";
- /// <summary>
- /// Gets a value indicating whether this instance is hidden.
- /// </summary>
- /// <value><c>true</c> if this instance is hidden; otherwise, <c>false</c>.</value>
- public bool IsHidden => true;
+ public string Key => "DeleteCacheFiles";
+
+ public bool IsHidden => false;
public bool IsEnabled => true;
diff --git a/Emby.Server.Implementations/ScheduledTasks/Tasks/DeleteLogFileTask.cs b/Emby.Server.Implementations/ScheduledTasks/Tasks/DeleteLogFileTask.cs
index a57fe4945..e468c301a 100644
--- a/Emby.Server.Implementations/ScheduledTasks/Tasks/DeleteLogFileTask.cs
+++ b/Emby.Server.Implementations/ScheduledTasks/Tasks/DeleteLogFileTask.cs
@@ -81,31 +81,15 @@ namespace Emby.Server.Implementations.ScheduledTasks.Tasks
return Task.CompletedTask;
}
- public string Key => "CleanLogFiles";
-
- /// <summary>
- /// Gets the name of the task
- /// </summary>
- /// <value>The name.</value>
public string Name => "Log file cleanup";
- /// <summary>
- /// Gets the description.
- /// </summary>
- /// <value>The description.</value>
public string Description => string.Format("Deletes log files that are more than {0} days old.", ConfigurationManager.CommonConfiguration.LogFileRetentionDays);
- /// <summary>
- /// Gets the category.
- /// </summary>
- /// <value>The category.</value>
public string Category => "Maintenance";
- /// <summary>
- /// Gets a value indicating whether this instance is hidden.
- /// </summary>
- /// <value><c>true</c> if this instance is hidden; otherwise, <c>false</c>.</value>
- public bool IsHidden => true;
+ public string Key => "CleanLogFiles";
+
+ public bool IsHidden => false;
public bool IsEnabled => true;
diff --git a/Emby.Server.Implementations/ScheduledTasks/Tasks/PeopleValidationTask.cs b/Emby.Server.Implementations/ScheduledTasks/Tasks/PeopleValidationTask.cs
new file mode 100644
index 000000000..d70799c47
--- /dev/null
+++ b/Emby.Server.Implementations/ScheduledTasks/Tasks/PeopleValidationTask.cs
@@ -0,0 +1,75 @@
+using System;
+using System.Collections.Generic;
+using System.Threading;
+using System.Threading.Tasks;
+using MediaBrowser.Controller;
+using MediaBrowser.Controller.Library;
+using MediaBrowser.Model.Tasks;
+
+namespace Emby.Server.Implementations.ScheduledTasks
+{
+ /// <summary>
+ /// Class PeopleValidationTask
+ /// </summary>
+ public class PeopleValidationTask : IScheduledTask
+ {
+ /// <summary>
+ /// The _library manager
+ /// </summary>
+ private readonly ILibraryManager _libraryManager;
+
+ private readonly IServerApplicationHost _appHost;
+
+ /// <summary>
+ /// Initializes a new instance of the <see cref="PeopleValidationTask" /> class.
+ /// </summary>
+ /// <param name="libraryManager">The library manager.</param>
+ /// <param name="appHost">The server application host</param>
+ public PeopleValidationTask(ILibraryManager libraryManager, IServerApplicationHost appHost)
+ {
+ _libraryManager = libraryManager;
+ _appHost = appHost;
+ }
+
+ /// <summary>
+ /// Creates the triggers that define when the task will run
+ /// </summary>
+ public IEnumerable<TaskTriggerInfo> GetDefaultTriggers()
+ {
+ return new[]
+ {
+ // Every so often
+ new TaskTriggerInfo
+ {
+ Type = TaskTriggerInfo.TriggerInterval,
+ IntervalTicks = TimeSpan.FromDays(7).Ticks
+ }
+ };
+ }
+
+ /// <summary>
+ /// Returns the task to be executed
+ /// </summary>
+ /// <param name="cancellationToken">The cancellation token.</param>
+ /// <param name="progress">The progress.</param>
+ /// <returns>Task.</returns>
+ public Task Execute(CancellationToken cancellationToken, IProgress<double> progress)
+ {
+ return _libraryManager.ValidatePeople(cancellationToken, progress);
+ }
+
+ public string Name => "Refresh people";
+
+ public string Description => "Updates metadata for actors and directors in your media library.";
+
+ public string Category => "Library";
+
+ public string Key => "RefreshPeople";
+
+ public bool IsHidden => false;
+
+ public bool IsEnabled => true;
+
+ public bool IsLogged => true;
+ }
+}
diff --git a/Emby.Server.Implementations/ScheduledTasks/Tasks/PluginUpdateTask.cs b/Emby.Server.Implementations/ScheduledTasks/Tasks/PluginUpdateTask.cs
new file mode 100644
index 000000000..c6431c311
--- /dev/null
+++ b/Emby.Server.Implementations/ScheduledTasks/Tasks/PluginUpdateTask.cs
@@ -0,0 +1,119 @@
+using MediaBrowser.Common;
+using MediaBrowser.Common.Updates;
+using MediaBrowser.Model.Net;
+using System;
+using System.Collections.Generic;
+using System.IO;
+using System.Linq;
+using System.Threading;
+using System.Threading.Tasks;
+using MediaBrowser.Common.Progress;
+using MediaBrowser.Model.Tasks;
+using Microsoft.Extensions.Logging;
+
+namespace Emby.Server.Implementations.ScheduledTasks
+{
+ /// <summary>
+ /// Plugin Update Task
+ /// </summary>
+ public class PluginUpdateTask : IScheduledTask, IConfigurableScheduledTask
+ {
+ /// <summary>
+ /// The _logger
+ /// </summary>
+ private readonly ILogger _logger;
+
+ private readonly IInstallationManager _installationManager;
+
+ private readonly IApplicationHost _appHost;
+
+ public PluginUpdateTask(ILogger logger, IInstallationManager installationManager, IApplicationHost appHost)
+ {
+ _logger = logger;
+ _installationManager = installationManager;
+ _appHost = appHost;
+ }
+
+ /// <summary>
+ /// Creates the triggers that define when the task will run
+ /// </summary>
+ /// <returns>IEnumerable{BaseTaskTrigger}.</returns>
+ public IEnumerable<TaskTriggerInfo> GetDefaultTriggers()
+ {
+ return new[] {
+
+ // At startup
+ new TaskTriggerInfo {Type = TaskTriggerInfo.TriggerStartup},
+
+ // Every so often
+ new TaskTriggerInfo { Type = TaskTriggerInfo.TriggerInterval, IntervalTicks = TimeSpan.FromHours(24).Ticks}
+ };
+ }
+
+ /// <summary>
+ /// Update installed plugins
+ /// </summary>
+ /// <param name="cancellationToken">The cancellation token.</param>
+ /// <param name="progress">The progress.</param>
+ /// <returns>Task.</returns>
+ public async Task Execute(CancellationToken cancellationToken, IProgress<double> progress)
+ {
+ progress.Report(0);
+
+ var packagesToInstall = (await _installationManager.GetAvailablePluginUpdates(typeof(PluginUpdateTask).Assembly.GetName().Version, true, cancellationToken).ConfigureAwait(false)).ToList();
+
+ progress.Report(10);
+
+ var numComplete = 0;
+
+ foreach (var package in packagesToInstall)
+ {
+ cancellationToken.ThrowIfCancellationRequested();
+
+ try
+ {
+ await _installationManager.InstallPackage(package, true, new SimpleProgress<double>(), cancellationToken).ConfigureAwait(false);
+ }
+ catch (OperationCanceledException)
+ {
+ // InstallPackage has it's own inner cancellation token, so only throw this if it's ours
+ if (cancellationToken.IsCancellationRequested)
+ {
+ throw;
+ }
+ }
+ catch (HttpException ex)
+ {
+ _logger.LogError(ex, "Error downloading {0}", package.name);
+ }
+ catch (IOException ex)
+ {
+ _logger.LogError(ex, "Error updating {0}", package.name);
+ }
+
+ // Update progress
+ lock (progress)
+ {
+ numComplete++;
+ progress.Report(90.0 * numComplete / packagesToInstall.Count + 10);
+ }
+ }
+
+ progress.Report(100);
+ }
+
+ public string Name => "Check for plugin updates";
+
+ public string Description => "Downloads and installs updates for plugins that are configured to update automatically.";
+
+ public string Category => "Application";
+
+ public string Key => "PluginUpdates";
+
+ public bool IsHidden => false;
+
+ public bool IsEnabled => true;
+
+ public bool IsLogged => true;
+ }
+}
diff --git a/Emby.Server.Implementations/ScheduledTasks/Tasks/RefreshMediaLibraryTask.cs b/Emby.Server.Implementations/ScheduledTasks/Tasks/RefreshMediaLibraryTask.cs
new file mode 100644
index 000000000..1a3d85ad7
--- /dev/null
+++ b/Emby.Server.Implementations/ScheduledTasks/Tasks/RefreshMediaLibraryTask.cs
@@ -0,0 +1,75 @@
+using System;
+using System.Collections.Generic;
+using System.Threading;
+using System.Threading.Tasks;
+using Emby.Server.Implementations.Library;
+using MediaBrowser.Controller.Configuration;
+using MediaBrowser.Controller.Library;
+using MediaBrowser.Model.Tasks;
+
+namespace Emby.Server.Implementations.ScheduledTasks
+{
+ /// <summary>
+ /// Class RefreshMediaLibraryTask
+ /// </summary>
+ public class RefreshMediaLibraryTask : IScheduledTask
+ {
+ /// <summary>
+ /// The _library manager
+ /// </summary>
+ private readonly ILibraryManager _libraryManager;
+ private readonly IServerConfigurationManager _config;
+
+ /// <summary>
+ /// Initializes a new instance of the <see cref="RefreshMediaLibraryTask" /> class.
+ /// </summary>
+ /// <param name="libraryManager">The library manager.</param>
+ public RefreshMediaLibraryTask(ILibraryManager libraryManager, IServerConfigurationManager config)
+ {
+ _libraryManager = libraryManager;
+ _config = config;
+ }
+
+ /// <summary>
+ /// Creates the triggers that define when the task will run
+ /// </summary>
+ /// <returns>IEnumerable{BaseTaskTrigger}.</returns>
+ public IEnumerable<TaskTriggerInfo> GetDefaultTriggers()
+ {
+ return new[] {
+
+ // Every so often
+ new TaskTriggerInfo { Type = TaskTriggerInfo.TriggerInterval, IntervalTicks = TimeSpan.FromHours(12).Ticks}
+ };
+ }
+
+ /// <summary>
+ /// Executes the internal.
+ /// </summary>
+ /// <param name="cancellationToken">The cancellation token.</param>
+ /// <param name="progress">The progress.</param>
+ /// <returns>Task.</returns>
+ public Task Execute(CancellationToken cancellationToken, IProgress<double> progress)
+ {
+ cancellationToken.ThrowIfCancellationRequested();
+
+ progress.Report(0);
+
+ return ((LibraryManager)_libraryManager).ValidateMediaLibraryInternal(progress, cancellationToken);
+ }
+
+ public string Name => "Scan media library";
+
+ public string Description => "Scans your media library and refreshes metatata based on configuration.";
+
+ public string Category => "Library";
+
+ public string Key => "RefreshLibrary";
+
+ public bool IsHidden => false;
+
+ public bool IsEnabled => true;
+
+ public bool IsLogged => true;
+ }
+}