mirror of https://github.com/jellyfin/jellyfin.git
More DI
This commit is contained in:
parent
6c86721f6d
commit
8ce3e74e81
|
@ -5,13 +5,13 @@ using System;
|
|||
using System.IO;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace MediaBrowser.ApiInteraction.Javascript
|
||||
namespace MediaBrowser.Api.Javascript
|
||||
{
|
||||
/// <summary>
|
||||
/// Class GetJavascriptApiClient
|
||||
/// </summary>
|
||||
[Route("/JsApiClient.js", "GET")]
|
||||
[Api(("Gets an api wrapper in Javascript"))]
|
||||
[ServiceStack.ServiceHost.Api(("Gets an api wrapper in Javascript"))]
|
||||
public class GetJavascriptApiClient
|
||||
{
|
||||
/// <summary>
|
||||
|
@ -52,7 +52,7 @@ namespace MediaBrowser.ApiInteraction.Javascript
|
|||
/// <returns>Stream.</returns>
|
||||
private Task<Stream> GetStream()
|
||||
{
|
||||
return Task.FromResult(GetType().Assembly.GetManifestResourceStream("MediaBrowser.ApiInteraction.Javascript.ApiClient.js"));
|
||||
return Task.FromResult(GetType().Assembly.GetManifestResourceStream("MediaBrowser.Api.Javascript.ApiClient.js"));
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,4 +1,5 @@
|
|||
using MediaBrowser.Common.Net;
|
||||
using MediaBrowser.Common.Kernel;
|
||||
using MediaBrowser.Common.Net;
|
||||
using MediaBrowser.Controller;
|
||||
using MediaBrowser.Controller.Entities;
|
||||
using MediaBrowser.Controller.Library;
|
||||
|
@ -97,6 +98,26 @@ namespace MediaBrowser.Api
|
|||
/// </summary>
|
||||
public class LibraryService : BaseRestService
|
||||
{
|
||||
/// <summary>
|
||||
/// The _app host
|
||||
/// </summary>
|
||||
private readonly IApplicationHost _appHost;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="LibraryService" /> class.
|
||||
/// </summary>
|
||||
/// <param name="appHost">The app host.</param>
|
||||
/// <exception cref="System.ArgumentNullException">appHost</exception>
|
||||
public LibraryService(IApplicationHost appHost)
|
||||
{
|
||||
if (appHost == null)
|
||||
{
|
||||
throw new ArgumentNullException("appHost");
|
||||
}
|
||||
|
||||
_appHost = appHost;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the specified request.
|
||||
/// </summary>
|
||||
|
@ -210,7 +231,7 @@ namespace MediaBrowser.Api
|
|||
{
|
||||
var kernel = (Kernel)Kernel;
|
||||
|
||||
var allTypes = kernel.AllTypes.Where(t => !t.IsAbstract && t.IsSubclassOf(typeof(BaseItem)));
|
||||
var allTypes = _appHost.AllConcreteTypes.Where(t => t.IsSubclassOf(typeof(BaseItem)));
|
||||
|
||||
if (request.HasInternetProvider)
|
||||
{
|
||||
|
|
|
@ -80,6 +80,7 @@
|
|||
<Compile Include="Images\ImageService.cs" />
|
||||
<Compile Include="Images\ImageWriter.cs" />
|
||||
<Compile Include="Images\UploadImageHandler.cs" />
|
||||
<Compile Include="Javascript\JavascriptApiClientService.cs" />
|
||||
<Compile Include="LibraryService.cs" />
|
||||
<Compile Include="LocalizationService.cs" />
|
||||
<Compile Include="PackageService.cs" />
|
||||
|
@ -128,6 +129,7 @@
|
|||
<None Include="packages.config" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<EmbeddedResource Include="Javascript\ApiClient.js" />
|
||||
<Content Include="options.xml" />
|
||||
</ItemGroup>
|
||||
<ItemGroup />
|
||||
|
|
|
@ -1,15 +1,15 @@
|
|||
using MediaBrowser.Common.Extensions;
|
||||
using MediaBrowser.Common.Net;
|
||||
using MediaBrowser.Common.Serialization;
|
||||
using MediaBrowser.Controller;
|
||||
using MediaBrowser.Model.Entities;
|
||||
using MediaBrowser.Model.Plugins;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
using ServiceStack.ServiceHost;
|
||||
using ServiceStack.Text.Controller;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
using System.Linq;
|
||||
using ServiceStack.Text.Controller;
|
||||
|
||||
namespace MediaBrowser.Api
|
||||
{
|
||||
|
@ -119,6 +119,27 @@ namespace MediaBrowser.Api
|
|||
/// </summary>
|
||||
public class PluginService : BaseRestService
|
||||
{
|
||||
/// <summary>
|
||||
/// The _json serializer
|
||||
/// </summary>
|
||||
private readonly IJsonSerializer _jsonSerializer;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="PluginService" /> class.
|
||||
/// </summary>
|
||||
/// <param name="jsonSerializer">The json serializer.</param>
|
||||
/// <exception cref="System.ArgumentNullException">jsonSerializer</exception>
|
||||
public PluginService(IJsonSerializer jsonSerializer)
|
||||
: base()
|
||||
{
|
||||
if (jsonSerializer == null)
|
||||
{
|
||||
throw new ArgumentNullException("jsonSerializer");
|
||||
}
|
||||
|
||||
_jsonSerializer = jsonSerializer;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the specified request.
|
||||
/// </summary>
|
||||
|
@ -198,7 +219,7 @@ namespace MediaBrowser.Api
|
|||
{
|
||||
var kernel = (Kernel)Kernel;
|
||||
|
||||
var info = JsonSerializer.DeserializeFromStream<PluginSecurityInfo>(request.RequestStream);
|
||||
var info = _jsonSerializer.DeserializeFromStream<PluginSecurityInfo>(request.RequestStream);
|
||||
|
||||
kernel.PluginSecurityManager.SupporterKey = info.SupporterKey;
|
||||
kernel.PluginSecurityManager.LegacyKey = info.LegacyKey;
|
||||
|
@ -217,7 +238,7 @@ namespace MediaBrowser.Api
|
|||
|
||||
var plugin = Kernel.Plugins.First(p => p.Id == id);
|
||||
|
||||
var configuration = JsonSerializer.DeserializeFromStream(request.RequestStream, plugin.ConfigurationType) as BasePluginConfiguration;
|
||||
var configuration = _jsonSerializer.DeserializeFromStream(request.RequestStream, plugin.ConfigurationType) as BasePluginConfiguration;
|
||||
|
||||
plugin.UpdateConfiguration(configuration);
|
||||
}
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
using MediaBrowser.Common.Extensions;
|
||||
using MediaBrowser.Common.Net;
|
||||
using MediaBrowser.Common.ScheduledTasks;
|
||||
using MediaBrowser.Common.Serialization;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
using MediaBrowser.Model.Tasks;
|
||||
using ServiceStack.ServiceHost;
|
||||
using System;
|
||||
|
@ -90,11 +90,32 @@ namespace MediaBrowser.Api.ScheduledTasks
|
|||
/// <value>The task manager.</value>
|
||||
private ITaskManager TaskManager { get; set; }
|
||||
|
||||
public ScheduledTaskService(ITaskManager taskManager)
|
||||
/// <summary>
|
||||
/// The _json serializer
|
||||
/// </summary>
|
||||
private readonly IJsonSerializer _jsonSerializer;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="ScheduledTaskService" /> class.
|
||||
/// </summary>
|
||||
/// <param name="taskManager">The task manager.</param>
|
||||
/// <param name="jsonSerializer">The json serializer.</param>
|
||||
/// <exception cref="System.ArgumentNullException">taskManager</exception>
|
||||
public ScheduledTaskService(ITaskManager taskManager, IJsonSerializer jsonSerializer)
|
||||
{
|
||||
if (taskManager == null)
|
||||
{
|
||||
throw new ArgumentNullException("taskManager");
|
||||
}
|
||||
if (jsonSerializer == null)
|
||||
{
|
||||
throw new ArgumentNullException("jsonSerializer");
|
||||
}
|
||||
|
||||
TaskManager = taskManager;
|
||||
_jsonSerializer = jsonSerializer;
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Gets the specified request.
|
||||
/// </summary>
|
||||
|
@ -113,6 +134,7 @@ namespace MediaBrowser.Api.ScheduledTasks
|
|||
/// </summary>
|
||||
/// <param name="request">The request.</param>
|
||||
/// <returns>IEnumerable{TaskInfo}.</returns>
|
||||
/// <exception cref="MediaBrowser.Common.Extensions.ResourceNotFoundException">Task not found</exception>
|
||||
public object Get(GetScheduledTask request)
|
||||
{
|
||||
var task = TaskManager.ScheduledTasks.FirstOrDefault(i => i.Id == request.Id);
|
||||
|
@ -131,6 +153,7 @@ namespace MediaBrowser.Api.ScheduledTasks
|
|||
/// Posts the specified request.
|
||||
/// </summary>
|
||||
/// <param name="request">The request.</param>
|
||||
/// <exception cref="MediaBrowser.Common.Extensions.ResourceNotFoundException">Task not found</exception>
|
||||
public void Post(StartScheduledTask request)
|
||||
{
|
||||
var task = TaskManager.ScheduledTasks.FirstOrDefault(i => i.Id == request.Id);
|
||||
|
@ -147,6 +170,7 @@ namespace MediaBrowser.Api.ScheduledTasks
|
|||
/// Posts the specified request.
|
||||
/// </summary>
|
||||
/// <param name="request">The request.</param>
|
||||
/// <exception cref="MediaBrowser.Common.Extensions.ResourceNotFoundException">Task not found</exception>
|
||||
public void Delete(StopScheduledTask request)
|
||||
{
|
||||
var task = TaskManager.ScheduledTasks.FirstOrDefault(i => i.Id == request.Id);
|
||||
|
@ -163,6 +187,7 @@ namespace MediaBrowser.Api.ScheduledTasks
|
|||
/// Posts the specified request.
|
||||
/// </summary>
|
||||
/// <param name="request">The request.</param>
|
||||
/// <exception cref="MediaBrowser.Common.Extensions.ResourceNotFoundException">Task not found</exception>
|
||||
public void Post(UpdateScheduledTaskTriggers request)
|
||||
{
|
||||
// We need to parse this manually because we told service stack not to with IRequiresRequestStream
|
||||
|
@ -177,7 +202,7 @@ namespace MediaBrowser.Api.ScheduledTasks
|
|||
throw new ResourceNotFoundException("Task not found");
|
||||
}
|
||||
|
||||
var triggerInfos = JsonSerializer.DeserializeFromStream<TaskTriggerInfo[]>(request.RequestStream);
|
||||
var triggerInfos = _jsonSerializer.DeserializeFromStream<TaskTriggerInfo[]>(request.RequestStream);
|
||||
|
||||
task.Triggers = triggerInfos.Select(ScheduledTaskHelpers.GetTrigger);
|
||||
}
|
||||
|
|
|
@ -1,15 +1,19 @@
|
|||
using MediaBrowser.Common.Extensions;
|
||||
using MediaBrowser.Common.Net;
|
||||
using MediaBrowser.Common.Serialization;
|
||||
using MediaBrowser.Controller;
|
||||
using MediaBrowser.Model.Configuration;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
using MediaBrowser.Model.System;
|
||||
using ServiceStack.ServiceHost;
|
||||
using System;
|
||||
using System.IO;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace MediaBrowser.Api
|
||||
{
|
||||
/// <summary>
|
||||
/// Class GetSystemInfo
|
||||
/// </summary>
|
||||
[Route("/System/Info", "GET")]
|
||||
public class GetSystemInfo : IReturn<SystemInfo>
|
||||
{
|
||||
|
@ -40,6 +44,10 @@ namespace MediaBrowser.Api
|
|||
[Route("/System/Configuration", "POST")]
|
||||
public class UpdateConfiguration : IRequiresRequestStream
|
||||
{
|
||||
/// <summary>
|
||||
/// The raw Http Request Input Stream
|
||||
/// </summary>
|
||||
/// <value>The request stream.</value>
|
||||
public Stream RequestStream { get; set; }
|
||||
}
|
||||
|
||||
|
@ -48,6 +56,27 @@ namespace MediaBrowser.Api
|
|||
/// </summary>
|
||||
public class SystemService : BaseRestService
|
||||
{
|
||||
/// <summary>
|
||||
/// The _json serializer
|
||||
/// </summary>
|
||||
private readonly IJsonSerializer _jsonSerializer;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="SystemService" /> class.
|
||||
/// </summary>
|
||||
/// <param name="jsonSerializer">The json serializer.</param>
|
||||
/// <exception cref="System.ArgumentNullException">jsonSerializer</exception>
|
||||
public SystemService(IJsonSerializer jsonSerializer)
|
||||
: base()
|
||||
{
|
||||
if (jsonSerializer == null)
|
||||
{
|
||||
throw new ArgumentNullException("jsonSerializer");
|
||||
}
|
||||
|
||||
_jsonSerializer = jsonSerializer;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the specified request.
|
||||
/// </summary>
|
||||
|
@ -95,8 +124,8 @@ namespace MediaBrowser.Api
|
|||
/// <param name="request">The request.</param>
|
||||
public void Post(UpdateConfiguration request)
|
||||
{
|
||||
var serverConfig = JsonSerializer.DeserializeFromStream<ServerConfiguration>(request.RequestStream);
|
||||
|
||||
var serverConfig = _jsonSerializer.DeserializeFromStream<ServerConfiguration>(request.RequestStream);
|
||||
|
||||
var kernel = (Kernel)Kernel;
|
||||
|
||||
kernel.UpdateConfiguration(serverConfig);
|
||||
|
|
|
@ -1,11 +1,11 @@
|
|||
using MediaBrowser.Common.Net;
|
||||
using MediaBrowser.Common.Serialization;
|
||||
using MediaBrowser.Controller;
|
||||
using MediaBrowser.Controller.Entities;
|
||||
using MediaBrowser.Controller.Entities.Movies;
|
||||
using MediaBrowser.Controller.Library;
|
||||
using MediaBrowser.Model.Dto;
|
||||
using MediaBrowser.Model.Entities;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
using ServiceStack.ServiceHost;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
|
@ -28,7 +28,7 @@ namespace MediaBrowser.Api.UserLibrary
|
|||
/// </summary>
|
||||
/// <value>The user id.</value>
|
||||
public Guid UserId { get; set; }
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the id.
|
||||
/// </summary>
|
||||
|
@ -48,7 +48,7 @@ namespace MediaBrowser.Api.UserLibrary
|
|||
/// </summary>
|
||||
/// <value>The user id.</value>
|
||||
public Guid UserId { get; set; }
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the item id.
|
||||
/// </summary>
|
||||
|
@ -68,7 +68,7 @@ namespace MediaBrowser.Api.UserLibrary
|
|||
/// </summary>
|
||||
/// <value>The user id.</value>
|
||||
public Guid UserId { get; set; }
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the id.
|
||||
/// </summary>
|
||||
|
@ -106,7 +106,7 @@ namespace MediaBrowser.Api.UserLibrary
|
|||
/// </summary>
|
||||
/// <value>The user id.</value>
|
||||
public Guid UserId { get; set; }
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the id.
|
||||
/// </summary>
|
||||
|
@ -125,7 +125,7 @@ namespace MediaBrowser.Api.UserLibrary
|
|||
/// </summary>
|
||||
/// <value>The user id.</value>
|
||||
public Guid UserId { get; set; }
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the id.
|
||||
/// </summary>
|
||||
|
@ -144,7 +144,7 @@ namespace MediaBrowser.Api.UserLibrary
|
|||
/// </summary>
|
||||
/// <value>The user id.</value>
|
||||
public Guid UserId { get; set; }
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the id.
|
||||
/// </summary>
|
||||
|
@ -163,7 +163,7 @@ namespace MediaBrowser.Api.UserLibrary
|
|||
/// </summary>
|
||||
/// <value>The user id.</value>
|
||||
public Guid UserId { get; set; }
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the id.
|
||||
/// </summary>
|
||||
|
@ -215,6 +215,9 @@ namespace MediaBrowser.Api.UserLibrary
|
|||
public string Id { get; set; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Class GetLocalTrailers
|
||||
/// </summary>
|
||||
[Route("/Users/{UserId}/Items/{Id}/LocalTrailers", "GET")]
|
||||
public class GetLocalTrailers : IReturn<List<BaseItemDto>>
|
||||
{
|
||||
|
@ -231,6 +234,9 @@ namespace MediaBrowser.Api.UserLibrary
|
|||
public string Id { get; set; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Class GetSpecialFeatures
|
||||
/// </summary>
|
||||
[Route("/Users/{UserId}/Items/{Id}/SpecialFeatures", "GET")]
|
||||
public class GetSpecialFeatures : IReturn<List<BaseItemDto>>
|
||||
{
|
||||
|
@ -253,6 +259,32 @@ namespace MediaBrowser.Api.UserLibrary
|
|||
/// </summary>
|
||||
public class UserLibraryService : BaseRestService
|
||||
{
|
||||
/// <summary>
|
||||
/// The _json serializer
|
||||
/// </summary>
|
||||
private readonly IJsonSerializer _jsonSerializer;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="UserLibraryService" /> class.
|
||||
/// </summary>
|
||||
/// <param name="jsonSerializer">The json serializer.</param>
|
||||
/// <exception cref="System.ArgumentNullException">jsonSerializer</exception>
|
||||
public UserLibraryService(IJsonSerializer jsonSerializer)
|
||||
: base()
|
||||
{
|
||||
if (jsonSerializer == null)
|
||||
{
|
||||
throw new ArgumentNullException("jsonSerializer");
|
||||
}
|
||||
|
||||
_jsonSerializer = jsonSerializer;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the specified request.
|
||||
/// </summary>
|
||||
/// <param name="request">The request.</param>
|
||||
/// <returns>System.Object.</returns>
|
||||
public object Get(GetSpecialFeatures request)
|
||||
{
|
||||
var kernel = (Kernel)Kernel;
|
||||
|
@ -260,7 +292,7 @@ namespace MediaBrowser.Api.UserLibrary
|
|||
var user = kernel.GetUserById(request.UserId);
|
||||
|
||||
var item = DtoBuilder.GetItemByClientId(request.Id, user.Id);
|
||||
|
||||
|
||||
// Get everything
|
||||
var fields = Enum.GetNames(typeof(ItemFields)).Select(i => (ItemFields)Enum.Parse(typeof(ItemFields), i, true)).ToList();
|
||||
|
||||
|
@ -272,7 +304,12 @@ namespace MediaBrowser.Api.UserLibrary
|
|||
|
||||
return ToOptimizedResult(items);
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Gets the specified request.
|
||||
/// </summary>
|
||||
/// <param name="request">The request.</param>
|
||||
/// <returns>System.Object.</returns>
|
||||
public object Get(GetLocalTrailers request)
|
||||
{
|
||||
var kernel = (Kernel)Kernel;
|
||||
|
@ -280,7 +317,7 @@ namespace MediaBrowser.Api.UserLibrary
|
|||
var user = kernel.GetUserById(request.UserId);
|
||||
|
||||
var item = DtoBuilder.GetItemByClientId(request.Id, user.Id);
|
||||
|
||||
|
||||
// Get everything
|
||||
var fields = Enum.GetNames(typeof(ItemFields)).Select(i => (ItemFields)Enum.Parse(typeof(ItemFields), i, true)).ToList();
|
||||
|
||||
|
@ -290,7 +327,7 @@ namespace MediaBrowser.Api.UserLibrary
|
|||
|
||||
return ToOptimizedResult(items);
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Gets the specified request.
|
||||
/// </summary>
|
||||
|
@ -303,7 +340,7 @@ namespace MediaBrowser.Api.UserLibrary
|
|||
var user = kernel.GetUserById(request.UserId);
|
||||
|
||||
var item = string.IsNullOrEmpty(request.Id) ? user.RootFolder : DtoBuilder.GetItemByClientId(request.Id, user.Id);
|
||||
|
||||
|
||||
// Get everything
|
||||
var fields = Enum.GetNames(typeof(ItemFields)).Select(i => (ItemFields)Enum.Parse(typeof(ItemFields), i, true)).ToList();
|
||||
|
||||
|
@ -366,7 +403,7 @@ namespace MediaBrowser.Api.UserLibrary
|
|||
|
||||
var item = (Folder)DtoBuilder.GetItemByClientId(itemId, user.Id);
|
||||
|
||||
var displayPreferences = JsonSerializer.DeserializeFromStream<DisplayPreferences>(request.RequestStream);
|
||||
var displayPreferences = _jsonSerializer.DeserializeFromStream<DisplayPreferences>(request.RequestStream);
|
||||
|
||||
var task = kernel.LibraryManager.SaveDisplayPreferencesForFolder(user, item, displayPreferences);
|
||||
|
||||
|
|
|
@ -1,16 +1,16 @@
|
|||
using MediaBrowser.Common.Extensions;
|
||||
using MediaBrowser.Common.Net;
|
||||
using MediaBrowser.Common.Serialization;
|
||||
using MediaBrowser.Controller;
|
||||
using MediaBrowser.Controller.Library;
|
||||
using MediaBrowser.Model.Dto;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
using ServiceStack.ServiceHost;
|
||||
using ServiceStack.Text.Controller;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
using System.Linq;
|
||||
using System.Threading.Tasks;
|
||||
using ServiceStack.Text.Controller;
|
||||
|
||||
namespace MediaBrowser.Api
|
||||
{
|
||||
|
@ -135,6 +135,39 @@ namespace MediaBrowser.Api
|
|||
/// </summary>
|
||||
public class UserService : BaseRestService
|
||||
{
|
||||
/// <summary>
|
||||
/// The _XML serializer
|
||||
/// </summary>
|
||||
private readonly IXmlSerializer _xmlSerializer;
|
||||
|
||||
/// <summary>
|
||||
/// The _json serializer
|
||||
/// </summary>
|
||||
private readonly IJsonSerializer _jsonSerializer;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="UserService" /> class.
|
||||
/// </summary>
|
||||
/// <param name="xmlSerializer">The XML serializer.</param>
|
||||
/// <param name="jsonSerializer">The json serializer.</param>
|
||||
/// <exception cref="System.ArgumentNullException">xmlSerializer</exception>
|
||||
public UserService(IXmlSerializer xmlSerializer, IJsonSerializer jsonSerializer)
|
||||
: base()
|
||||
{
|
||||
if (jsonSerializer == null)
|
||||
{
|
||||
throw new ArgumentNullException("jsonSerializer");
|
||||
}
|
||||
|
||||
if (xmlSerializer == null)
|
||||
{
|
||||
throw new ArgumentNullException("xmlSerializer");
|
||||
}
|
||||
|
||||
_jsonSerializer = jsonSerializer;
|
||||
_xmlSerializer = xmlSerializer;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the specified request.
|
||||
/// </summary>
|
||||
|
@ -262,10 +295,10 @@ namespace MediaBrowser.Api
|
|||
// https://code.google.com/p/servicestack/source/browse/trunk/Common/ServiceStack.Text/ServiceStack.Text/Controller/PathInfo.cs
|
||||
var pathInfo = PathInfo.Parse(Request.PathInfo);
|
||||
var id = new Guid(pathInfo.GetArgumentValue<string>(1));
|
||||
|
||||
|
||||
var kernel = (Kernel)Kernel;
|
||||
|
||||
var dtoUser = JsonSerializer.DeserializeFromStream<UserDto>(request.RequestStream);
|
||||
var dtoUser = _jsonSerializer.DeserializeFromStream<UserDto>(request.RequestStream);
|
||||
|
||||
var user = kernel.GetUserById(id);
|
||||
|
||||
|
@ -273,7 +306,7 @@ namespace MediaBrowser.Api
|
|||
|
||||
Task.WaitAll(task);
|
||||
|
||||
user.UpdateConfiguration(dtoUser.Configuration);
|
||||
user.UpdateConfiguration(dtoUser.Configuration, _xmlSerializer);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
@ -285,7 +318,7 @@ namespace MediaBrowser.Api
|
|||
{
|
||||
var kernel = (Kernel)Kernel;
|
||||
|
||||
var dtoUser = JsonSerializer.DeserializeFromStream<UserDto>(request.RequestStream);
|
||||
var dtoUser = _jsonSerializer.DeserializeFromStream<UserDto>(request.RequestStream);
|
||||
|
||||
var newUser = kernel.UserManager.CreateUser(dtoUser.Name).Result;
|
||||
|
||||
|
|
|
@ -1,105 +0,0 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project ToolsVersion="4.0" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<Import Project="$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props" Condition="Exists('$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props')" />
|
||||
<PropertyGroup>
|
||||
<Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
|
||||
<Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform>
|
||||
<ProjectGuid>{767B536E-D90C-4D74-A14B-8564B16F3499}</ProjectGuid>
|
||||
<OutputType>Library</OutputType>
|
||||
<AppDesignerFolder>Properties</AppDesignerFolder>
|
||||
<RootNamespace>MediaBrowser.ApiInteraction.Javascript</RootNamespace>
|
||||
<AssemblyName>MediaBrowser.ApiInteraction.Javascript</AssemblyName>
|
||||
<TargetFrameworkVersion>v4.5</TargetFrameworkVersion>
|
||||
<FileAlignment>512</FileAlignment>
|
||||
<SolutionDir Condition="$(SolutionDir) == '' Or $(SolutionDir) == '*Undefined*'">..\</SolutionDir>
|
||||
<RestorePackages>true</RestorePackages>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
|
||||
<DebugSymbols>true</DebugSymbols>
|
||||
<DebugType>full</DebugType>
|
||||
<Optimize>false</Optimize>
|
||||
<OutputPath>bin\Debug\</OutputPath>
|
||||
<DefineConstants>DEBUG;TRACE</DefineConstants>
|
||||
<ErrorReport>prompt</ErrorReport>
|
||||
<WarningLevel>4</WarningLevel>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' ">
|
||||
<DebugType>pdbonly</DebugType>
|
||||
<Optimize>true</Optimize>
|
||||
<OutputPath>bin\Release\</OutputPath>
|
||||
<DefineConstants>TRACE</DefineConstants>
|
||||
<ErrorReport>prompt</ErrorReport>
|
||||
<WarningLevel>4</WarningLevel>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup>
|
||||
<RunPostBuildEvent>Always</RunPostBuildEvent>
|
||||
</PropertyGroup>
|
||||
<ItemGroup>
|
||||
<Reference Include="ServiceStack, Version=3.9.37.0, Culture=neutral, processorArchitecture=MSIL">
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>..\packages\ServiceStack.3.9.37\lib\net35\ServiceStack.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="ServiceStack.Common, Version=3.9.37.0, Culture=neutral, processorArchitecture=MSIL">
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>..\packages\ServiceStack.Common.3.9.37\lib\net35\ServiceStack.Common.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="ServiceStack.Interfaces, Version=3.9.37.0, Culture=neutral, processorArchitecture=MSIL">
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>..\packages\ServiceStack.Common.3.9.37\lib\net35\ServiceStack.Interfaces.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="ServiceStack.OrmLite, Version=3.9.37.0, Culture=neutral, processorArchitecture=MSIL">
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>..\packages\ServiceStack.OrmLite.SqlServer.3.9.37\lib\ServiceStack.OrmLite.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="ServiceStack.OrmLite.SqlServer, Version=1.0.0.0, Culture=neutral, processorArchitecture=MSIL">
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>..\packages\ServiceStack.OrmLite.SqlServer.3.9.37\lib\ServiceStack.OrmLite.SqlServer.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="ServiceStack.Redis, Version=3.9.37.0, Culture=neutral, processorArchitecture=MSIL">
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>..\packages\ServiceStack.Redis.3.9.37\lib\net35\ServiceStack.Redis.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="ServiceStack.ServiceInterface, Version=1.0.0.0, Culture=neutral, processorArchitecture=MSIL">
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>..\packages\ServiceStack.3.9.37\lib\net35\ServiceStack.ServiceInterface.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="ServiceStack.Text, Version=3.9.37.0, Culture=neutral, processorArchitecture=MSIL">
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>..\packages\ServiceStack.Text.3.9.37\lib\net35\ServiceStack.Text.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="System" />
|
||||
<Reference Include="System.Core" />
|
||||
<Reference Include="Microsoft.CSharp" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Compile Include="..\SharedVersion.cs">
|
||||
<Link>Properties\SharedVersion.cs</Link>
|
||||
</Compile>
|
||||
<Compile Include="JavascriptApiClientService.cs" />
|
||||
<Compile Include="Properties\AssemblyInfo.cs" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\MediaBrowser.Common\MediaBrowser.Common.csproj">
|
||||
<Project>{9142eefa-7570-41e1-bfcc-468bb571af2f}</Project>
|
||||
<Name>MediaBrowser.Common</Name>
|
||||
</ProjectReference>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<EmbeddedResource Include="ApiClient.js" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="packages.config" />
|
||||
</ItemGroup>
|
||||
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
|
||||
<PropertyGroup>
|
||||
<PostBuildEvent>xcopy "$(TargetPath)" "$(SolutionDir)\MediaBrowser.ServerApplication\CorePlugins\" /y</PostBuildEvent>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(SolutionDir)\.nuget\nuget.targets" />
|
||||
<!-- To modify your build process, add your task inside one of the targets below and uncomment it.
|
||||
Other similar extension points exist, see Microsoft.Common.targets.
|
||||
<Target Name="BeforeBuild">
|
||||
</Target>
|
||||
<Target Name="AfterBuild">
|
||||
</Target>
|
||||
-->
|
||||
</Project>
|
|
@ -1,30 +0,0 @@
|
|||
using System.Reflection;
|
||||
using System.Runtime.InteropServices;
|
||||
|
||||
// General Information about an assembly is controlled through the following
|
||||
// set of attributes. Change these attribute values to modify the information
|
||||
// associated with an assembly.
|
||||
[assembly: AssemblyTitle("MediaBrowser.ApiInteraction.Javascript")]
|
||||
[assembly: AssemblyDescription("")]
|
||||
[assembly: AssemblyConfiguration("")]
|
||||
[assembly: AssemblyCompany("")]
|
||||
[assembly: AssemblyProduct("MediaBrowser.ApiInteraction.Javascript")]
|
||||
[assembly: AssemblyCopyright("Copyright © 2012")]
|
||||
[assembly: AssemblyTrademark("")]
|
||||
[assembly: AssemblyCulture("")]
|
||||
|
||||
// Setting ComVisible to false makes the types in this assembly not visible
|
||||
// to COM components. If you need to access a type in this assembly from
|
||||
// COM, set the ComVisible attribute to true on that type.
|
||||
[assembly: ComVisible(false)]
|
||||
|
||||
// The following GUID is for the ID of the typelib if this project is exposed to COM
|
||||
[assembly: Guid("97f9d4da-d7de-47d9-ae68-06d78679d327")]
|
||||
|
||||
// Version information for an assembly consists of the following four values:
|
||||
//
|
||||
// Major Version
|
||||
// Minor Version
|
||||
// Build Number
|
||||
// Revision
|
||||
//
|
|
@ -1,8 +0,0 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<packages>
|
||||
<package id="ServiceStack" version="3.9.37" targetFramework="net45" />
|
||||
<package id="ServiceStack.Common" version="3.9.37" targetFramework="net45" />
|
||||
<package id="ServiceStack.OrmLite.SqlServer" version="3.9.37" targetFramework="net45" />
|
||||
<package id="ServiceStack.Redis" version="3.9.37" targetFramework="net45" />
|
||||
<package id="ServiceStack.Text" version="3.9.37" targetFramework="net45" />
|
||||
</packages>
|
|
@ -3,7 +3,7 @@ using System.Configuration;
|
|||
using System.IO;
|
||||
using System.Reflection;
|
||||
|
||||
namespace MediaBrowser.Common.Kernel
|
||||
namespace MediaBrowser.Common.Implementations
|
||||
{
|
||||
/// <summary>
|
||||
/// Provides a base class to hold common application paths used by both the Ui and Server.
|
|
@ -4,13 +4,15 @@
|
|||
<PropertyGroup>
|
||||
<Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
|
||||
<Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform>
|
||||
<ProjectGuid>{973CA45C-8362-490B-8327-C68098FD4891}</ProjectGuid>
|
||||
<ProjectGuid>{C4D2573A-3FD3-441F-81AF-174AC4CD4E1D}</ProjectGuid>
|
||||
<OutputType>Library</OutputType>
|
||||
<AppDesignerFolder>Properties</AppDesignerFolder>
|
||||
<RootNamespace>MediaBrowser.Server.WorldWeatherOnline</RootNamespace>
|
||||
<AssemblyName>MediaBrowser.Server.WorldWeatherOnline</AssemblyName>
|
||||
<RootNamespace>MediaBrowser.Common.Implementations</RootNamespace>
|
||||
<AssemblyName>MediaBrowser.Common.Implementations</AssemblyName>
|
||||
<TargetFrameworkVersion>v4.5</TargetFrameworkVersion>
|
||||
<FileAlignment>512</FileAlignment>
|
||||
<SolutionDir Condition="$(SolutionDir) == '' Or $(SolutionDir) == '*Undefined*'">..\</SolutionDir>
|
||||
<RestorePackages>true</RestorePackages>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
|
||||
<DebugSymbols>true</DebugSymbols>
|
||||
|
@ -29,39 +31,52 @@
|
|||
<ErrorReport>prompt</ErrorReport>
|
||||
<WarningLevel>4</WarningLevel>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup>
|
||||
<RunPostBuildEvent>Always</RunPostBuildEvent>
|
||||
</PropertyGroup>
|
||||
<ItemGroup>
|
||||
<Reference Include="protobuf-net">
|
||||
<HintPath>..\packages\protobuf-net.2.0.0.621\lib\net40\protobuf-net.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="ServiceStack.Text">
|
||||
<HintPath>..\packages\ServiceStack.Text.3.9.37\lib\net35\ServiceStack.Text.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="System" />
|
||||
<Reference Include="System.Configuration" />
|
||||
<Reference Include="System.Core" />
|
||||
<Reference Include="System.Xml.Linq" />
|
||||
<Reference Include="System.Data.DataSetExtensions" />
|
||||
<Reference Include="Microsoft.CSharp" />
|
||||
<Reference Include="System.Data" />
|
||||
<Reference Include="System.Xml" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Compile Include="..\SharedVersion.cs">
|
||||
<Link>Properties\SharedVersion.cs</Link>
|
||||
</Compile>
|
||||
<Compile Include="BaseApplicationPaths.cs" />
|
||||
<Compile Include="Properties\AssemblyInfo.cs" />
|
||||
<Compile Include="WeatherProvider.cs" />
|
||||
<Compile Include="ScheduledTasks\TaskManager.cs" />
|
||||
<Compile Include="ScheduledTasks\Tasks\DeleteCacheFileTask.cs" />
|
||||
<Compile Include="ScheduledTasks\Tasks\DeleteLogFileTask.cs" />
|
||||
<Compile Include="ScheduledTasks\Tasks\ReloadLoggerTask.cs" />
|
||||
<Compile Include="ScheduledTasks\Tasks\SystemUpdateTask.cs" />
|
||||
<Compile Include="Serialization\JsonSerializer.cs" />
|
||||
<Compile Include="Serialization\ProtobufSerializer.cs" />
|
||||
<Compile Include="Serialization\XmlSerializer.cs" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\MediaBrowser.Common\MediaBrowser.Common.csproj">
|
||||
<Project>{9142eefa-7570-41e1-bfcc-468bb571af2f}</Project>
|
||||
<Name>MediaBrowser.Common</Name>
|
||||
</ProjectReference>
|
||||
<ProjectReference Include="..\MediaBrowser.Controller\MediaBrowser.Controller.csproj">
|
||||
<Project>{17e1f4e6-8abd-4fe5-9ecf-43d4b6087ba2}</Project>
|
||||
<Name>MediaBrowser.Controller</Name>
|
||||
</ProjectReference>
|
||||
<ProjectReference Include="..\MediaBrowser.Model\MediaBrowser.Model.csproj">
|
||||
<Project>{7eeeb4bb-f3e8-48fc-b4c5-70f0fff8329b}</Project>
|
||||
<Name>MediaBrowser.Model</Name>
|
||||
</ProjectReference>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="packages.config" />
|
||||
</ItemGroup>
|
||||
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
|
||||
<PropertyGroup>
|
||||
<PostBuildEvent>xcopy "$(TargetPath)" "$(SolutionDir)\MediaBrowser.ServerApplication\CorePlugins\" /y</PostBuildEvent>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(SolutionDir)\.nuget\nuget.targets" />
|
||||
<!-- To modify your build process, add your task inside one of the targets below and uncomment it.
|
||||
Other similar extension points exist, see Microsoft.Common.targets.
|
||||
<Target Name="BeforeBuild">
|
|
@ -5,11 +5,11 @@ using System.Runtime.InteropServices;
|
|||
// General Information about an assembly is controlled through the following
|
||||
// set of attributes. Change these attribute values to modify the information
|
||||
// associated with an assembly.
|
||||
[assembly: AssemblyTitle("MediaBrowser.Server.Sqlite")]
|
||||
[assembly: AssemblyTitle("MediaBrowser.Common.Implementations")]
|
||||
[assembly: AssemblyDescription("")]
|
||||
[assembly: AssemblyConfiguration("")]
|
||||
[assembly: AssemblyCompany("")]
|
||||
[assembly: AssemblyProduct("MediaBrowser.Server.Sqlite")]
|
||||
[assembly: AssemblyProduct("MediaBrowser.Common.Implementations")]
|
||||
[assembly: AssemblyCopyright("Copyright © 2013")]
|
||||
[assembly: AssemblyTrademark("")]
|
||||
[assembly: AssemblyCulture("")]
|
||||
|
@ -20,7 +20,7 @@ using System.Runtime.InteropServices;
|
|||
[assembly: ComVisible(false)]
|
||||
|
||||
// The following GUID is for the ID of the typelib if this project is exposed to COM
|
||||
[assembly: Guid("f46c9f4b-24ed-49e1-be19-4b6242dd8382")]
|
||||
[assembly: Guid("fc7d85c6-0fe7-4db6-8158-54f7b18f17cd")]
|
||||
|
||||
// Version information for an assembly consists of the following four values:
|
||||
//
|
||||
|
@ -28,4 +28,4 @@ using System.Runtime.InteropServices;
|
|||
// Minor Version
|
||||
// Build Number
|
||||
// Revision
|
||||
//
|
||||
//
|
|
@ -0,0 +1,322 @@
|
|||
using MediaBrowser.Common.Kernel;
|
||||
using MediaBrowser.Common.ScheduledTasks;
|
||||
using MediaBrowser.Model.Logging;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
using MediaBrowser.Model.Tasks;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
using System.Linq;
|
||||
|
||||
namespace MediaBrowser.Common.Implementations.ScheduledTasks
|
||||
{
|
||||
/// <summary>
|
||||
/// Class TaskManager
|
||||
/// </summary>
|
||||
public class TaskManager : ITaskManager
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets the list of Scheduled Tasks
|
||||
/// </summary>
|
||||
/// <value>The scheduled tasks.</value>
|
||||
public IScheduledTask[] ScheduledTasks { get; private set; }
|
||||
|
||||
/// <summary>
|
||||
/// The _task queue
|
||||
/// </summary>
|
||||
private readonly List<Type> _taskQueue = new List<Type>();
|
||||
|
||||
/// <summary>
|
||||
/// The _logger
|
||||
/// </summary>
|
||||
private readonly ILogger _logger;
|
||||
|
||||
/// <summary>
|
||||
/// The _application paths
|
||||
/// </summary>
|
||||
private readonly IApplicationPaths _applicationPaths;
|
||||
|
||||
/// <summary>
|
||||
/// The _json serializer
|
||||
/// </summary>
|
||||
private readonly IJsonSerializer _jsonSerializer;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="TaskManager" /> class.
|
||||
/// </summary>
|
||||
/// <param name="applicationPaths">The application paths.</param>
|
||||
/// <param name="jsonSerializer">The json serializer.</param>
|
||||
/// <param name="logger">The logger.</param>
|
||||
/// <exception cref="System.ArgumentException">kernel</exception>
|
||||
public TaskManager(IApplicationPaths applicationPaths, IJsonSerializer jsonSerializer, ILogger logger)
|
||||
{
|
||||
if (applicationPaths == null)
|
||||
{
|
||||
throw new ArgumentException("applicationPaths");
|
||||
}
|
||||
if (jsonSerializer == null)
|
||||
{
|
||||
throw new ArgumentException("jsonSerializer");
|
||||
}
|
||||
if (logger == null)
|
||||
{
|
||||
throw new ArgumentException("logger");
|
||||
}
|
||||
|
||||
_applicationPaths = applicationPaths;
|
||||
_jsonSerializer = jsonSerializer;
|
||||
_logger = logger;
|
||||
|
||||
ScheduledTasks = new IScheduledTask[] {};
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Cancels if running and queue.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
public void CancelIfRunningAndQueue<T>()
|
||||
where T : IScheduledTask
|
||||
{
|
||||
ScheduledTasks.OfType<T>().First().CancelIfRunning();
|
||||
QueueScheduledTask<T>();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Queues the scheduled task.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
public void QueueScheduledTask<T>()
|
||||
where T : IScheduledTask
|
||||
{
|
||||
var scheduledTask = ScheduledTasks.OfType<T>().First();
|
||||
|
||||
QueueScheduledTask(scheduledTask);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Queues the scheduled task.
|
||||
/// </summary>
|
||||
/// <param name="task">The task.</param>
|
||||
public void QueueScheduledTask(IScheduledTask task)
|
||||
{
|
||||
var type = task.GetType();
|
||||
|
||||
var scheduledTask = ScheduledTasks.First(t => t.GetType() == type);
|
||||
|
||||
lock (_taskQueue)
|
||||
{
|
||||
// If it's idle just execute immediately
|
||||
if (scheduledTask.State == TaskState.Idle)
|
||||
{
|
||||
scheduledTask.Execute();
|
||||
return;
|
||||
}
|
||||
|
||||
if (!_taskQueue.Contains(type))
|
||||
{
|
||||
_logger.Info("Queueing task {0}", type.Name);
|
||||
_taskQueue.Add(type);
|
||||
}
|
||||
else
|
||||
{
|
||||
_logger.Info("Task already queued: {0}", type.Name);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Called when [task completed].
|
||||
/// </summary>
|
||||
/// <param name="task">The task.</param>
|
||||
public void OnTaskCompleted(IScheduledTask task)
|
||||
{
|
||||
// Execute queued tasks
|
||||
lock (_taskQueue)
|
||||
{
|
||||
var copy = _taskQueue.ToList();
|
||||
|
||||
foreach (var type in copy)
|
||||
{
|
||||
var scheduledTask = ScheduledTasks.First(t => t.GetType() == type);
|
||||
|
||||
if (scheduledTask.State == TaskState.Idle)
|
||||
{
|
||||
scheduledTask.Execute();
|
||||
|
||||
_taskQueue.Remove(type);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Adds the tasks.
|
||||
/// </summary>
|
||||
/// <param name="tasks">The tasks.</param>
|
||||
public void AddTasks(IEnumerable<IScheduledTask> tasks)
|
||||
{
|
||||
var myTasks = ScheduledTasks.ToList();
|
||||
|
||||
myTasks.AddRange(tasks);
|
||||
|
||||
ScheduledTasks = myTasks.ToArray();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// The _scheduled tasks configuration directory
|
||||
/// </summary>
|
||||
private string _scheduledTasksConfigurationDirectory;
|
||||
/// <summary>
|
||||
/// Gets the scheduled tasks configuration directory.
|
||||
/// </summary>
|
||||
/// <value>The scheduled tasks configuration directory.</value>
|
||||
private string ScheduledTasksConfigurationDirectory
|
||||
{
|
||||
get
|
||||
{
|
||||
if (_scheduledTasksConfigurationDirectory == null)
|
||||
{
|
||||
_scheduledTasksConfigurationDirectory = Path.Combine(_applicationPaths.ConfigurationDirectoryPath, "ScheduledTasks");
|
||||
|
||||
if (!Directory.Exists(_scheduledTasksConfigurationDirectory))
|
||||
{
|
||||
Directory.CreateDirectory(_scheduledTasksConfigurationDirectory);
|
||||
}
|
||||
}
|
||||
return _scheduledTasksConfigurationDirectory;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// The _scheduled tasks data directory
|
||||
/// </summary>
|
||||
private string _scheduledTasksDataDirectory;
|
||||
/// <summary>
|
||||
/// Gets the scheduled tasks data directory.
|
||||
/// </summary>
|
||||
/// <value>The scheduled tasks data directory.</value>
|
||||
private string ScheduledTasksDataDirectory
|
||||
{
|
||||
get
|
||||
{
|
||||
if (_scheduledTasksDataDirectory == null)
|
||||
{
|
||||
_scheduledTasksDataDirectory = Path.Combine(_applicationPaths.DataPath, "ScheduledTasks");
|
||||
|
||||
if (!Directory.Exists(_scheduledTasksDataDirectory))
|
||||
{
|
||||
Directory.CreateDirectory(_scheduledTasksDataDirectory);
|
||||
}
|
||||
}
|
||||
return _scheduledTasksDataDirectory;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the history file path.
|
||||
/// </summary>
|
||||
/// <value>The history file path.</value>
|
||||
private string GetHistoryFilePath(IScheduledTask task)
|
||||
{
|
||||
return Path.Combine(ScheduledTasksDataDirectory, task.Id + ".js");
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the configuration file path.
|
||||
/// </summary>
|
||||
/// <param name="task">The task.</param>
|
||||
/// <returns>System.String.</returns>
|
||||
private string GetConfigurationFilePath(IScheduledTask task)
|
||||
{
|
||||
return Path.Combine(ScheduledTasksConfigurationDirectory, task.Id + ".js");
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Called when [task completed].
|
||||
/// </summary>
|
||||
/// <param name="task">The task.</param>
|
||||
/// <param name="startTime">The start time.</param>
|
||||
/// <param name="endTime">The end time.</param>
|
||||
/// <param name="status">The status.</param>
|
||||
public void OnTaskCompleted(IScheduledTask task, DateTime startTime, DateTime endTime, TaskCompletionStatus status)
|
||||
{
|
||||
var elapsedTime = endTime - startTime;
|
||||
|
||||
_logger.Info("{0} {1} after {2} minute(s) and {3} seconds", task.Name, status, Math.Truncate(elapsedTime.TotalMinutes), elapsedTime.Seconds);
|
||||
|
||||
var result = new TaskResult
|
||||
{
|
||||
StartTimeUtc = startTime,
|
||||
EndTimeUtc = endTime,
|
||||
Status = status,
|
||||
Name = task.Name,
|
||||
Id = task.Id
|
||||
};
|
||||
|
||||
_jsonSerializer.SerializeToFile(result, GetHistoryFilePath(task));
|
||||
|
||||
//task.LastExecutionResult = result;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the last execution result.
|
||||
/// </summary>
|
||||
/// <param name="task">The task.</param>
|
||||
/// <returns>TaskResult.</returns>
|
||||
public TaskResult GetLastExecutionResult(IScheduledTask task)
|
||||
{
|
||||
return _jsonSerializer.DeserializeFromFile<TaskResult>(GetHistoryFilePath(task));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Loads the triggers.
|
||||
/// </summary>
|
||||
/// <param name="task">The task.</param>
|
||||
/// <returns>IEnumerable{BaseTaskTrigger}.</returns>
|
||||
public IEnumerable<ITaskTrigger> LoadTriggers(IScheduledTask task)
|
||||
{
|
||||
try
|
||||
{
|
||||
return _jsonSerializer.DeserializeFromFile<IEnumerable<TaskTriggerInfo>>(GetConfigurationFilePath(task))
|
||||
.Select(ScheduledTaskHelpers.GetTrigger)
|
||||
.ToList();
|
||||
}
|
||||
catch (IOException)
|
||||
{
|
||||
// File doesn't exist. No biggie. Return defaults.
|
||||
return task.GetDefaultTriggers();
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Saves the triggers.
|
||||
/// </summary>
|
||||
/// <param name="task">The task.</param>
|
||||
/// <param name="triggers">The triggers.</param>
|
||||
public void SaveTriggers(IScheduledTask task, IEnumerable<ITaskTrigger> triggers)
|
||||
{
|
||||
_jsonSerializer.SerializeToFile(triggers.Select(ScheduledTaskHelpers.GetTriggerInfo), GetConfigurationFilePath(task));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Performs application-defined tasks associated with freeing, releasing, or resetting unmanaged resources.
|
||||
/// </summary>
|
||||
public void Dispose()
|
||||
{
|
||||
Dispose(true);
|
||||
GC.SuppressFinalize(this);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Releases unmanaged and - optionally - managed resources.
|
||||
/// </summary>
|
||||
/// <param name="dispose"><c>true</c> to release both managed and unmanaged resources; <c>false</c> to release only unmanaged resources.</param>
|
||||
protected virtual void Dispose(bool dispose)
|
||||
{
|
||||
foreach (var task in ScheduledTasks)
|
||||
{
|
||||
task.Dispose();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,4 +1,5 @@
|
|||
using MediaBrowser.Common.Kernel;
|
||||
using MediaBrowser.Common.ScheduledTasks;
|
||||
using MediaBrowser.Model.Logging;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
|
@ -7,7 +8,7 @@ using System.Linq;
|
|||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace MediaBrowser.Common.ScheduledTasks.Tasks
|
||||
namespace MediaBrowser.Common.Implementations.ScheduledTasks.Tasks
|
||||
{
|
||||
/// <summary>
|
||||
/// Deletes old cache files
|
||||
|
@ -29,7 +30,7 @@ namespace MediaBrowser.Common.ScheduledTasks.Tasks
|
|||
/// Creates the triggers that define when the task will run
|
||||
/// </summary>
|
||||
/// <returns>IEnumerable{BaseTaskTrigger}.</returns>
|
||||
protected override IEnumerable<BaseTaskTrigger> GetDefaultTriggers()
|
||||
public override IEnumerable<ITaskTrigger> GetDefaultTriggers()
|
||||
{
|
||||
var trigger = new DailyTrigger { TimeOfDay = TimeSpan.FromHours(2) }; //2am
|
||||
|
|
@ -1,4 +1,5 @@
|
|||
using MediaBrowser.Common.Kernel;
|
||||
using MediaBrowser.Common.ScheduledTasks;
|
||||
using MediaBrowser.Model.Logging;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
|
@ -7,7 +8,7 @@ using System.Linq;
|
|||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace MediaBrowser.Common.ScheduledTasks.Tasks
|
||||
namespace MediaBrowser.Common.Implementations.ScheduledTasks.Tasks
|
||||
{
|
||||
/// <summary>
|
||||
/// Deletes old log files
|
||||
|
@ -29,7 +30,7 @@ namespace MediaBrowser.Common.ScheduledTasks.Tasks
|
|||
/// Creates the triggers that define when the task will run
|
||||
/// </summary>
|
||||
/// <returns>IEnumerable{BaseTaskTrigger}.</returns>
|
||||
protected override IEnumerable<BaseTaskTrigger> GetDefaultTriggers()
|
||||
public override IEnumerable<ITaskTrigger> GetDefaultTriggers()
|
||||
{
|
||||
var trigger = new DailyTrigger { TimeOfDay = TimeSpan.FromHours(2) }; //2am
|
||||
|
|
@ -1,11 +1,12 @@
|
|||
using MediaBrowser.Common.Kernel;
|
||||
using MediaBrowser.Common.ScheduledTasks;
|
||||
using MediaBrowser.Model.Logging;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace MediaBrowser.Common.ScheduledTasks.Tasks
|
||||
namespace MediaBrowser.Common.Implementations.ScheduledTasks.Tasks
|
||||
{
|
||||
/// <summary>
|
||||
/// Class ReloadLoggerFileTask
|
||||
|
@ -27,7 +28,7 @@ namespace MediaBrowser.Common.ScheduledTasks.Tasks
|
|||
/// Gets the default triggers.
|
||||
/// </summary>
|
||||
/// <returns>IEnumerable{BaseTaskTrigger}.</returns>
|
||||
protected override IEnumerable<BaseTaskTrigger> GetDefaultTriggers()
|
||||
public override IEnumerable<ITaskTrigger> GetDefaultTriggers()
|
||||
{
|
||||
var trigger = new DailyTrigger { TimeOfDay = TimeSpan.FromHours(0) }; //12am
|
||||
|
|
@ -1,11 +1,12 @@
|
|||
using MediaBrowser.Common.Kernel;
|
||||
using MediaBrowser.Common.ScheduledTasks;
|
||||
using MediaBrowser.Model.Logging;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace MediaBrowser.Common.ScheduledTasks.Tasks
|
||||
namespace MediaBrowser.Common.Implementations.ScheduledTasks.Tasks
|
||||
{
|
||||
/// <summary>
|
||||
/// Plugin Update Task
|
||||
|
@ -34,9 +35,9 @@ namespace MediaBrowser.Common.ScheduledTasks.Tasks
|
|||
/// Creates the triggers that define when the task will run
|
||||
/// </summary>
|
||||
/// <returns>IEnumerable{BaseTaskTrigger}.</returns>
|
||||
protected override IEnumerable<BaseTaskTrigger> GetDefaultTriggers()
|
||||
public override IEnumerable<ITaskTrigger> GetDefaultTriggers()
|
||||
{
|
||||
return new BaseTaskTrigger[] {
|
||||
return new ITaskTrigger[] {
|
||||
|
||||
// 1am
|
||||
new DailyTrigger { TimeOfDay = TimeSpan.FromHours(1) },
|
|
@ -1,13 +1,19 @@
|
|||
using System;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
using System;
|
||||
using System.IO;
|
||||
|
||||
namespace MediaBrowser.Common.Serialization
|
||||
namespace MediaBrowser.Common.Implementations.Serialization
|
||||
{
|
||||
/// <summary>
|
||||
/// Provides a wrapper around third party json serialization.
|
||||
/// </summary>
|
||||
public class JsonSerializer
|
||||
public class JsonSerializer : IJsonSerializer
|
||||
{
|
||||
public JsonSerializer()
|
||||
{
|
||||
Configure();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Serializes to stream.
|
||||
/// </summary>
|
||||
|
@ -15,7 +21,7 @@ namespace MediaBrowser.Common.Serialization
|
|||
/// <param name="obj">The obj.</param>
|
||||
/// <param name="stream">The stream.</param>
|
||||
/// <exception cref="System.ArgumentNullException">obj</exception>
|
||||
public static void SerializeToStream<T>(T obj, Stream stream)
|
||||
public void SerializeToStream<T>(T obj, Stream stream)
|
||||
where T : class
|
||||
{
|
||||
if (obj == null)
|
||||
|
@ -28,8 +34,6 @@ namespace MediaBrowser.Common.Serialization
|
|||
throw new ArgumentNullException("stream");
|
||||
}
|
||||
|
||||
Configure();
|
||||
|
||||
ServiceStack.Text.JsonSerializer.SerializeToStream(obj, obj.GetType(), stream);
|
||||
}
|
||||
|
||||
|
@ -40,7 +44,7 @@ namespace MediaBrowser.Common.Serialization
|
|||
/// <param name="obj">The obj.</param>
|
||||
/// <param name="file">The file.</param>
|
||||
/// <exception cref="System.ArgumentNullException">obj</exception>
|
||||
public static void SerializeToFile<T>(T obj, string file)
|
||||
public void SerializeToFile<T>(T obj, string file)
|
||||
where T : class
|
||||
{
|
||||
if (obj == null)
|
||||
|
@ -53,8 +57,6 @@ namespace MediaBrowser.Common.Serialization
|
|||
throw new ArgumentNullException("file");
|
||||
}
|
||||
|
||||
Configure();
|
||||
|
||||
using (Stream stream = File.Open(file, FileMode.Create))
|
||||
{
|
||||
SerializeToStream(obj, stream);
|
||||
|
@ -68,7 +70,7 @@ namespace MediaBrowser.Common.Serialization
|
|||
/// <param name="file">The file.</param>
|
||||
/// <returns>System.Object.</returns>
|
||||
/// <exception cref="System.ArgumentNullException">type</exception>
|
||||
public static object DeserializeFromFile(Type type, string file)
|
||||
public object DeserializeFromFile(Type type, string file)
|
||||
{
|
||||
if (type == null)
|
||||
{
|
||||
|
@ -80,8 +82,6 @@ namespace MediaBrowser.Common.Serialization
|
|||
throw new ArgumentNullException("file");
|
||||
}
|
||||
|
||||
Configure();
|
||||
|
||||
using (Stream stream = File.OpenRead(file))
|
||||
{
|
||||
return ServiceStack.Text.JsonSerializer.DeserializeFromStream(type, stream);
|
||||
|
@ -95,7 +95,7 @@ namespace MediaBrowser.Common.Serialization
|
|||
/// <param name="file">The file.</param>
|
||||
/// <returns>``0.</returns>
|
||||
/// <exception cref="System.ArgumentNullException">file</exception>
|
||||
public static T DeserializeFromFile<T>(string file)
|
||||
public T DeserializeFromFile<T>(string file)
|
||||
where T : class
|
||||
{
|
||||
if (string.IsNullOrEmpty(file))
|
||||
|
@ -103,8 +103,6 @@ namespace MediaBrowser.Common.Serialization
|
|||
throw new ArgumentNullException("file");
|
||||
}
|
||||
|
||||
Configure();
|
||||
|
||||
using (Stream stream = File.OpenRead(file))
|
||||
{
|
||||
return ServiceStack.Text.JsonSerializer.DeserializeFromStream<T>(stream);
|
||||
|
@ -118,15 +116,13 @@ namespace MediaBrowser.Common.Serialization
|
|||
/// <param name="stream">The stream.</param>
|
||||
/// <returns>``0.</returns>
|
||||
/// <exception cref="System.ArgumentNullException">stream</exception>
|
||||
public static T DeserializeFromStream<T>(Stream stream)
|
||||
public T DeserializeFromStream<T>(Stream stream)
|
||||
{
|
||||
if (stream == null)
|
||||
{
|
||||
throw new ArgumentNullException("stream");
|
||||
}
|
||||
|
||||
Configure();
|
||||
|
||||
return ServiceStack.Text.JsonSerializer.DeserializeFromStream<T>(stream);
|
||||
}
|
||||
|
||||
|
@ -137,15 +133,13 @@ namespace MediaBrowser.Common.Serialization
|
|||
/// <param name="text">The text.</param>
|
||||
/// <returns>``0.</returns>
|
||||
/// <exception cref="System.ArgumentNullException">text</exception>
|
||||
public static T DeserializeFromString<T>(string text)
|
||||
public T DeserializeFromString<T>(string text)
|
||||
{
|
||||
if (string.IsNullOrEmpty(text))
|
||||
{
|
||||
throw new ArgumentNullException("text");
|
||||
}
|
||||
|
||||
Configure();
|
||||
|
||||
return ServiceStack.Text.JsonSerializer.DeserializeFromString<T>(text);
|
||||
}
|
||||
|
||||
|
@ -156,7 +150,7 @@ namespace MediaBrowser.Common.Serialization
|
|||
/// <param name="type">The type.</param>
|
||||
/// <returns>System.Object.</returns>
|
||||
/// <exception cref="System.ArgumentNullException">stream</exception>
|
||||
public static object DeserializeFromStream(Stream stream, Type type)
|
||||
public object DeserializeFromStream(Stream stream, Type type)
|
||||
{
|
||||
if (stream == null)
|
||||
{
|
||||
|
@ -168,27 +162,17 @@ namespace MediaBrowser.Common.Serialization
|
|||
throw new ArgumentNullException("type");
|
||||
}
|
||||
|
||||
Configure();
|
||||
|
||||
return ServiceStack.Text.JsonSerializer.DeserializeFromStream(type, stream);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// The _is configured
|
||||
/// </summary>
|
||||
private static bool _isConfigured;
|
||||
/// <summary>
|
||||
/// Configures this instance.
|
||||
/// </summary>
|
||||
internal static void Configure()
|
||||
private void Configure()
|
||||
{
|
||||
if (!_isConfigured)
|
||||
{
|
||||
ServiceStack.Text.JsConfig.DateHandler = ServiceStack.Text.JsonDateHandler.ISO8601;
|
||||
ServiceStack.Text.JsConfig.ExcludeTypeInfo = true;
|
||||
ServiceStack.Text.JsConfig.IncludeNullValues = false;
|
||||
_isConfigured = true;
|
||||
}
|
||||
ServiceStack.Text.JsConfig.DateHandler = ServiceStack.Text.JsonDateHandler.ISO8601;
|
||||
ServiceStack.Text.JsConfig.ExcludeTypeInfo = true;
|
||||
ServiceStack.Text.JsConfig.IncludeNullValues = false;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
@ -198,7 +182,7 @@ namespace MediaBrowser.Common.Serialization
|
|||
/// <param name="type">The type.</param>
|
||||
/// <returns>System.Object.</returns>
|
||||
/// <exception cref="System.ArgumentNullException">json</exception>
|
||||
public static object DeserializeFromString(string json, Type type)
|
||||
public object DeserializeFromString(string json, Type type)
|
||||
{
|
||||
if (string.IsNullOrEmpty(json))
|
||||
{
|
||||
|
@ -210,8 +194,6 @@ namespace MediaBrowser.Common.Serialization
|
|||
throw new ArgumentNullException("type");
|
||||
}
|
||||
|
||||
Configure();
|
||||
|
||||
return ServiceStack.Text.JsonSerializer.DeserializeFromString(json, type);
|
||||
}
|
||||
|
||||
|
@ -222,7 +204,7 @@ namespace MediaBrowser.Common.Serialization
|
|||
/// <param name="obj">The obj.</param>
|
||||
/// <returns>System.String.</returns>
|
||||
/// <exception cref="System.ArgumentNullException">obj</exception>
|
||||
public static string SerializeToString<T>(T obj)
|
||||
public string SerializeToString<T>(T obj)
|
||||
where T : class
|
||||
{
|
||||
if (obj == null)
|
||||
|
@ -230,7 +212,6 @@ namespace MediaBrowser.Common.Serialization
|
|||
throw new ArgumentNullException("obj");
|
||||
}
|
||||
|
||||
Configure();
|
||||
return ServiceStack.Text.JsonSerializer.SerializeToString(obj, obj.GetType());
|
||||
}
|
||||
|
||||
|
@ -241,7 +222,7 @@ namespace MediaBrowser.Common.Serialization
|
|||
/// <param name="obj">The obj.</param>
|
||||
/// <returns>System.Byte[][].</returns>
|
||||
/// <exception cref="System.ArgumentNullException">obj</exception>
|
||||
public static byte[] SerializeToBytes<T>(T obj)
|
||||
public byte[] SerializeToBytes<T>(T obj)
|
||||
where T : class
|
||||
{
|
||||
if (obj == null)
|
|
@ -1,22 +1,23 @@
|
|||
using ProtoBuf;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
using ProtoBuf;
|
||||
using ProtoBuf.Meta;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
using System.Linq;
|
||||
|
||||
namespace MediaBrowser.Common.Serialization
|
||||
namespace MediaBrowser.Common.Implementations.Serialization
|
||||
{
|
||||
/// <summary>
|
||||
/// Creates a compiled protobuf serializer based on a set of assemblies
|
||||
/// </summary>
|
||||
public class DynamicProtobufSerializer
|
||||
public class ProtobufSerializer : IProtobufSerializer
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets or sets the type model.
|
||||
/// </summary>
|
||||
/// <value>The type model.</value>
|
||||
public TypeModel TypeModel { get; set; }
|
||||
private TypeModel TypeModel { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Serializes to stream.
|
||||
|
@ -135,7 +136,7 @@ namespace MediaBrowser.Common.Serialization
|
|||
/// </summary>
|
||||
/// <returns>DynamicProtobufSerializer.</returns>
|
||||
/// <exception cref="System.ArgumentNullException">assemblies</exception>
|
||||
public static DynamicProtobufSerializer Create(IEnumerable<Type> types)
|
||||
public static ProtobufSerializer Create(IEnumerable<Type> types)
|
||||
{
|
||||
if (types == null)
|
||||
{
|
||||
|
@ -151,7 +152,7 @@ namespace MediaBrowser.Common.Serialization
|
|||
model.Add(type, true);
|
||||
}
|
||||
|
||||
return new DynamicProtobufSerializer { TypeModel = model.Compile() };
|
||||
return new ProtobufSerializer { TypeModel = model.Compile() };
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,35 +1,21 @@
|
|||
using MediaBrowser.Model.Logging;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
using System;
|
||||
using System.IO;
|
||||
using System.Linq;
|
||||
using System.Xml;
|
||||
|
||||
namespace MediaBrowser.Common.Serialization
|
||||
namespace MediaBrowser.Common.Implementations.Serialization
|
||||
{
|
||||
/// <summary>
|
||||
/// Provides a wrapper around third party xml serialization.
|
||||
/// </summary>
|
||||
public class XmlSerializer
|
||||
public class XmlSerializer : IXmlSerializer
|
||||
{
|
||||
/// <summary>
|
||||
/// Serializes to writer.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <param name="obj">The obj.</param>
|
||||
/// <param name="writer">The writer.</param>
|
||||
public static void SerializeToWriter<T>(T obj, XmlTextWriter writer)
|
||||
{
|
||||
writer.Formatting = Formatting.Indented;
|
||||
var netSerializer = new System.Xml.Serialization.XmlSerializer(typeof(T));
|
||||
netSerializer.Serialize(writer, obj);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Serializes to writer.
|
||||
/// </summary>
|
||||
/// <param name="obj">The obj.</param>
|
||||
/// <param name="writer">The writer.</param>
|
||||
public static void SerializeToWriter(object obj, XmlTextWriter writer)
|
||||
private void SerializeToWriter(object obj, XmlTextWriter writer)
|
||||
{
|
||||
writer.Formatting = Formatting.Indented;
|
||||
var netSerializer = new System.Xml.Serialization.XmlSerializer(obj.GetType());
|
||||
|
@ -42,7 +28,7 @@ namespace MediaBrowser.Common.Serialization
|
|||
/// <typeparam name="T"></typeparam>
|
||||
/// <param name="stream">The stream.</param>
|
||||
/// <returns>``0.</returns>
|
||||
public static T DeserializeFromStream<T>(Stream stream)
|
||||
public T DeserializeFromStream<T>(Stream stream)
|
||||
{
|
||||
using (var reader = new XmlTextReader(stream))
|
||||
{
|
||||
|
@ -58,7 +44,7 @@ namespace MediaBrowser.Common.Serialization
|
|||
/// <param name="type">The type.</param>
|
||||
/// <param name="stream">The stream.</param>
|
||||
/// <returns>System.Object.</returns>
|
||||
public static object DeserializeFromStream(Type type, Stream stream)
|
||||
public object DeserializeFromStream(Type type, Stream stream)
|
||||
{
|
||||
using (var reader = new XmlTextReader(stream))
|
||||
{
|
||||
|
@ -73,7 +59,7 @@ namespace MediaBrowser.Common.Serialization
|
|||
/// </summary>
|
||||
/// <param name="obj">The obj.</param>
|
||||
/// <param name="stream">The stream.</param>
|
||||
public static void SerializeToStream(object obj, Stream stream)
|
||||
public void SerializeToStream(object obj, Stream stream)
|
||||
{
|
||||
using (var writer = new XmlTextWriter(stream, null))
|
||||
{
|
||||
|
@ -87,7 +73,7 @@ namespace MediaBrowser.Common.Serialization
|
|||
/// <typeparam name="T"></typeparam>
|
||||
/// <param name="file">The file.</param>
|
||||
/// <returns>``0.</returns>
|
||||
public static T DeserializeFromFile<T>(string file)
|
||||
public T DeserializeFromFile<T>(string file)
|
||||
{
|
||||
using (var stream = File.OpenRead(file))
|
||||
{
|
||||
|
@ -100,7 +86,7 @@ namespace MediaBrowser.Common.Serialization
|
|||
/// </summary>
|
||||
/// <param name="obj">The obj.</param>
|
||||
/// <param name="file">The file.</param>
|
||||
public static void SerializeToFile(object obj, string file)
|
||||
public void SerializeToFile(object obj, string file)
|
||||
{
|
||||
using (var stream = new FileStream(file, FileMode.Create))
|
||||
{
|
||||
|
@ -114,7 +100,7 @@ namespace MediaBrowser.Common.Serialization
|
|||
/// <param name="type">The type.</param>
|
||||
/// <param name="file">The file.</param>
|
||||
/// <returns>System.Object.</returns>
|
||||
public static object DeserializeFromFile(Type type, string file)
|
||||
public object DeserializeFromFile(Type type, string file)
|
||||
{
|
||||
using (var stream = File.OpenRead(file))
|
||||
{
|
||||
|
@ -128,7 +114,7 @@ namespace MediaBrowser.Common.Serialization
|
|||
/// <param name="type">The type.</param>
|
||||
/// <param name="buffer">The buffer.</param>
|
||||
/// <returns>System.Object.</returns>
|
||||
public static object DeserializeFromBytes(Type type, byte[] buffer)
|
||||
public object DeserializeFromBytes(Type type, byte[] buffer)
|
||||
{
|
||||
using (var stream = new MemoryStream(buffer))
|
||||
{
|
||||
|
@ -141,7 +127,7 @@ namespace MediaBrowser.Common.Serialization
|
|||
/// </summary>
|
||||
/// <param name="obj">The obj.</param>
|
||||
/// <returns>System.Byte[][].</returns>
|
||||
public static byte[] SerializeToBytes(object obj)
|
||||
public byte[] SerializeToBytes(object obj)
|
||||
{
|
||||
using (var stream = new MemoryStream())
|
||||
{
|
||||
|
@ -150,63 +136,5 @@ namespace MediaBrowser.Common.Serialization
|
|||
return stream.ToArray();
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Reads an xml configuration file from the file system
|
||||
/// It will immediately re-serialize and save if new serialization data is available due to property changes
|
||||
/// </summary>
|
||||
/// <param name="type">The type.</param>
|
||||
/// <param name="path">The path.</param>
|
||||
/// <param name="logger">The logger.</param>
|
||||
/// <returns>System.Object.</returns>
|
||||
public static object GetXmlConfiguration(Type type, string path, ILogger logger)
|
||||
{
|
||||
logger.Info("Loading {0} at {1}", type.Name, path);
|
||||
|
||||
object configuration;
|
||||
|
||||
byte[] buffer = null;
|
||||
|
||||
// Use try/catch to avoid the extra file system lookup using File.Exists
|
||||
try
|
||||
{
|
||||
buffer = File.ReadAllBytes(path);
|
||||
|
||||
configuration = DeserializeFromBytes(type, buffer);
|
||||
}
|
||||
catch (FileNotFoundException)
|
||||
{
|
||||
configuration = Activator.CreateInstance(type);
|
||||
}
|
||||
|
||||
// Take the object we just got and serialize it back to bytes
|
||||
var newBytes = SerializeToBytes(configuration);
|
||||
|
||||
// If the file didn't exist before, or if something has changed, re-save
|
||||
if (buffer == null || !buffer.SequenceEqual(newBytes))
|
||||
{
|
||||
logger.Info("Saving {0} to {1}", type.Name, path);
|
||||
|
||||
// Save it after load in case we got new items
|
||||
File.WriteAllBytes(path, newBytes);
|
||||
}
|
||||
|
||||
return configuration;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Reads an xml configuration file from the file system
|
||||
/// It will immediately save the configuration after loading it, just
|
||||
/// in case there are new serializable properties
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <param name="path">The path.</param>
|
||||
/// <param name="logger">The logger.</param>
|
||||
/// <returns>``0.</returns>
|
||||
public static T GetXmlConfiguration<T>(string path, ILogger logger)
|
||||
where T : class
|
||||
{
|
||||
return GetXmlConfiguration(typeof(T), path, logger) as T;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -0,0 +1,5 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<packages>
|
||||
<package id="protobuf-net" version="2.0.0.621" targetFramework="net45" />
|
||||
<package id="ServiceStack.Text" version="3.9.37" targetFramework="net45" />
|
||||
</packages>
|
|
@ -2,16 +2,14 @@
|
|||
using MediaBrowser.Common.Net;
|
||||
using MediaBrowser.Common.Plugins;
|
||||
using MediaBrowser.Common.ScheduledTasks;
|
||||
using MediaBrowser.Common.Serialization;
|
||||
using MediaBrowser.Model.Configuration;
|
||||
using MediaBrowser.Model.Logging;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
using MediaBrowser.Model.System;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Diagnostics;
|
||||
using System.IO;
|
||||
using System.Linq;
|
||||
using System.Reflection;
|
||||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
|
@ -24,7 +22,7 @@ namespace MediaBrowser.Common.Kernel
|
|||
/// <typeparam name="TApplicationPathsType">The type of the T application paths type.</typeparam>
|
||||
public abstract class BaseKernel<TConfigurationType, TApplicationPathsType> : IDisposable, IKernel
|
||||
where TConfigurationType : BaseApplicationConfiguration, new()
|
||||
where TApplicationPathsType : BaseApplicationPaths, new()
|
||||
where TApplicationPathsType : IApplicationPaths
|
||||
{
|
||||
/// <summary>
|
||||
/// Occurs when [has pending restart changed].
|
||||
|
@ -129,7 +127,7 @@ namespace MediaBrowser.Common.Kernel
|
|||
get
|
||||
{
|
||||
// Lazy load
|
||||
LazyInitializer.EnsureInitialized(ref _configuration, ref _configurationLoaded, ref _configurationSyncLock, () => XmlSerializer.GetXmlConfiguration<TConfigurationType>(ApplicationPaths.SystemConfigurationFilePath, Logger));
|
||||
LazyInitializer.EnsureInitialized(ref _configuration, ref _configurationLoaded, ref _configurationSyncLock, () => GetXmlConfiguration<TConfigurationType>(ApplicationPaths.SystemConfigurationFilePath));
|
||||
return _configuration;
|
||||
}
|
||||
protected set
|
||||
|
@ -161,19 +159,6 @@ namespace MediaBrowser.Common.Kernel
|
|||
/// <value>The application paths.</value>
|
||||
public TApplicationPathsType ApplicationPaths { get; private set; }
|
||||
|
||||
/// <summary>
|
||||
/// The _failed assembly loads
|
||||
/// </summary>
|
||||
private readonly List<string> _failedPluginAssemblies = new List<string>();
|
||||
/// <summary>
|
||||
/// Gets the plugin assemblies that failed to load.
|
||||
/// </summary>
|
||||
/// <value>The failed assembly loads.</value>
|
||||
public IEnumerable<string> FailedPluginAssemblies
|
||||
{
|
||||
get { return _failedPluginAssemblies; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the list of currently loaded plugins
|
||||
/// </summary>
|
||||
|
@ -204,46 +189,6 @@ namespace MediaBrowser.Common.Kernel
|
|||
/// <value>The rest services.</value>
|
||||
public IEnumerable<IRestfulService> RestServices { get; private set; }
|
||||
|
||||
/// <summary>
|
||||
/// The disposable parts
|
||||
/// </summary>
|
||||
private readonly List<IDisposable> _disposableParts = new List<IDisposable>();
|
||||
|
||||
/// <summary>
|
||||
/// The _protobuf serializer initialized
|
||||
/// </summary>
|
||||
private bool _protobufSerializerInitialized;
|
||||
/// <summary>
|
||||
/// The _protobuf serializer sync lock
|
||||
/// </summary>
|
||||
private object _protobufSerializerSyncLock = new object();
|
||||
/// <summary>
|
||||
/// Gets a dynamically compiled generated serializer that can serialize protocontracts without reflection
|
||||
/// </summary>
|
||||
private DynamicProtobufSerializer _protobufSerializer;
|
||||
/// <summary>
|
||||
/// Gets the protobuf serializer.
|
||||
/// </summary>
|
||||
/// <value>The protobuf serializer.</value>
|
||||
public DynamicProtobufSerializer ProtobufSerializer
|
||||
{
|
||||
get
|
||||
{
|
||||
// Lazy load
|
||||
LazyInitializer.EnsureInitialized(ref _protobufSerializer, ref _protobufSerializerInitialized, ref _protobufSerializerSyncLock, () => DynamicProtobufSerializer.Create(AllTypes));
|
||||
return _protobufSerializer;
|
||||
}
|
||||
private set
|
||||
{
|
||||
_protobufSerializer = value;
|
||||
|
||||
if (value == null)
|
||||
{
|
||||
_protobufSerializerInitialized = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the UDP server port number.
|
||||
/// This can't be configurable because then the user would have to configure their client to discover the server.
|
||||
|
@ -301,42 +246,40 @@ namespace MediaBrowser.Common.Kernel
|
|||
protected IApplicationHost ApplicationHost { get; private set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the task manager.
|
||||
/// The _XML serializer
|
||||
/// </summary>
|
||||
/// <value>The task manager.</value>
|
||||
protected ITaskManager TaskManager { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the assemblies.
|
||||
/// </summary>
|
||||
/// <value>The assemblies.</value>
|
||||
protected Assembly[] Assemblies { get; private set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets all types.
|
||||
/// </summary>
|
||||
/// <value>All types.</value>
|
||||
public Type[] AllTypes { get; private set; }
|
||||
private readonly IXmlSerializer _xmlSerializer;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="BaseKernel{TApplicationPathsType}" /> class.
|
||||
/// </summary>
|
||||
/// <param name="appHost">The app host.</param>
|
||||
/// <param name="appPaths">The app paths.</param>
|
||||
/// <param name="xmlSerializer">The XML serializer.</param>
|
||||
/// <param name="logger">The logger.</param>
|
||||
/// <exception cref="System.ArgumentNullException">isoManager</exception>
|
||||
protected BaseKernel(IApplicationHost appHost, ILogger logger)
|
||||
protected BaseKernel(IApplicationHost appHost, TApplicationPathsType appPaths, IXmlSerializer xmlSerializer, ILogger logger)
|
||||
{
|
||||
if (appHost == null)
|
||||
{
|
||||
throw new ArgumentNullException("appHost");
|
||||
}
|
||||
|
||||
if (appPaths == null)
|
||||
{
|
||||
throw new ArgumentNullException("appPaths");
|
||||
}
|
||||
if (xmlSerializer == null)
|
||||
{
|
||||
throw new ArgumentNullException("xmlSerializer");
|
||||
}
|
||||
if (logger == null)
|
||||
{
|
||||
throw new ArgumentNullException("logger");
|
||||
}
|
||||
|
||||
ApplicationPaths = appPaths;
|
||||
ApplicationHost = appHost;
|
||||
_xmlSerializer = xmlSerializer;
|
||||
Logger = logger;
|
||||
}
|
||||
|
||||
|
@ -344,14 +287,12 @@ namespace MediaBrowser.Common.Kernel
|
|||
/// Initializes the Kernel
|
||||
/// </summary>
|
||||
/// <returns>Task.</returns>
|
||||
public async Task Init()
|
||||
public Task Init()
|
||||
{
|
||||
ApplicationPaths = new TApplicationPathsType();
|
||||
|
||||
IsFirstRun = !File.Exists(ApplicationPaths.SystemConfigurationFilePath);
|
||||
|
||||
// Performs initializations that can be reloaded at anytime
|
||||
await Reload().ConfigureAwait(false);
|
||||
return Reload();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
@ -377,7 +318,6 @@ namespace MediaBrowser.Common.Kernel
|
|||
{
|
||||
// Set these to null so that they can be lazy loaded again
|
||||
Configuration = null;
|
||||
ProtobufSerializer = null;
|
||||
|
||||
ReloadLogger();
|
||||
|
||||
|
@ -388,14 +328,12 @@ namespace MediaBrowser.Common.Kernel
|
|||
|
||||
await OnConfigurationLoaded().ConfigureAwait(false);
|
||||
|
||||
DisposeTaskManager();
|
||||
TaskManager = new TaskManager(Logger);
|
||||
FindParts();
|
||||
|
||||
Logger.Info("Loading Plugins");
|
||||
await ReloadComposableParts().ConfigureAwait(false);
|
||||
await OnComposablePartsLoaded().ConfigureAwait(false);
|
||||
|
||||
DisposeTcpManager();
|
||||
TcpManager = new TcpManager(ApplicationHost, this, ApplicationHost.Resolve<INetworkManager>(), Logger);
|
||||
TcpManager = (TcpManager)ApplicationHost.CreateInstance(typeof(TcpManager));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
@ -417,184 +355,14 @@ namespace MediaBrowser.Common.Kernel
|
|||
OnLoggerLoaded();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Uses MEF to locate plugins
|
||||
/// Subclasses can use this to locate types within plugins
|
||||
/// </summary>
|
||||
/// <returns>Task.</returns>
|
||||
private async Task ReloadComposableParts()
|
||||
{
|
||||
_failedPluginAssemblies.Clear();
|
||||
|
||||
DisposeComposableParts();
|
||||
|
||||
Assemblies = GetComposablePartAssemblies().ToArray();
|
||||
|
||||
AllTypes = Assemblies.SelectMany(GetTypes).ToArray();
|
||||
|
||||
ComposeParts(AllTypes);
|
||||
|
||||
await OnComposablePartsLoaded().ConfigureAwait(false);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Composes the parts.
|
||||
/// </summary>
|
||||
/// <param name="allTypes">All types.</param>
|
||||
private void ComposeParts(IEnumerable<Type> allTypes)
|
||||
{
|
||||
var concreteTypes = allTypes.Where(t => t.IsClass && !t.IsAbstract && !t.IsInterface && !t.IsGenericType).ToArray();
|
||||
|
||||
RegisterExportedValues();
|
||||
|
||||
FindParts(concreteTypes);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Composes the parts with ioc container.
|
||||
/// </summary>
|
||||
/// <param name="allTypes">All types.</param>
|
||||
protected virtual void FindParts(Type[] allTypes)
|
||||
protected virtual void FindParts()
|
||||
{
|
||||
RestServices = GetExports<IRestfulService>(allTypes);
|
||||
WebSocketListeners = GetExports<IWebSocketListener>(allTypes);
|
||||
Plugins = GetExports<IPlugin>(allTypes);
|
||||
|
||||
var tasks = GetExports<IScheduledTask>(allTypes, false);
|
||||
|
||||
TaskManager.AddTasks(tasks);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the exports.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <param name="allTypes">All types.</param>
|
||||
/// <param name="manageLiftime">if set to <c>true</c> [manage liftime].</param>
|
||||
/// <returns>IEnumerable{``0}.</returns>
|
||||
protected IEnumerable<T> GetExports<T>(Type[] allTypes, bool manageLiftime = true)
|
||||
{
|
||||
var currentType = typeof(T);
|
||||
|
||||
Logger.Info("Composing instances of " + currentType.Name);
|
||||
|
||||
var parts = allTypes.Where(currentType.IsAssignableFrom).Select(Instantiate).Cast<T>().ToArray();
|
||||
|
||||
if (manageLiftime)
|
||||
{
|
||||
_disposableParts.AddRange(parts.OfType<IDisposable>());
|
||||
}
|
||||
|
||||
return parts;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Instantiates the specified type.
|
||||
/// </summary>
|
||||
/// <param name="type">The type.</param>
|
||||
/// <returns>System.Object.</returns>
|
||||
private object Instantiate(Type type)
|
||||
{
|
||||
return ApplicationHost.CreateInstance(type);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Composes the exported values.
|
||||
/// </summary>
|
||||
/// <param name="container">The container.</param>
|
||||
protected virtual void RegisterExportedValues()
|
||||
{
|
||||
ApplicationHost.RegisterSingleInstance<IKernel>(this);
|
||||
ApplicationHost.RegisterSingleInstance(TaskManager);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the composable part assemblies.
|
||||
/// </summary>
|
||||
/// <returns>IEnumerable{Assembly}.</returns>
|
||||
protected virtual IEnumerable<Assembly> GetComposablePartAssemblies()
|
||||
{
|
||||
// Gets all plugin assemblies by first reading all bytes of the .dll and calling Assembly.Load against that
|
||||
// This will prevent the .dll file from getting locked, and allow us to replace it when needed
|
||||
var pluginAssemblies = Directory.EnumerateFiles(ApplicationPaths.PluginsPath, "*.dll", SearchOption.TopDirectoryOnly)
|
||||
.Select(file =>
|
||||
{
|
||||
try
|
||||
{
|
||||
return Assembly.Load(File.ReadAllBytes((file)));
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
_failedPluginAssemblies.Add(file);
|
||||
Logger.ErrorException("Error loading {0}", ex, file);
|
||||
return null;
|
||||
}
|
||||
|
||||
}).Where(a => a != null);
|
||||
|
||||
foreach (var pluginAssembly in pluginAssemblies)
|
||||
{
|
||||
yield return pluginAssembly;
|
||||
}
|
||||
|
||||
var runningDirectory = Path.GetDirectoryName(Process.GetCurrentProcess().MainModule.FileName);
|
||||
var corePluginDirectory = Path.Combine(runningDirectory, "CorePlugins");
|
||||
|
||||
// This will prevent the .dll file from getting locked, and allow us to replace it when needed
|
||||
pluginAssemblies = Directory.EnumerateFiles(corePluginDirectory, "*.dll", SearchOption.TopDirectoryOnly)
|
||||
.Select(file =>
|
||||
{
|
||||
try
|
||||
{
|
||||
return Assembly.Load(File.ReadAllBytes((file)));
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
_failedPluginAssemblies.Add(file);
|
||||
Logger.ErrorException("Error loading {0}", ex, file);
|
||||
return null;
|
||||
}
|
||||
|
||||
}).Where(a => a != null);
|
||||
|
||||
foreach (var pluginAssembly in pluginAssemblies)
|
||||
{
|
||||
yield return pluginAssembly;
|
||||
}
|
||||
|
||||
// Include composable parts in the Model assembly
|
||||
yield return typeof(SystemInfo).Assembly;
|
||||
|
||||
// Include composable parts in the Common assembly
|
||||
yield return Assembly.GetExecutingAssembly();
|
||||
|
||||
// Include composable parts in the subclass assembly
|
||||
yield return GetType().Assembly;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets a list of types within an assembly
|
||||
/// This will handle situations that would normally throw an exception - such as a type within the assembly that depends on some other non-existant reference
|
||||
/// </summary>
|
||||
/// <param name="assembly">The assembly.</param>
|
||||
/// <returns>IEnumerable{Type}.</returns>
|
||||
/// <exception cref="System.ArgumentNullException">assembly</exception>
|
||||
private static IEnumerable<Type> GetTypes(Assembly assembly)
|
||||
{
|
||||
if (assembly == null)
|
||||
{
|
||||
throw new ArgumentNullException("assembly");
|
||||
}
|
||||
|
||||
try
|
||||
{
|
||||
return assembly.GetTypes();
|
||||
}
|
||||
catch (ReflectionTypeLoadException ex)
|
||||
{
|
||||
// If it fails we can still get a list of the Types it was able to resolve
|
||||
return ex.Types.Where(t => t != null);
|
||||
}
|
||||
RestServices = ApplicationHost.GetExports<IRestfulService>();
|
||||
WebSocketListeners = ApplicationHost.GetExports<IWebSocketListener>();
|
||||
Plugins = ApplicationHost.GetExports<IPlugin>();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
@ -612,7 +380,7 @@ namespace MediaBrowser.Common.Kernel
|
|||
|
||||
try
|
||||
{
|
||||
plugin.Initialize(this, Logger);
|
||||
plugin.Initialize(this, _xmlSerializer, Logger);
|
||||
|
||||
Logger.Info("{0} {1} initialized.", plugin.Name, plugin.Version);
|
||||
}
|
||||
|
@ -654,12 +422,7 @@ namespace MediaBrowser.Common.Kernel
|
|||
if (dispose)
|
||||
{
|
||||
DisposeTcpManager();
|
||||
DisposeTaskManager();
|
||||
DisposeHttpManager();
|
||||
|
||||
DisposeComposableParts();
|
||||
|
||||
_disposableParts.Clear();
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -675,18 +438,6 @@ namespace MediaBrowser.Common.Kernel
|
|||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Disposes the task manager.
|
||||
/// </summary>
|
||||
private void DisposeTaskManager()
|
||||
{
|
||||
if (TaskManager != null)
|
||||
{
|
||||
TaskManager.Dispose();
|
||||
TaskManager = null;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Disposes the HTTP manager.
|
||||
/// </summary>
|
||||
|
@ -699,17 +450,6 @@ namespace MediaBrowser.Common.Kernel
|
|||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Disposes all objects gathered through MEF composable parts
|
||||
/// </summary>
|
||||
protected virtual void DisposeComposableParts()
|
||||
{
|
||||
foreach (var part in _disposableParts)
|
||||
{
|
||||
part.Dispose();
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the current application version
|
||||
/// </summary>
|
||||
|
@ -761,7 +501,7 @@ namespace MediaBrowser.Common.Kernel
|
|||
IsNetworkDeployed = ApplicationHost.CanSelfUpdate,
|
||||
WebSocketPortNumber = TcpManager.WebSocketPortNumber,
|
||||
SupportsNativeWebSocket = TcpManager.SupportsNativeWebSocket,
|
||||
FailedPluginAssemblies = FailedPluginAssemblies.ToArray()
|
||||
FailedPluginAssemblies = ApplicationHost.FailedAssemblies.ToArray()
|
||||
};
|
||||
}
|
||||
|
||||
|
@ -777,7 +517,7 @@ namespace MediaBrowser.Common.Kernel
|
|||
{
|
||||
lock (_configurationSaveLock)
|
||||
{
|
||||
XmlSerializer.SerializeToFile(Configuration, ApplicationPaths.SystemConfigurationFilePath);
|
||||
_xmlSerializer.SerializeToFile(Configuration, ApplicationPaths.SystemConfigurationFilePath);
|
||||
}
|
||||
|
||||
OnConfigurationUpdated();
|
||||
|
@ -787,7 +527,7 @@ namespace MediaBrowser.Common.Kernel
|
|||
/// Gets the application paths.
|
||||
/// </summary>
|
||||
/// <value>The application paths.</value>
|
||||
BaseApplicationPaths IKernel.ApplicationPaths
|
||||
IApplicationPaths IKernel.ApplicationPaths
|
||||
{
|
||||
get { return ApplicationPaths; }
|
||||
}
|
||||
|
@ -798,6 +538,63 @@ namespace MediaBrowser.Common.Kernel
|
|||
BaseApplicationConfiguration IKernel.Configuration
|
||||
{
|
||||
get { return Configuration; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Reads an xml configuration file from the file system
|
||||
/// It will immediately re-serialize and save if new serialization data is available due to property changes
|
||||
/// </summary>
|
||||
/// <param name="type">The type.</param>
|
||||
/// <param name="path">The path.</param>
|
||||
/// <returns>System.Object.</returns>
|
||||
public object GetXmlConfiguration(Type type, string path)
|
||||
{
|
||||
Logger.Info("Loading {0} at {1}", type.Name, path);
|
||||
|
||||
object configuration;
|
||||
|
||||
byte[] buffer = null;
|
||||
|
||||
// Use try/catch to avoid the extra file system lookup using File.Exists
|
||||
try
|
||||
{
|
||||
buffer = File.ReadAllBytes(path);
|
||||
|
||||
configuration = _xmlSerializer.DeserializeFromBytes(type, buffer);
|
||||
}
|
||||
catch (FileNotFoundException)
|
||||
{
|
||||
configuration = ApplicationHost.CreateInstance(type);
|
||||
}
|
||||
|
||||
// Take the object we just got and serialize it back to bytes
|
||||
var newBytes = _xmlSerializer.SerializeToBytes(configuration);
|
||||
|
||||
// If the file didn't exist before, or if something has changed, re-save
|
||||
if (buffer == null || !buffer.SequenceEqual(newBytes))
|
||||
{
|
||||
Logger.Info("Saving {0} to {1}", type.Name, path);
|
||||
|
||||
// Save it after load in case we got new items
|
||||
File.WriteAllBytes(path, newBytes);
|
||||
}
|
||||
|
||||
return configuration;
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Reads an xml configuration file from the file system
|
||||
/// It will immediately save the configuration after loading it, just
|
||||
/// in case there are new serializable properties
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <param name="path">The path.</param>
|
||||
/// <returns>``0.</returns>
|
||||
private T GetXmlConfiguration<T>(string path)
|
||||
where T : class
|
||||
{
|
||||
return GetXmlConfiguration(typeof(T), path) as T;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,5 +1,6 @@
|
|||
using MediaBrowser.Model.Updates;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
|
@ -32,6 +33,26 @@ namespace MediaBrowser.Common.Kernel
|
|||
/// <value><c>true</c> if this instance can self update; otherwise, <c>false</c>.</value>
|
||||
bool CanSelfUpdate { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the failed assemblies.
|
||||
/// </summary>
|
||||
/// <value>The failed assemblies.</value>
|
||||
IEnumerable<string> FailedAssemblies { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets all concrete types.
|
||||
/// </summary>
|
||||
/// <value>All concrete types.</value>
|
||||
Type[] AllConcreteTypes { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the exports.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <param name="manageLiftime">if set to <c>true</c> [manage liftime].</param>
|
||||
/// <returns>IEnumerable{``0}.</returns>
|
||||
IEnumerable<T> GetExports<T>(bool manageLiftime = true);
|
||||
|
||||
/// <summary>
|
||||
/// Checks for update.
|
||||
/// </summary>
|
||||
|
|
|
@ -0,0 +1,76 @@
|
|||
|
||||
namespace MediaBrowser.Common.Kernel
|
||||
{
|
||||
/// <summary>
|
||||
/// Interface IApplicationPaths
|
||||
/// </summary>
|
||||
public interface IApplicationPaths
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets the path to the program data folder
|
||||
/// </summary>
|
||||
/// <value>The program data path.</value>
|
||||
string ProgramDataPath { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the folder path to the data directory
|
||||
/// </summary>
|
||||
/// <value>The data directory.</value>
|
||||
string DataPath { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the image cache path.
|
||||
/// </summary>
|
||||
/// <value>The image cache path.</value>
|
||||
string ImageCachePath { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the path to the plugin directory
|
||||
/// </summary>
|
||||
/// <value>The plugins path.</value>
|
||||
string PluginsPath { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the path to the plugin configurations directory
|
||||
/// </summary>
|
||||
/// <value>The plugin configurations path.</value>
|
||||
string PluginConfigurationsPath { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the path to where temporary update files will be stored
|
||||
/// </summary>
|
||||
/// <value>The plugin configurations path.</value>
|
||||
string TempUpdatePath { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the path to the log directory
|
||||
/// </summary>
|
||||
/// <value>The log directory path.</value>
|
||||
string LogDirectoryPath { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the path to the application configuration root directory
|
||||
/// </summary>
|
||||
/// <value>The configuration directory path.</value>
|
||||
string ConfigurationDirectoryPath { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the path to the system configuration file
|
||||
/// </summary>
|
||||
/// <value>The system configuration file path.</value>
|
||||
string SystemConfigurationFilePath { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the folder path to the cache directory
|
||||
/// </summary>
|
||||
/// <value>The cache directory.</value>
|
||||
string CachePath { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the folder path to the temp directory within the cache folder
|
||||
/// </summary>
|
||||
/// <value>The temp directory.</value>
|
||||
string TempDirectory { get; }
|
||||
}
|
||||
|
||||
}
|
|
@ -1,6 +1,5 @@
|
|||
using MediaBrowser.Common.Net;
|
||||
using MediaBrowser.Common.Plugins;
|
||||
using MediaBrowser.Common.Serialization;
|
||||
using MediaBrowser.Model.Configuration;
|
||||
using MediaBrowser.Model.System;
|
||||
using System;
|
||||
|
@ -18,7 +17,7 @@ namespace MediaBrowser.Common.Kernel
|
|||
/// Gets the application paths.
|
||||
/// </summary>
|
||||
/// <value>The application paths.</value>
|
||||
BaseApplicationPaths ApplicationPaths { get; }
|
||||
IApplicationPaths ApplicationPaths { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the configuration.
|
||||
|
@ -32,12 +31,6 @@ namespace MediaBrowser.Common.Kernel
|
|||
/// <value>The kernel context.</value>
|
||||
KernelContext KernelContext { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the protobuf serializer.
|
||||
/// </summary>
|
||||
/// <value>The protobuf serializer.</value>
|
||||
DynamicProtobufSerializer ProtobufSerializer { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Inits this instance.
|
||||
/// </summary>
|
||||
|
@ -156,5 +149,13 @@ namespace MediaBrowser.Common.Kernel
|
|||
/// Notifies the pending restart.
|
||||
/// </summary>
|
||||
void NotifyPendingRestart();
|
||||
|
||||
/// <summary>
|
||||
/// Gets the XML configuration.
|
||||
/// </summary>
|
||||
/// <param name="type">The type.</param>
|
||||
/// <param name="path">The path.</param>
|
||||
/// <returns>System.Object.</returns>
|
||||
object GetXmlConfiguration(Type type, string path);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,5 +1,4 @@
|
|||
using MediaBrowser.Common.Net;
|
||||
using MediaBrowser.Common.Serialization;
|
||||
using MediaBrowser.Model.Configuration;
|
||||
using MediaBrowser.Model.Logging;
|
||||
using System;
|
||||
|
@ -14,6 +13,7 @@ using System.Reflection;
|
|||
using System.Text;
|
||||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
|
||||
namespace MediaBrowser.Common.Kernel
|
||||
{
|
||||
|
@ -35,6 +35,12 @@ namespace MediaBrowser.Common.Kernel
|
|||
/// <value>The HTTP server.</value>
|
||||
private IHttpServer HttpServer { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the json serializer.
|
||||
/// </summary>
|
||||
/// <value>The json serializer.</value>
|
||||
private IJsonSerializer _jsonSerializer;
|
||||
|
||||
/// <summary>
|
||||
/// This subscribes to HttpListener requests and finds the appropriate BaseHandler to process it
|
||||
/// </summary>
|
||||
|
@ -96,8 +102,10 @@ namespace MediaBrowser.Common.Kernel
|
|||
/// <param name="applicationHost">The application host.</param>
|
||||
/// <param name="kernel">The kernel.</param>
|
||||
/// <param name="networkManager">The network manager.</param>
|
||||
/// <param name="jsonSerializer">The json serializer.</param>
|
||||
/// <param name="logger">The logger.</param>
|
||||
public TcpManager(IApplicationHost applicationHost, IKernel kernel, INetworkManager networkManager, ILogger logger)
|
||||
/// <exception cref="System.ArgumentNullException">applicationHost</exception>
|
||||
public TcpManager(IApplicationHost applicationHost, IKernel kernel, INetworkManager networkManager, IJsonSerializer jsonSerializer, ILogger logger)
|
||||
{
|
||||
if (applicationHost == null)
|
||||
{
|
||||
|
@ -111,12 +119,17 @@ namespace MediaBrowser.Common.Kernel
|
|||
{
|
||||
throw new ArgumentNullException("networkManager");
|
||||
}
|
||||
if (jsonSerializer == null)
|
||||
{
|
||||
throw new ArgumentNullException("jsonSerializer");
|
||||
}
|
||||
if (logger == null)
|
||||
{
|
||||
throw new ArgumentNullException("logger");
|
||||
}
|
||||
|
||||
_logger = logger;
|
||||
_jsonSerializer = jsonSerializer;
|
||||
_kernel = kernel;
|
||||
_applicationHost = applicationHost;
|
||||
_networkManager = networkManager;
|
||||
|
@ -203,7 +216,7 @@ namespace MediaBrowser.Common.Kernel
|
|||
/// <param name="e">The <see cref="WebSocketConnectEventArgs" /> instance containing the event data.</param>
|
||||
void HttpServer_WebSocketConnected(object sender, WebSocketConnectEventArgs e)
|
||||
{
|
||||
var connection = new WebSocketConnection(e.WebSocket, e.Endpoint, ProcessWebSocketMessageReceived, _logger);
|
||||
var connection = new WebSocketConnection(e.WebSocket, e.Endpoint, ProcessWebSocketMessageReceived, _jsonSerializer, _logger);
|
||||
|
||||
_webSocketConnections.Add(connection);
|
||||
}
|
||||
|
@ -342,7 +355,7 @@ namespace MediaBrowser.Common.Kernel
|
|||
_logger.Info("Sending web socket message {0}", messageType);
|
||||
|
||||
var message = new WebSocketMessage<T> { MessageType = messageType, Data = dataFunction() };
|
||||
var bytes = JsonSerializer.SerializeToBytes(message);
|
||||
var bytes = _jsonSerializer.SerializeToBytes(message);
|
||||
|
||||
var tasks = connections.Select(s => Task.Run(() =>
|
||||
{
|
||||
|
|
|
@ -38,10 +38,6 @@
|
|||
</ApplicationIcon>
|
||||
</PropertyGroup>
|
||||
<ItemGroup>
|
||||
<Reference Include="protobuf-net, Version=2.0.0.621, Culture=neutral, PublicKeyToken=257b51d87d2e4d67, processorArchitecture=MSIL">
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>..\packages\protobuf-net.2.0.0.621\lib\net40\protobuf-net.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="ServiceStack, Version=3.9.37.0, Culture=neutral, processorArchitecture=MSIL">
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>..\packages\ServiceStack.3.9.37\lib\net35\ServiceStack.dll</HintPath>
|
||||
|
@ -75,14 +71,12 @@
|
|||
<HintPath>..\packages\ServiceStack.Text.3.9.37\lib\net35\ServiceStack.Text.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="System" />
|
||||
<Reference Include="System.Configuration" />
|
||||
<Reference Include="System.Core" />
|
||||
<Reference Include="System.Net" />
|
||||
<Reference Include="System.Net.Http" />
|
||||
<Reference Include="System.Net.Http.WebRequest" />
|
||||
<Reference Include="System.Web" />
|
||||
<Reference Include="Microsoft.CSharp" />
|
||||
<Reference Include="System.Xml" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Compile Include="..\SharedVersion.cs">
|
||||
|
@ -98,8 +92,8 @@
|
|||
<Compile Include="IO\IIsoMount.cs" />
|
||||
<Compile Include="IO\ProgressStream.cs" />
|
||||
<Compile Include="IO\StreamDefaults.cs" />
|
||||
<Compile Include="Kernel\BaseApplicationPaths.cs" />
|
||||
<Compile Include="Kernel\BasePeriodicWebSocketListener.cs" />
|
||||
<Compile Include="Kernel\IApplicationPaths.cs" />
|
||||
<Compile Include="Kernel\IWebSocketListener.cs" />
|
||||
<Compile Include="Kernel\IApplicationHost.cs" />
|
||||
<Compile Include="Kernel\IKernel.cs" />
|
||||
|
@ -116,7 +110,6 @@
|
|||
<Compile Include="Net\IWebSocket.cs" />
|
||||
<Compile Include="Net\IWebSocketServer.cs" />
|
||||
<Compile Include="Net\MimeTypes.cs" />
|
||||
<Compile Include="Net\NativeWebSocket.cs" />
|
||||
<Compile Include="Net\UdpMessageReceivedEventArgs.cs" />
|
||||
<Compile Include="Net\WebSocketConnectEventArgs.cs" />
|
||||
<Compile Include="Net\WebSocketConnection.cs" />
|
||||
|
@ -130,26 +123,18 @@
|
|||
<DependentUpon>Resources.resx</DependentUpon>
|
||||
</Compile>
|
||||
<Compile Include="ScheduledTasks\ITaskManager.cs" />
|
||||
<Compile Include="ScheduledTasks\TaskManager.cs" />
|
||||
<Compile Include="ScheduledTasks\Tasks\ReloadLoggerTask.cs" />
|
||||
<Compile Include="ScheduledTasks\ITaskTrigger.cs" />
|
||||
<Compile Include="ScheduledTasks\ScheduledTaskHelpers.cs" />
|
||||
<Compile Include="ScheduledTasks\StartupTrigger.cs" />
|
||||
<Compile Include="ScheduledTasks\SystemEventTrigger.cs" />
|
||||
<Compile Include="ScheduledTasks\Tasks\SystemUpdateTask.cs" />
|
||||
<Compile Include="Serialization\DynamicProtobufSerializer.cs" />
|
||||
<Compile Include="Serialization\JsonSerializer.cs" />
|
||||
<Compile Include="Kernel\BaseKernel.cs" />
|
||||
<Compile Include="Kernel\KernelContext.cs" />
|
||||
<Compile Include="Net\Handlers\BaseHandler.cs" />
|
||||
<Compile Include="Net\Handlers\BaseSerializationHandler.cs" />
|
||||
<Compile Include="Plugins\BasePlugin.cs" />
|
||||
<Compile Include="Properties\AssemblyInfo.cs" />
|
||||
<Compile Include="Serialization\XmlSerializer.cs" />
|
||||
<Compile Include="ScheduledTasks\BaseScheduledTask.cs" />
|
||||
<Compile Include="ScheduledTasks\BaseTaskTrigger.cs" />
|
||||
<Compile Include="ScheduledTasks\DailyTrigger.cs" />
|
||||
<Compile Include="ScheduledTasks\Tasks\DeleteCacheFileTask.cs" />
|
||||
<Compile Include="ScheduledTasks\Tasks\DeleteLogFileTask.cs" />
|
||||
<Compile Include="ScheduledTasks\IntervalTrigger.cs" />
|
||||
<Compile Include="ScheduledTasks\IScheduledTask.cs" />
|
||||
<Compile Include="ScheduledTasks\WeeklyTrigger.cs" />
|
||||
|
|
|
@ -1,6 +1,5 @@
|
|||
using MediaBrowser.Common.Extensions;
|
||||
using MediaBrowser.Common.Kernel;
|
||||
using MediaBrowser.Common.Serialization;
|
||||
using System;
|
||||
using System.IO;
|
||||
using System.Threading.Tasks;
|
||||
|
@ -104,15 +103,15 @@ namespace MediaBrowser.Common.Net.Handlers
|
|||
{
|
||||
return Task.Run(() =>
|
||||
{
|
||||
switch (SerializationFormat)
|
||||
{
|
||||
case SerializationFormat.Protobuf:
|
||||
Kernel.ProtobufSerializer.SerializeToStream(_objectToSerialize, stream);
|
||||
break;
|
||||
default:
|
||||
JsonSerializer.SerializeToStream(_objectToSerialize, stream);
|
||||
break;
|
||||
}
|
||||
//switch (SerializationFormat)
|
||||
//{
|
||||
// case SerializationFormat.Protobuf:
|
||||
// Kernel.ProtobufSerializer.SerializeToStream(_objectToSerialize, stream);
|
||||
// break;
|
||||
// default:
|
||||
// JsonSerializer.SerializeToStream(_objectToSerialize, stream);
|
||||
// break;
|
||||
//}
|
||||
});
|
||||
}
|
||||
}
|
||||
|
|
|
@ -20,7 +20,7 @@ namespace MediaBrowser.Common.Net
|
|||
/// Gets or sets the receive action.
|
||||
/// </summary>
|
||||
/// <value>The receive action.</value>
|
||||
Action<WebSocketMessageInfo> OnReceiveDelegate { get; set; }
|
||||
Action<byte[]> OnReceiveDelegate { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Sends the async.
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
using MediaBrowser.Common.Serialization;
|
||||
using System.IO;
|
||||
using MediaBrowser.Model.Logging;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
using System;
|
||||
using System.Net;
|
||||
using System.Net.WebSockets;
|
||||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
|
@ -38,14 +38,21 @@ namespace MediaBrowser.Common.Net
|
|||
/// </summary>
|
||||
private readonly ILogger _logger;
|
||||
|
||||
/// <summary>
|
||||
/// The _json serializer
|
||||
/// </summary>
|
||||
private readonly IJsonSerializer _jsonSerializer;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="WebSocketConnection" /> class.
|
||||
/// </summary>
|
||||
/// <param name="socket">The socket.</param>
|
||||
/// <param name="remoteEndPoint">The remote end point.</param>
|
||||
/// <param name="receiveAction">The receive action.</param>
|
||||
/// <param name="jsonSerializer">The json serializer.</param>
|
||||
/// <param name="logger">The logger.</param>
|
||||
/// <exception cref="System.ArgumentNullException">socket</exception>
|
||||
public WebSocketConnection(IWebSocket socket, string remoteEndPoint, Action<WebSocketMessageInfo> receiveAction, ILogger logger)
|
||||
public WebSocketConnection(IWebSocket socket, string remoteEndPoint, Action<WebSocketMessageInfo> receiveAction, IJsonSerializer jsonSerializer, ILogger logger)
|
||||
{
|
||||
if (socket == null)
|
||||
{
|
||||
|
@ -59,11 +66,16 @@ namespace MediaBrowser.Common.Net
|
|||
{
|
||||
throw new ArgumentNullException("receiveAction");
|
||||
}
|
||||
if (jsonSerializer == null)
|
||||
{
|
||||
throw new ArgumentNullException("jsonSerializer");
|
||||
}
|
||||
if (logger == null)
|
||||
{
|
||||
throw new ArgumentNullException("logger");
|
||||
}
|
||||
|
||||
_jsonSerializer = jsonSerializer;
|
||||
_socket = socket;
|
||||
_socket.OnReceiveDelegate = info => OnReceive(info, receiveAction);
|
||||
RemoteEndPoint = remoteEndPoint;
|
||||
|
@ -73,12 +85,19 @@ namespace MediaBrowser.Common.Net
|
|||
/// <summary>
|
||||
/// Called when [receive].
|
||||
/// </summary>
|
||||
/// <param name="info">The info.</param>
|
||||
/// <param name="bytes">The bytes.</param>
|
||||
/// <param name="callback">The callback.</param>
|
||||
private void OnReceive(WebSocketMessageInfo info, Action<WebSocketMessageInfo> callback)
|
||||
private void OnReceive(byte[] bytes, Action<WebSocketMessageInfo> callback)
|
||||
{
|
||||
try
|
||||
{
|
||||
WebSocketMessageInfo info;
|
||||
|
||||
using (var memoryStream = new MemoryStream(bytes))
|
||||
{
|
||||
info = _jsonSerializer.DeserializeFromStream<WebSocketMessageInfo>(memoryStream);
|
||||
}
|
||||
|
||||
info.Connection = this;
|
||||
|
||||
callback(info);
|
||||
|
@ -103,8 +122,8 @@ namespace MediaBrowser.Common.Net
|
|||
{
|
||||
throw new ArgumentNullException("message");
|
||||
}
|
||||
|
||||
var bytes = JsonSerializer.SerializeToBytes(message);
|
||||
|
||||
var bytes = _jsonSerializer.SerializeToBytes(message);
|
||||
|
||||
return SendAsync(bytes, cancellationToken);
|
||||
}
|
||||
|
|
|
@ -1,5 +1,4 @@
|
|||
using MediaBrowser.Common.Kernel;
|
||||
using MediaBrowser.Common.Serialization;
|
||||
using MediaBrowser.Model.Logging;
|
||||
using MediaBrowser.Model.Plugins;
|
||||
using System;
|
||||
|
@ -7,6 +6,7 @@ using System.IO;
|
|||
using System.Reflection;
|
||||
using System.Runtime.InteropServices;
|
||||
using System.Threading;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
|
||||
namespace MediaBrowser.Common.Plugins
|
||||
{
|
||||
|
@ -188,7 +188,7 @@ namespace MediaBrowser.Common.Plugins
|
|||
get
|
||||
{
|
||||
// Lazy load
|
||||
LazyInitializer.EnsureInitialized(ref _configuration, ref _configurationInitialized, ref _configurationSyncLock, () => XmlSerializer.GetXmlConfiguration(ConfigurationType, ConfigurationFilePath, Logger) as TConfigurationType);
|
||||
LazyInitializer.EnsureInitialized(ref _configuration, ref _configurationInitialized, ref _configurationSyncLock, () => Kernel.GetXmlConfiguration(ConfigurationType, ConfigurationFilePath) as TConfigurationType);
|
||||
return _configuration;
|
||||
}
|
||||
protected set
|
||||
|
@ -269,26 +269,38 @@ namespace MediaBrowser.Common.Plugins
|
|||
/// <value>The logger.</value>
|
||||
public ILogger Logger { get; private set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the XML serializer.
|
||||
/// </summary>
|
||||
/// <value>The XML serializer.</value>
|
||||
protected IXmlSerializer XmlSerializer { get; private set; }
|
||||
|
||||
/// <summary>
|
||||
/// Starts the plugin.
|
||||
/// </summary>
|
||||
/// <param name="kernel">The kernel.</param>
|
||||
/// <param name="xmlSerializer">The XML serializer.</param>
|
||||
/// <param name="logger">The logger.</param>
|
||||
/// <exception cref="System.ArgumentNullException">kernel</exception>
|
||||
public void Initialize(IKernel kernel, ILogger logger)
|
||||
public void Initialize(IKernel kernel, IXmlSerializer xmlSerializer, ILogger logger)
|
||||
{
|
||||
if (kernel == null)
|
||||
{
|
||||
throw new ArgumentNullException("kernel");
|
||||
}
|
||||
|
||||
if (xmlSerializer == null)
|
||||
{
|
||||
throw new ArgumentNullException("xmlSerializer");
|
||||
}
|
||||
|
||||
if (logger == null)
|
||||
{
|
||||
throw new ArgumentNullException("logger");
|
||||
}
|
||||
|
||||
|
||||
XmlSerializer = xmlSerializer;
|
||||
Logger = logger;
|
||||
|
||||
Kernel = kernel;
|
||||
|
||||
if (kernel.KernelContext == KernelContext.Server)
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
using MediaBrowser.Common.Kernel;
|
||||
using MediaBrowser.Model.Logging;
|
||||
using MediaBrowser.Model.Plugins;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
using System;
|
||||
|
||||
namespace MediaBrowser.Common.Plugins
|
||||
|
@ -107,9 +108,10 @@ namespace MediaBrowser.Common.Plugins
|
|||
/// Starts the plugin.
|
||||
/// </summary>
|
||||
/// <param name="kernel">The kernel.</param>
|
||||
/// <param name="xmlSerializer">The XML serializer.</param>
|
||||
/// <param name="logger">The logger.</param>
|
||||
/// <exception cref="System.ArgumentNullException">kernel</exception>
|
||||
void Initialize(IKernel kernel, ILogger logger);
|
||||
void Initialize(IKernel kernel, IXmlSerializer xmlSerializer, ILogger logger);
|
||||
|
||||
/// <summary>
|
||||
/// Disposes the plugins. Undos all actions performed during Init.
|
||||
|
|
|
@ -1,6 +1,5 @@
|
|||
using MediaBrowser.Common.Extensions;
|
||||
using MediaBrowser.Common.Kernel;
|
||||
using MediaBrowser.Common.Serialization;
|
||||
using MediaBrowser.Model.Logging;
|
||||
using MediaBrowser.Model.Tasks;
|
||||
using System;
|
||||
|
@ -90,7 +89,7 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
{
|
||||
try
|
||||
{
|
||||
return JsonSerializer.DeserializeFromFile<TaskResult>(HistoryFilePath);
|
||||
return TaskManager.GetLastExecutionResult(this);
|
||||
}
|
||||
catch (IOException)
|
||||
{
|
||||
|
@ -109,74 +108,6 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// The _scheduled tasks data directory
|
||||
/// </summary>
|
||||
private string _scheduledTasksDataDirectory;
|
||||
/// <summary>
|
||||
/// Gets the scheduled tasks data directory.
|
||||
/// </summary>
|
||||
/// <value>The scheduled tasks data directory.</value>
|
||||
private string ScheduledTasksDataDirectory
|
||||
{
|
||||
get
|
||||
{
|
||||
if (_scheduledTasksDataDirectory == null)
|
||||
{
|
||||
_scheduledTasksDataDirectory = Path.Combine(Kernel.ApplicationPaths.DataPath, "ScheduledTasks");
|
||||
|
||||
if (!Directory.Exists(_scheduledTasksDataDirectory))
|
||||
{
|
||||
Directory.CreateDirectory(_scheduledTasksDataDirectory);
|
||||
}
|
||||
}
|
||||
return _scheduledTasksDataDirectory;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// The _scheduled tasks configuration directory
|
||||
/// </summary>
|
||||
private string _scheduledTasksConfigurationDirectory;
|
||||
/// <summary>
|
||||
/// Gets the scheduled tasks configuration directory.
|
||||
/// </summary>
|
||||
/// <value>The scheduled tasks configuration directory.</value>
|
||||
private string ScheduledTasksConfigurationDirectory
|
||||
{
|
||||
get
|
||||
{
|
||||
if (_scheduledTasksConfigurationDirectory == null)
|
||||
{
|
||||
_scheduledTasksConfigurationDirectory = Path.Combine(Kernel.ApplicationPaths.ConfigurationDirectoryPath, "ScheduledTasks");
|
||||
|
||||
if (!Directory.Exists(_scheduledTasksConfigurationDirectory))
|
||||
{
|
||||
Directory.CreateDirectory(_scheduledTasksConfigurationDirectory);
|
||||
}
|
||||
}
|
||||
return _scheduledTasksConfigurationDirectory;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the configuration file path.
|
||||
/// </summary>
|
||||
/// <value>The configuration file path.</value>
|
||||
private string ConfigurationFilePath
|
||||
{
|
||||
get { return Path.Combine(ScheduledTasksConfigurationDirectory, Id + ".js"); }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the history file path.
|
||||
/// </summary>
|
||||
/// <value>The history file path.</value>
|
||||
private string HistoryFilePath
|
||||
{
|
||||
get { return Path.Combine(ScheduledTasksDataDirectory, Id + ".js"); }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the current cancellation token
|
||||
/// </summary>
|
||||
|
@ -217,7 +148,7 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
/// <summary>
|
||||
/// The _triggers
|
||||
/// </summary>
|
||||
private IEnumerable<BaseTaskTrigger> _triggers;
|
||||
private IEnumerable<ITaskTrigger> _triggers;
|
||||
/// <summary>
|
||||
/// The _triggers initialized
|
||||
/// </summary>
|
||||
|
@ -231,24 +162,11 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
/// </summary>
|
||||
/// <value>The triggers.</value>
|
||||
/// <exception cref="System.ArgumentNullException">value</exception>
|
||||
public IEnumerable<BaseTaskTrigger> Triggers
|
||||
public IEnumerable<ITaskTrigger> Triggers
|
||||
{
|
||||
get
|
||||
{
|
||||
LazyInitializer.EnsureInitialized(ref _triggers, ref _triggersInitialized, ref _triggersSyncLock, () =>
|
||||
{
|
||||
try
|
||||
{
|
||||
return JsonSerializer.DeserializeFromFile<IEnumerable<TaskTriggerInfo>>(ConfigurationFilePath)
|
||||
.Select(ScheduledTaskHelpers.GetTrigger)
|
||||
.ToList();
|
||||
}
|
||||
catch (IOException)
|
||||
{
|
||||
// File doesn't exist. No biggie. Return defaults.
|
||||
return GetDefaultTriggers();
|
||||
}
|
||||
});
|
||||
LazyInitializer.EnsureInitialized(ref _triggers, ref _triggersInitialized, ref _triggersSyncLock, () => TaskManager.LoadTriggers(this));
|
||||
|
||||
return _triggers;
|
||||
}
|
||||
|
@ -271,7 +189,7 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
|
||||
ReloadTriggerEvents(false);
|
||||
|
||||
JsonSerializer.SerializeToFile(_triggers.Select(ScheduledTaskHelpers.GetTriggerInfo), ConfigurationFilePath);
|
||||
TaskManager.SaveTriggers(this, _triggers);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -279,7 +197,7 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
/// Creates the triggers that define when the task will run
|
||||
/// </summary>
|
||||
/// <returns>IEnumerable{BaseTaskTrigger}.</returns>
|
||||
protected abstract IEnumerable<BaseTaskTrigger> GetDefaultTriggers();
|
||||
public abstract IEnumerable<ITaskTrigger> GetDefaultTriggers();
|
||||
|
||||
/// <summary>
|
||||
/// Returns the task to be executed
|
||||
|
@ -314,6 +232,7 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
/// The _id
|
||||
/// </summary>
|
||||
private Guid? _id;
|
||||
|
||||
/// <summary>
|
||||
/// Gets the unique id.
|
||||
/// </summary>
|
||||
|
@ -352,13 +271,19 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
/// </summary>
|
||||
/// <param name="sender">The source of the event.</param>
|
||||
/// <param name="e">The <see cref="EventArgs" /> instance containing the event data.</param>
|
||||
void trigger_Triggered(object sender, EventArgs e)
|
||||
async void trigger_Triggered(object sender, EventArgs e)
|
||||
{
|
||||
var trigger = (BaseTaskTrigger)sender;
|
||||
var trigger = (ITaskTrigger)sender;
|
||||
|
||||
Logger.Info("{0} fired for task: {1}", trigger.GetType().Name, Name);
|
||||
|
||||
trigger.Stop();
|
||||
|
||||
TaskManager.QueueScheduledTask(this);
|
||||
|
||||
await Task.Delay(1000).ConfigureAwait(false);
|
||||
|
||||
trigger.Start(false);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
@ -404,10 +329,9 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
status = TaskCompletionStatus.Failed;
|
||||
}
|
||||
|
||||
var startTime = CurrentExecutionStartTime;
|
||||
var endTime = DateTime.UtcNow;
|
||||
|
||||
LogResult(endTime, status);
|
||||
|
||||
Kernel.TcpManager.SendWebSocketMessage("ScheduledTaskEndExecute", LastExecutionResult);
|
||||
|
||||
progress.ProgressChanged -= progress_ProgressChanged;
|
||||
|
@ -415,33 +339,7 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
CurrentCancellationTokenSource = null;
|
||||
CurrentProgress = null;
|
||||
|
||||
TaskManager.OnTaskCompleted(this);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Logs the result.
|
||||
/// </summary>
|
||||
/// <param name="endTime">The end time.</param>
|
||||
/// <param name="status">The status.</param>
|
||||
private void LogResult(DateTime endTime, TaskCompletionStatus status)
|
||||
{
|
||||
var startTime = CurrentExecutionStartTime;
|
||||
var elapsedTime = endTime - startTime;
|
||||
|
||||
Logger.Info("{0} {1} after {2} minute(s) and {3} seconds", Name, status, Math.Truncate(elapsedTime.TotalMinutes), elapsedTime.Seconds);
|
||||
|
||||
var result = new TaskResult
|
||||
{
|
||||
StartTimeUtc = startTime,
|
||||
EndTimeUtc = endTime,
|
||||
Status = status,
|
||||
Name = Name,
|
||||
Id = Id
|
||||
};
|
||||
|
||||
JsonSerializer.SerializeToFile(result, HistoryFilePath);
|
||||
|
||||
LastExecutionResult = result;
|
||||
TaskManager.OnTaskCompleted(this, startTime, endTime, status);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
@ -501,7 +399,7 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
|
||||
if (State == TaskState.Running)
|
||||
{
|
||||
LogResult(DateTime.UtcNow, TaskCompletionStatus.Aborted);
|
||||
TaskManager.OnTaskCompleted(this, CurrentExecutionStartTime, DateTime.UtcNow, TaskCompletionStatus.Aborted);
|
||||
}
|
||||
|
||||
if (CurrentCancellationTokenSource != null)
|
||||
|
@ -519,7 +417,7 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
foreach (var trigger in Triggers)
|
||||
{
|
||||
trigger.Triggered -= trigger_Triggered;
|
||||
trigger.Dispose();
|
||||
trigger.Stop();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,64 +0,0 @@
|
|||
using System;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace MediaBrowser.Common.ScheduledTasks
|
||||
{
|
||||
/// <summary>
|
||||
/// Use to indicate that a scheduled task should run
|
||||
/// </summary>
|
||||
public abstract class BaseTaskTrigger : IDisposable
|
||||
{
|
||||
/// <summary>
|
||||
/// Fires when the trigger condition is satisfied and the task should run
|
||||
/// </summary>
|
||||
internal event EventHandler<EventArgs> Triggered;
|
||||
|
||||
/// <summary>
|
||||
/// Called when [triggered].
|
||||
/// </summary>
|
||||
protected async void OnTriggered()
|
||||
{
|
||||
Stop();
|
||||
|
||||
if (Triggered != null)
|
||||
{
|
||||
Triggered(this, EventArgs.Empty);
|
||||
}
|
||||
|
||||
await Task.Delay(1000).ConfigureAwait(false);
|
||||
|
||||
Start(false);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Stars waiting for the trigger action
|
||||
/// </summary>
|
||||
protected internal abstract void Start(bool isApplicationStartup);
|
||||
|
||||
/// <summary>
|
||||
/// Stops waiting for the trigger action
|
||||
/// </summary>
|
||||
protected internal abstract void Stop();
|
||||
|
||||
/// <summary>
|
||||
/// Performs application-defined tasks associated with freeing, releasing, or resetting unmanaged resources.
|
||||
/// </summary>
|
||||
public void Dispose()
|
||||
{
|
||||
Dispose(true);
|
||||
GC.SuppressFinalize(this);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Releases unmanaged and - optionally - managed resources.
|
||||
/// </summary>
|
||||
/// <param name="dispose"><c>true</c> to release both managed and unmanaged resources; <c>false</c> to release only unmanaged resources.</param>
|
||||
protected virtual void Dispose(bool dispose)
|
||||
{
|
||||
if (dispose)
|
||||
{
|
||||
Stop();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
|
@ -6,7 +6,7 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
/// <summary>
|
||||
/// Represents a task trigger that fires everyday
|
||||
/// </summary>
|
||||
public class DailyTrigger : BaseTaskTrigger
|
||||
public class DailyTrigger : ITaskTrigger
|
||||
{
|
||||
/// <summary>
|
||||
/// Get the time of day to trigger the task to run
|
||||
|
@ -24,7 +24,7 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
/// Stars waiting for the trigger action
|
||||
/// </summary>
|
||||
/// <param name="isApplicationStartup">if set to <c>true</c> [is application startup].</param>
|
||||
protected internal override void Start(bool isApplicationStartup)
|
||||
public void Start(bool isApplicationStartup)
|
||||
{
|
||||
DisposeTimer();
|
||||
|
||||
|
@ -39,25 +39,11 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
/// <summary>
|
||||
/// Stops waiting for the trigger action
|
||||
/// </summary>
|
||||
protected internal override void Stop()
|
||||
public void Stop()
|
||||
{
|
||||
DisposeTimer();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Disposes this instance.
|
||||
/// </summary>
|
||||
/// <param name="dispose"><c>true</c> to release both managed and unmanaged resources; <c>false</c> to release only unmanaged resources.</param>
|
||||
protected override void Dispose(bool dispose)
|
||||
{
|
||||
if (dispose)
|
||||
{
|
||||
DisposeTimer();
|
||||
}
|
||||
|
||||
base.Dispose(dispose);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Disposes the timer.
|
||||
/// </summary>
|
||||
|
@ -68,5 +54,21 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
Timer.Dispose();
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Occurs when [triggered].
|
||||
/// </summary>
|
||||
public event EventHandler<EventArgs> Triggered;
|
||||
|
||||
/// <summary>
|
||||
/// Called when [triggered].
|
||||
/// </summary>
|
||||
private void OnTriggered()
|
||||
{
|
||||
if (Triggered != null)
|
||||
{
|
||||
Triggered(this, EventArgs.Empty);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -14,7 +14,7 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
/// Gets the triggers.
|
||||
/// </summary>
|
||||
/// <value>The triggers.</value>
|
||||
IEnumerable<BaseTaskTrigger> Triggers { get; set; }
|
||||
IEnumerable<ITaskTrigger> Triggers { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the last execution result.
|
||||
|
@ -75,5 +75,11 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
/// Cancels if running.
|
||||
/// </summary>
|
||||
void CancelIfRunning();
|
||||
|
||||
/// <summary>
|
||||
/// Gets the default triggers.
|
||||
/// </summary>
|
||||
/// <returns>IEnumerable{BaseTaskTrigger}.</returns>
|
||||
IEnumerable<ITaskTrigger> GetDefaultTriggers();
|
||||
}
|
||||
}
|
|
@ -1,4 +1,5 @@
|
|||
using System;
|
||||
using MediaBrowser.Model.Tasks;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
|
||||
namespace MediaBrowser.Common.ScheduledTasks
|
||||
|
@ -41,6 +42,30 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
/// Called when [task completed].
|
||||
/// </summary>
|
||||
/// <param name="task">The task.</param>
|
||||
void OnTaskCompleted(IScheduledTask task);
|
||||
/// <param name="startTime">The start time.</param>
|
||||
/// <param name="endTime">The end time.</param>
|
||||
/// <param name="status">The status.</param>
|
||||
void OnTaskCompleted(IScheduledTask task, DateTime startTime, DateTime endTime, TaskCompletionStatus status);
|
||||
|
||||
/// <summary>
|
||||
/// Gets the last execution result.
|
||||
/// </summary>
|
||||
/// <param name="task">The task.</param>
|
||||
/// <returns>TaskResult.</returns>
|
||||
TaskResult GetLastExecutionResult(IScheduledTask task);
|
||||
|
||||
/// <summary>
|
||||
/// Loads the triggers.
|
||||
/// </summary>
|
||||
/// <param name="task">The task.</param>
|
||||
/// <returns>IEnumerable{BaseTaskTrigger}.</returns>
|
||||
IEnumerable<ITaskTrigger> LoadTriggers(IScheduledTask task);
|
||||
|
||||
/// <summary>
|
||||
/// Saves the triggers.
|
||||
/// </summary>
|
||||
/// <param name="task">The task.</param>
|
||||
/// <param name="triggers">The triggers.</param>
|
||||
void SaveTriggers(IScheduledTask task, IEnumerable<ITaskTrigger> triggers);
|
||||
}
|
||||
}
|
|
@ -0,0 +1,26 @@
|
|||
using System;
|
||||
|
||||
namespace MediaBrowser.Common.ScheduledTasks
|
||||
{
|
||||
/// <summary>
|
||||
/// Interface ITaskTrigger
|
||||
/// </summary>
|
||||
public interface ITaskTrigger
|
||||
{
|
||||
/// <summary>
|
||||
/// Fires when the trigger condition is satisfied and the task should run
|
||||
/// </summary>
|
||||
event EventHandler<EventArgs> Triggered;
|
||||
|
||||
/// <summary>
|
||||
/// Stars waiting for the trigger action
|
||||
/// </summary>
|
||||
/// <param name="isApplicationStartup">if set to <c>true</c> [is application startup].</param>
|
||||
void Start(bool isApplicationStartup);
|
||||
|
||||
/// <summary>
|
||||
/// Stops waiting for the trigger action
|
||||
/// </summary>
|
||||
void Stop();
|
||||
}
|
||||
}
|
|
@ -6,7 +6,7 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
/// <summary>
|
||||
/// Represents a task trigger that runs repeatedly on an interval
|
||||
/// </summary>
|
||||
public class IntervalTrigger : BaseTaskTrigger
|
||||
public class IntervalTrigger : ITaskTrigger
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets or sets the interval.
|
||||
|
@ -24,7 +24,7 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
/// Stars waiting for the trigger action
|
||||
/// </summary>
|
||||
/// <param name="isApplicationStartup">if set to <c>true</c> [is application startup].</param>
|
||||
protected internal override void Start(bool isApplicationStartup)
|
||||
public void Start(bool isApplicationStartup)
|
||||
{
|
||||
DisposeTimer();
|
||||
|
||||
|
@ -34,25 +34,11 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
/// <summary>
|
||||
/// Stops waiting for the trigger action
|
||||
/// </summary>
|
||||
protected internal override void Stop()
|
||||
public void Stop()
|
||||
{
|
||||
DisposeTimer();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Disposes this instance.
|
||||
/// </summary>
|
||||
/// <param name="dispose"><c>true</c> to release both managed and unmanaged resources; <c>false</c> to release only unmanaged resources.</param>
|
||||
protected override void Dispose(bool dispose)
|
||||
{
|
||||
if (dispose)
|
||||
{
|
||||
DisposeTimer();
|
||||
}
|
||||
|
||||
base.Dispose(dispose);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Disposes the timer.
|
||||
/// </summary>
|
||||
|
@ -63,5 +49,21 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
Timer.Dispose();
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Occurs when [triggered].
|
||||
/// </summary>
|
||||
public event EventHandler<EventArgs> Triggered;
|
||||
|
||||
/// <summary>
|
||||
/// Called when [triggered].
|
||||
/// </summary>
|
||||
private void OnTriggered()
|
||||
{
|
||||
if (Triggered != null)
|
||||
{
|
||||
Triggered(this, EventArgs.Empty);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -35,7 +35,7 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
/// </summary>
|
||||
/// <param name="trigger">The trigger.</param>
|
||||
/// <returns>TaskTriggerInfo.</returns>
|
||||
public static TaskTriggerInfo GetTriggerInfo(BaseTaskTrigger trigger)
|
||||
public static TaskTriggerInfo GetTriggerInfo(ITaskTrigger trigger)
|
||||
{
|
||||
var info = new TaskTriggerInfo
|
||||
{
|
||||
|
@ -81,7 +81,7 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
/// <returns>BaseTaskTrigger.</returns>
|
||||
/// <exception cref="System.ArgumentNullException"></exception>
|
||||
/// <exception cref="System.ArgumentException">Invalid trigger type: + info.Type</exception>
|
||||
public static BaseTaskTrigger GetTrigger(TaskTriggerInfo info)
|
||||
public static ITaskTrigger GetTrigger(TaskTriggerInfo info)
|
||||
{
|
||||
if (info.Type.Equals(typeof(DailyTrigger).Name, StringComparison.OrdinalIgnoreCase))
|
||||
{
|
||||
|
|
|
@ -1,17 +1,18 @@
|
|||
using System.Threading.Tasks;
|
||||
using System;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace MediaBrowser.Common.ScheduledTasks
|
||||
{
|
||||
/// <summary>
|
||||
/// Class StartupTaskTrigger
|
||||
/// </summary>
|
||||
public class StartupTrigger : BaseTaskTrigger
|
||||
public class StartupTrigger : ITaskTrigger
|
||||
{
|
||||
/// <summary>
|
||||
/// Stars waiting for the trigger action
|
||||
/// </summary>
|
||||
/// <param name="isApplicationStartup">if set to <c>true</c> [is application startup].</param>
|
||||
protected internal async override void Start(bool isApplicationStartup)
|
||||
public async void Start(bool isApplicationStartup)
|
||||
{
|
||||
if (isApplicationStartup)
|
||||
{
|
||||
|
@ -24,8 +25,24 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
/// <summary>
|
||||
/// Stops waiting for the trigger action
|
||||
/// </summary>
|
||||
protected internal override void Stop()
|
||||
public void Stop()
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Occurs when [triggered].
|
||||
/// </summary>
|
||||
public event EventHandler<EventArgs> Triggered;
|
||||
|
||||
/// <summary>
|
||||
/// Called when [triggered].
|
||||
/// </summary>
|
||||
private void OnTriggered()
|
||||
{
|
||||
if (Triggered != null)
|
||||
{
|
||||
Triggered(this, EventArgs.Empty);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,5 +1,6 @@
|
|||
using MediaBrowser.Model.Tasks;
|
||||
using Microsoft.Win32;
|
||||
using System;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace MediaBrowser.Common.ScheduledTasks
|
||||
|
@ -7,7 +8,7 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
/// <summary>
|
||||
/// Class SystemEventTrigger
|
||||
/// </summary>
|
||||
public class SystemEventTrigger : BaseTaskTrigger
|
||||
public class SystemEventTrigger : ITaskTrigger
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets or sets the system event.
|
||||
|
@ -19,7 +20,7 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
/// Stars waiting for the trigger action
|
||||
/// </summary>
|
||||
/// <param name="isApplicationStartup">if set to <c>true</c> [is application startup].</param>
|
||||
protected internal override void Start(bool isApplicationStartup)
|
||||
public void Start(bool isApplicationStartup)
|
||||
{
|
||||
switch (SystemEvent)
|
||||
{
|
||||
|
@ -32,7 +33,7 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
/// <summary>
|
||||
/// Stops waiting for the trigger action
|
||||
/// </summary>
|
||||
protected internal override void Stop()
|
||||
public void Stop()
|
||||
{
|
||||
SystemEvents.PowerModeChanged -= SystemEvents_PowerModeChanged;
|
||||
}
|
||||
|
@ -52,5 +53,21 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
OnTriggered();
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Occurs when [triggered].
|
||||
/// </summary>
|
||||
public event EventHandler<EventArgs> Triggered;
|
||||
|
||||
/// <summary>
|
||||
/// Called when [triggered].
|
||||
/// </summary>
|
||||
private void OnTriggered()
|
||||
{
|
||||
if (Triggered != null)
|
||||
{
|
||||
Triggered(this, EventArgs.Empty);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,159 +0,0 @@
|
|||
using MediaBrowser.Model.Logging;
|
||||
using MediaBrowser.Model.Tasks;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
|
||||
namespace MediaBrowser.Common.ScheduledTasks
|
||||
{
|
||||
/// <summary>
|
||||
/// Class TaskManager
|
||||
/// </summary>
|
||||
internal class TaskManager : ITaskManager
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets the list of Scheduled Tasks
|
||||
/// </summary>
|
||||
/// <value>The scheduled tasks.</value>
|
||||
public IScheduledTask[] ScheduledTasks { get; private set; }
|
||||
|
||||
/// <summary>
|
||||
/// The _task queue
|
||||
/// </summary>
|
||||
private readonly List<Type> _taskQueue = new List<Type>();
|
||||
|
||||
/// <summary>
|
||||
/// The _logger
|
||||
/// </summary>
|
||||
private readonly ILogger _logger;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="TaskManager" /> class.
|
||||
/// </summary>
|
||||
/// <param name="logger">The logger.</param>
|
||||
public TaskManager(ILogger logger)
|
||||
{
|
||||
if (logger == null)
|
||||
{
|
||||
throw new ArgumentException("logger");
|
||||
}
|
||||
|
||||
_logger = logger;
|
||||
|
||||
ScheduledTasks = new IScheduledTask[] {};
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Cancels if running and queue.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
public void CancelIfRunningAndQueue<T>()
|
||||
where T : IScheduledTask
|
||||
{
|
||||
ScheduledTasks.OfType<T>().First().CancelIfRunning();
|
||||
QueueScheduledTask<T>();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Queues the scheduled task.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
public void QueueScheduledTask<T>()
|
||||
where T : IScheduledTask
|
||||
{
|
||||
var scheduledTask = ScheduledTasks.OfType<T>().First();
|
||||
|
||||
QueueScheduledTask(scheduledTask);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Queues the scheduled task.
|
||||
/// </summary>
|
||||
/// <param name="task">The task.</param>
|
||||
public void QueueScheduledTask(IScheduledTask task)
|
||||
{
|
||||
var type = task.GetType();
|
||||
|
||||
var scheduledTask = ScheduledTasks.First(t => t.GetType() == type);
|
||||
|
||||
lock (_taskQueue)
|
||||
{
|
||||
// If it's idle just execute immediately
|
||||
if (scheduledTask.State == TaskState.Idle)
|
||||
{
|
||||
scheduledTask.Execute();
|
||||
return;
|
||||
}
|
||||
|
||||
if (!_taskQueue.Contains(type))
|
||||
{
|
||||
_logger.Info("Queueing task {0}", type.Name);
|
||||
_taskQueue.Add(type);
|
||||
}
|
||||
else
|
||||
{
|
||||
_logger.Info("Task already queued: {0}", type.Name);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Called when [task completed].
|
||||
/// </summary>
|
||||
/// <param name="task">The task.</param>
|
||||
public void OnTaskCompleted(IScheduledTask task)
|
||||
{
|
||||
// Execute queued tasks
|
||||
lock (_taskQueue)
|
||||
{
|
||||
var copy = _taskQueue.ToList();
|
||||
|
||||
foreach (var type in copy)
|
||||
{
|
||||
var scheduledTask = ScheduledTasks.First(t => t.GetType() == type);
|
||||
|
||||
if (scheduledTask.State == TaskState.Idle)
|
||||
{
|
||||
scheduledTask.Execute();
|
||||
|
||||
_taskQueue.Remove(type);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Performs application-defined tasks associated with freeing, releasing, or resetting unmanaged resources.
|
||||
/// </summary>
|
||||
public void Dispose()
|
||||
{
|
||||
Dispose(true);
|
||||
GC.SuppressFinalize(this);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Releases unmanaged and - optionally - managed resources.
|
||||
/// </summary>
|
||||
/// <param name="dispose"><c>true</c> to release both managed and unmanaged resources; <c>false</c> to release only unmanaged resources.</param>
|
||||
protected virtual void Dispose(bool dispose)
|
||||
{
|
||||
foreach (var task in ScheduledTasks)
|
||||
{
|
||||
task.Dispose();
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Adds the tasks.
|
||||
/// </summary>
|
||||
/// <param name="tasks">The tasks.</param>
|
||||
public void AddTasks(IEnumerable<IScheduledTask> tasks)
|
||||
{
|
||||
var myTasks = ScheduledTasks.ToList();
|
||||
|
||||
myTasks.AddRange(tasks);
|
||||
|
||||
ScheduledTasks = myTasks.ToArray();
|
||||
}
|
||||
}
|
||||
}
|
|
@ -6,7 +6,7 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
/// <summary>
|
||||
/// Represents a task trigger that fires on a weekly basis
|
||||
/// </summary>
|
||||
public class WeeklyTrigger : BaseTaskTrigger
|
||||
public class WeeklyTrigger : ITaskTrigger
|
||||
{
|
||||
/// <summary>
|
||||
/// Get the time of day to trigger the task to run
|
||||
|
@ -30,7 +30,7 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
/// Stars waiting for the trigger action
|
||||
/// </summary>
|
||||
/// <param name="isApplicationStartup">if set to <c>true</c> [is application startup].</param>
|
||||
protected internal override void Start(bool isApplicationStartup)
|
||||
public void Start(bool isApplicationStartup)
|
||||
{
|
||||
DisposeTimer();
|
||||
|
||||
|
@ -69,25 +69,11 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
/// <summary>
|
||||
/// Stops waiting for the trigger action
|
||||
/// </summary>
|
||||
protected internal override void Stop()
|
||||
public void Stop()
|
||||
{
|
||||
DisposeTimer();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Disposes this instance.
|
||||
/// </summary>
|
||||
/// <param name="dispose"><c>true</c> to release both managed and unmanaged resources; <c>false</c> to release only unmanaged resources.</param>
|
||||
protected override void Dispose(bool dispose)
|
||||
{
|
||||
if (dispose)
|
||||
{
|
||||
DisposeTimer();
|
||||
}
|
||||
|
||||
base.Dispose(dispose);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Disposes the timer.
|
||||
/// </summary>
|
||||
|
@ -98,5 +84,21 @@ namespace MediaBrowser.Common.ScheduledTasks
|
|||
Timer.Dispose();
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Occurs when [triggered].
|
||||
/// </summary>
|
||||
public event EventHandler<EventArgs> Triggered;
|
||||
|
||||
/// <summary>
|
||||
/// Called when [triggered].
|
||||
/// </summary>
|
||||
private void OnTriggered()
|
||||
{
|
||||
if (Triggered != null)
|
||||
{
|
||||
Triggered(this, EventArgs.Empty);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,6 +1,5 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<packages>
|
||||
<package id="protobuf-net" version="2.0.0.621" targetFramework="net45" />
|
||||
<package id="ServiceStack" version="3.9.37" targetFramework="net45" />
|
||||
<package id="ServiceStack.Common" version="3.9.37" targetFramework="net45" />
|
||||
<package id="ServiceStack.OrmLite.SqlServer" version="3.9.37" targetFramework="net45" />
|
||||
|
|
|
@ -1,12 +1,12 @@
|
|||
using MediaBrowser.Common.Extensions;
|
||||
using MediaBrowser.Common.IO;
|
||||
using MediaBrowser.Common.Kernel;
|
||||
using MediaBrowser.Controller.Entities;
|
||||
using MediaBrowser.Controller.Entities.TV;
|
||||
using MediaBrowser.Controller.Providers;
|
||||
using MediaBrowser.Model.Drawing;
|
||||
using MediaBrowser.Model.Entities;
|
||||
using MediaBrowser.Model.Logging;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
using System;
|
||||
using System.Collections.Concurrent;
|
||||
using System.Collections.Generic;
|
||||
|
@ -22,7 +22,7 @@ namespace MediaBrowser.Controller.Drawing
|
|||
/// <summary>
|
||||
/// Class ImageManager
|
||||
/// </summary>
|
||||
public class ImageManager : BaseManager<Kernel>
|
||||
public class ImageManager : IDisposable
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets the image size cache.
|
||||
|
@ -57,20 +57,32 @@ namespace MediaBrowser.Controller.Drawing
|
|||
/// </summary>
|
||||
private readonly ILogger _logger;
|
||||
|
||||
/// <summary>
|
||||
/// The _protobuf serializer
|
||||
/// </summary>
|
||||
private readonly IProtobufSerializer _protobufSerializer;
|
||||
|
||||
/// <summary>
|
||||
/// The _kernel
|
||||
/// </summary>
|
||||
private readonly Kernel _kernel;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="ImageManager" /> class.
|
||||
/// </summary>
|
||||
/// <param name="kernel">The kernel.</param>
|
||||
/// <param name="protobufSerializer">The protobuf serializer.</param>
|
||||
/// <param name="logger">The logger.</param>
|
||||
public ImageManager(Kernel kernel, ILogger logger)
|
||||
: base(kernel)
|
||||
public ImageManager(Kernel kernel, IProtobufSerializer protobufSerializer, ILogger logger)
|
||||
{
|
||||
_protobufSerializer = protobufSerializer;
|
||||
_logger = logger;
|
||||
_kernel = kernel;
|
||||
|
||||
ImageSizeCache = new FileSystemRepository(Path.Combine(Kernel.ApplicationPaths.ImageCachePath, "image-sizes"));
|
||||
ResizedImageCache = new FileSystemRepository(Path.Combine(Kernel.ApplicationPaths.ImageCachePath, "resized-images"));
|
||||
CroppedImageCache = new FileSystemRepository(Path.Combine(Kernel.ApplicationPaths.ImageCachePath, "cropped-images"));
|
||||
EnhancedImageCache = new FileSystemRepository(Path.Combine(Kernel.ApplicationPaths.ImageCachePath, "enhanced-images"));
|
||||
ImageSizeCache = new FileSystemRepository(Path.Combine(_kernel.ApplicationPaths.ImageCachePath, "image-sizes"));
|
||||
ResizedImageCache = new FileSystemRepository(Path.Combine(_kernel.ApplicationPaths.ImageCachePath, "resized-images"));
|
||||
CroppedImageCache = new FileSystemRepository(Path.Combine(_kernel.ApplicationPaths.ImageCachePath, "cropped-images"));
|
||||
EnhancedImageCache = new FileSystemRepository(Path.Combine(_kernel.ApplicationPaths.ImageCachePath, "enhanced-images"));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
@ -276,7 +288,7 @@ namespace MediaBrowser.Controller.Drawing
|
|||
|
||||
try
|
||||
{
|
||||
var result = Kernel.ProtobufSerializer.DeserializeFromFile<int[]>(fullCachePath);
|
||||
var result = _protobufSerializer.DeserializeFromFile<int[]>(fullCachePath);
|
||||
|
||||
return new ImageSize { Width = result[0], Height = result[1] };
|
||||
}
|
||||
|
@ -305,7 +317,7 @@ namespace MediaBrowser.Controller.Drawing
|
|||
{
|
||||
var output = new[] { width, height };
|
||||
|
||||
Kernel.ProtobufSerializer.SerializeToFile(output, cachePath);
|
||||
_protobufSerializer.SerializeToFile(output, cachePath);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
@ -472,7 +484,7 @@ namespace MediaBrowser.Controller.Drawing
|
|||
throw new ArgumentNullException("item");
|
||||
}
|
||||
|
||||
var supportedEnhancers = Kernel.ImageEnhancers.Where(i => i.Supports(item, imageType)).ToList();
|
||||
var supportedEnhancers = _kernel.ImageEnhancers.Where(i => i.Supports(item, imageType)).ToList();
|
||||
|
||||
// No enhancement - don't cache
|
||||
if (supportedEnhancers.Count == 0)
|
||||
|
@ -526,7 +538,7 @@ namespace MediaBrowser.Controller.Drawing
|
|||
|
||||
var dateModified = GetImageDateModified(item, imagePath);
|
||||
|
||||
var supportedEnhancers = Kernel.ImageEnhancers.Where(i => i.Supports(item, imageType));
|
||||
var supportedEnhancers = _kernel.ImageEnhancers.Where(i => i.Supports(item, imageType));
|
||||
|
||||
return GetImageCacheTag(imagePath, dateModified, supportedEnhancers, item, imageType);
|
||||
}
|
||||
|
@ -600,11 +612,16 @@ namespace MediaBrowser.Controller.Drawing
|
|||
return result;
|
||||
}
|
||||
|
||||
public void Dispose()
|
||||
{
|
||||
Dispose(true);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Releases unmanaged and - optionally - managed resources.
|
||||
/// </summary>
|
||||
/// <param name="dispose"><c>true</c> to release both managed and unmanaged resources; <c>false</c> to release only unmanaged resources.</param>
|
||||
protected override void Dispose(bool dispose)
|
||||
protected void Dispose(bool dispose)
|
||||
{
|
||||
if (dispose)
|
||||
{
|
||||
|
@ -613,8 +630,6 @@ namespace MediaBrowser.Controller.Drawing
|
|||
CroppedImageCache.Dispose();
|
||||
EnhancedImageCache.Dispose();
|
||||
}
|
||||
|
||||
base.Dispose(dispose);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,15 +1,13 @@
|
|||
using MediaBrowser.Common.Extensions;
|
||||
using MediaBrowser.Common.IO;
|
||||
using MediaBrowser.Common.Serialization;
|
||||
using MediaBrowser.Controller.IO;
|
||||
using MediaBrowser.Model.Configuration;
|
||||
using MediaBrowser.Model.Tasks;
|
||||
using System;
|
||||
using System.IO;
|
||||
using System.Linq;
|
||||
using System.Runtime.Serialization;
|
||||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
|
||||
namespace MediaBrowser.Controller.Entities
|
||||
{
|
||||
|
@ -170,7 +168,7 @@ namespace MediaBrowser.Controller.Entities
|
|||
get
|
||||
{
|
||||
// Lazy load
|
||||
LazyInitializer.EnsureInitialized(ref _configuration, ref _configurationInitialized, ref _configurationSyncLock, () => XmlSerializer.GetXmlConfiguration<UserConfiguration>(ConfigurationFilePath, Logger));
|
||||
LazyInitializer.EnsureInitialized(ref _configuration, ref _configurationInitialized, ref _configurationSyncLock, () => (UserConfiguration)Kernel.Instance.GetXmlConfiguration(typeof(UserConfiguration), ConfigurationFilePath));
|
||||
return _configuration;
|
||||
}
|
||||
private set
|
||||
|
@ -338,9 +336,9 @@ namespace MediaBrowser.Controller.Entities
|
|||
/// <summary>
|
||||
/// Saves the current configuration to the file system
|
||||
/// </summary>
|
||||
public void SaveConfiguration()
|
||||
public void SaveConfiguration(IXmlSerializer serializer)
|
||||
{
|
||||
XmlSerializer.SerializeToFile(Configuration, ConfigurationFilePath);
|
||||
serializer.SerializeToFile(Configuration, ConfigurationFilePath);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
@ -376,8 +374,9 @@ namespace MediaBrowser.Controller.Entities
|
|||
/// Updates the configuration.
|
||||
/// </summary>
|
||||
/// <param name="config">The config.</param>
|
||||
/// <param name="serializer">The serializer.</param>
|
||||
/// <exception cref="System.ArgumentNullException">config</exception>
|
||||
public void UpdateConfiguration(UserConfiguration config)
|
||||
public void UpdateConfiguration(UserConfiguration config, IXmlSerializer serializer)
|
||||
{
|
||||
if (config == null)
|
||||
{
|
||||
|
@ -387,7 +386,7 @@ namespace MediaBrowser.Controller.Entities
|
|||
var customLibraryChanged = config.UseCustomLibrary != Configuration.UseCustomLibrary;
|
||||
|
||||
Configuration = config;
|
||||
SaveConfiguration();
|
||||
SaveConfiguration(serializer);
|
||||
|
||||
// Force these to be lazy loaded again
|
||||
if (customLibraryChanged)
|
||||
|
|
|
@ -0,0 +1,85 @@
|
|||
using MediaBrowser.Common.Kernel;
|
||||
|
||||
namespace MediaBrowser.Controller
|
||||
{
|
||||
public interface IServerApplicationPaths : IApplicationPaths
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets the path to the base root media directory
|
||||
/// </summary>
|
||||
/// <value>The root folder path.</value>
|
||||
string RootFolderPath { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the path to the default user view directory. Used if no specific user view is defined.
|
||||
/// </summary>
|
||||
/// <value>The default user views path.</value>
|
||||
string DefaultUserViewsPath { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the path to localization data.
|
||||
/// </summary>
|
||||
/// <value>The localization path.</value>
|
||||
string LocalizationPath { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the path to the Images By Name directory
|
||||
/// </summary>
|
||||
/// <value>The images by name path.</value>
|
||||
string ImagesByNamePath { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the path to the People directory
|
||||
/// </summary>
|
||||
/// <value>The people path.</value>
|
||||
string PeoplePath { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the path to the Genre directory
|
||||
/// </summary>
|
||||
/// <value>The genre path.</value>
|
||||
string GenrePath { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the path to the Studio directory
|
||||
/// </summary>
|
||||
/// <value>The studio path.</value>
|
||||
string StudioPath { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the path to the Year directory
|
||||
/// </summary>
|
||||
/// <value>The year path.</value>
|
||||
string YearPath { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the path to the General IBN directory
|
||||
/// </summary>
|
||||
/// <value>The general path.</value>
|
||||
string GeneralPath { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the path to the Ratings IBN directory
|
||||
/// </summary>
|
||||
/// <value>The ratings path.</value>
|
||||
string RatingsPath { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the path to the user configuration directory
|
||||
/// </summary>
|
||||
/// <value>The user configuration directory path.</value>
|
||||
string UserConfigurationDirectoryPath { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the FF MPEG stream cache path.
|
||||
/// </summary>
|
||||
/// <value>The FF MPEG stream cache path.</value>
|
||||
string FFMpegStreamCachePath { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the folder path to tools
|
||||
/// </summary>
|
||||
/// <value>The media tools path.</value>
|
||||
string MediaToolsPath { get; }
|
||||
}
|
||||
}
|
|
@ -1,5 +1,6 @@
|
|||
using MediaBrowser.Common.Kernel;
|
||||
using MediaBrowser.Common.Plugins;
|
||||
using MediaBrowser.Common.ScheduledTasks;
|
||||
using MediaBrowser.Controller.Drawing;
|
||||
using MediaBrowser.Controller.Entities;
|
||||
using MediaBrowser.Controller.IO;
|
||||
|
@ -16,6 +17,7 @@ using MediaBrowser.Controller.Updates;
|
|||
using MediaBrowser.Controller.Weather;
|
||||
using MediaBrowser.Model.Configuration;
|
||||
using MediaBrowser.Model.Logging;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
using MediaBrowser.Model.System;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
|
@ -28,7 +30,7 @@ namespace MediaBrowser.Controller
|
|||
/// <summary>
|
||||
/// Class Kernel
|
||||
/// </summary>
|
||||
public class Kernel : BaseKernel<ServerConfiguration, ServerApplicationPaths>
|
||||
public class Kernel : BaseKernel<ServerConfiguration, IServerApplicationPaths>
|
||||
{
|
||||
/// <summary>
|
||||
/// The MB admin URL
|
||||
|
@ -291,17 +293,24 @@ namespace MediaBrowser.Controller
|
|||
get { return 7359; }
|
||||
}
|
||||
|
||||
private readonly ITaskManager _taskManager;
|
||||
|
||||
/// <summary>
|
||||
/// Creates a kernel based on a Data path, which is akin to our current programdata path
|
||||
/// </summary>
|
||||
/// <param name="appHost">The app host.</param>
|
||||
/// <param name="appPaths">The app paths.</param>
|
||||
/// <param name="xmlSerializer">The XML serializer.</param>
|
||||
/// <param name="taskManager">The task manager.</param>
|
||||
/// <param name="logger">The logger.</param>
|
||||
/// <exception cref="System.ArgumentNullException">isoManager</exception>
|
||||
public Kernel(IApplicationHost appHost, ILogger logger)
|
||||
: base(appHost, logger)
|
||||
public Kernel(IApplicationHost appHost, IServerApplicationPaths appPaths, IXmlSerializer xmlSerializer, ITaskManager taskManager, ILogger logger)
|
||||
: base(appHost, appPaths, xmlSerializer, logger)
|
||||
{
|
||||
Instance = this;
|
||||
|
||||
_taskManager = taskManager;
|
||||
|
||||
// For now there's no real way to inject this properly
|
||||
BaseItem.Logger = logger;
|
||||
Ratings.Logger = logger;
|
||||
|
@ -310,21 +319,10 @@ namespace MediaBrowser.Controller
|
|||
BaseMetadataProvider.Logger = logger;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Composes the exported values.
|
||||
/// </summary>
|
||||
protected override void RegisterExportedValues()
|
||||
{
|
||||
ApplicationHost.RegisterSingleInstance(this);
|
||||
|
||||
base.RegisterExportedValues();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Composes the parts with ioc container.
|
||||
/// </summary>
|
||||
/// <param name="allTypes">All types.</param>
|
||||
protected override void FindParts(Type[] allTypes)
|
||||
protected override void FindParts()
|
||||
{
|
||||
InstallationManager = (InstallationManager)ApplicationHost.CreateInstance(typeof(InstallationManager));
|
||||
FFMpegManager = (FFMpegManager)ApplicationHost.CreateInstance(typeof(FFMpegManager));
|
||||
|
@ -335,21 +333,21 @@ namespace MediaBrowser.Controller
|
|||
UserDataManager = (UserDataManager)ApplicationHost.CreateInstance(typeof(UserDataManager));
|
||||
PluginSecurityManager = (PluginSecurityManager)ApplicationHost.CreateInstance(typeof(PluginSecurityManager));
|
||||
|
||||
base.FindParts(allTypes);
|
||||
base.FindParts();
|
||||
|
||||
EntityResolutionIgnoreRules = GetExports<IResolutionIgnoreRule>(allTypes);
|
||||
UserDataRepositories = GetExports<IUserDataRepository>(allTypes);
|
||||
UserRepositories = GetExports<IUserRepository>(allTypes);
|
||||
DisplayPreferencesRepositories = GetExports<IDisplayPreferencesRepository>(allTypes);
|
||||
ItemRepositories = GetExports<IItemRepository>(allTypes);
|
||||
WeatherProviders = GetExports<IWeatherProvider>(allTypes);
|
||||
IntroProviders = GetExports<IIntroProvider>(allTypes);
|
||||
PluginConfigurationPages = GetExports<IPluginConfigurationPage>(allTypes);
|
||||
ImageEnhancers = GetExports<IImageEnhancer>(allTypes).OrderBy(e => e.Priority).ToArray();
|
||||
PluginFolderCreators = GetExports<IVirtualFolderCreator>(allTypes);
|
||||
StringFiles = GetExports<LocalizedStringData>(allTypes);
|
||||
EntityResolvers = GetExports<IBaseItemResolver>(allTypes).OrderBy(e => e.Priority).ToArray();
|
||||
MetadataProviders = GetExports<BaseMetadataProvider>(allTypes).OrderBy(e => e.Priority).ToArray();
|
||||
EntityResolutionIgnoreRules = ApplicationHost.GetExports<IResolutionIgnoreRule>();
|
||||
UserDataRepositories = ApplicationHost.GetExports<IUserDataRepository>();
|
||||
UserRepositories = ApplicationHost.GetExports<IUserRepository>();
|
||||
DisplayPreferencesRepositories = ApplicationHost.GetExports<IDisplayPreferencesRepository>();
|
||||
ItemRepositories = ApplicationHost.GetExports<IItemRepository>();
|
||||
WeatherProviders = ApplicationHost.GetExports<IWeatherProvider>();
|
||||
IntroProviders = ApplicationHost.GetExports<IIntroProvider>();
|
||||
PluginConfigurationPages = ApplicationHost.GetExports<IPluginConfigurationPage>();
|
||||
ImageEnhancers = ApplicationHost.GetExports<IImageEnhancer>().OrderBy(e => e.Priority).ToArray();
|
||||
PluginFolderCreators = ApplicationHost.GetExports<IVirtualFolderCreator>();
|
||||
StringFiles = ApplicationHost.GetExports<LocalizedStringData>();
|
||||
EntityResolvers = ApplicationHost.GetExports<IBaseItemResolver>().OrderBy(e => e.Priority).ToArray();
|
||||
MetadataProviders = ApplicationHost.GetExports<BaseMetadataProvider>().OrderBy(e => e.Priority).ToArray();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
@ -471,7 +469,7 @@ namespace MediaBrowser.Controller
|
|||
{
|
||||
DisposeFileSystemManager();
|
||||
|
||||
FileSystemManager = new FileSystemManager(this, Logger, TaskManager);
|
||||
FileSystemManager = new FileSystemManager(this, Logger, _taskManager);
|
||||
FileSystemManager.StartWatchers();
|
||||
}
|
||||
|
||||
|
@ -570,11 +568,11 @@ namespace MediaBrowser.Controller
|
|||
ProviderManager.ValidateCurrentlyRunningProviders();
|
||||
|
||||
// Any number of configuration settings could change the way the library is refreshed, so do that now
|
||||
TaskManager.CancelIfRunningAndQueue<RefreshMediaLibraryTask>();
|
||||
_taskManager.CancelIfRunningAndQueue<RefreshMediaLibraryTask>();
|
||||
|
||||
if (refreshPeopleAfterUpdate)
|
||||
{
|
||||
TaskManager.CancelIfRunningAndQueue<PeopleValidationTask>();
|
||||
_taskManager.CancelIfRunningAndQueue<PeopleValidationTask>();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
|
|
@ -110,6 +110,7 @@
|
|||
<Compile Include="IO\FileSystem.cs" />
|
||||
<Compile Include="IO\FileSystemManager.cs" />
|
||||
<Compile Include="IO\NativeMethods.cs" />
|
||||
<Compile Include="IServerApplicationPaths.cs" />
|
||||
<Compile Include="Library\ChildrenChangedEventArgs.cs" />
|
||||
<Compile Include="Library\DtoBuilder.cs" />
|
||||
<Compile Include="Library\Profiler.cs" />
|
||||
|
@ -183,7 +184,6 @@
|
|||
<Compile Include="ScheduledTasks\PeopleValidationTask.cs" />
|
||||
<Compile Include="ScheduledTasks\PluginUpdateTask.cs" />
|
||||
<Compile Include="ScheduledTasks\RefreshMediaLibraryTask.cs" />
|
||||
<Compile Include="ServerApplicationPaths.cs" />
|
||||
<Compile Include="Library\ItemResolveArgs.cs" />
|
||||
<Compile Include="IO\DirectoryWatchers.cs" />
|
||||
<Compile Include="IO\FileData.cs" />
|
||||
|
|
|
@ -1,12 +1,10 @@
|
|||
using MediaBrowser.Common.Extensions;
|
||||
using MediaBrowser.Common.IO;
|
||||
using MediaBrowser.Common.Kernel;
|
||||
using MediaBrowser.Common.Serialization;
|
||||
using MediaBrowser.Common.IO;
|
||||
using MediaBrowser.Controller.Entities;
|
||||
using MediaBrowser.Controller.Entities.Audio;
|
||||
using MediaBrowser.Model.Entities;
|
||||
using MediaBrowser.Model.IO;
|
||||
using MediaBrowser.Model.Logging;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.ComponentModel;
|
||||
|
@ -23,7 +21,7 @@ namespace MediaBrowser.Controller.MediaInfo
|
|||
/// <summary>
|
||||
/// Class FFMpegManager
|
||||
/// </summary>
|
||||
public class FFMpegManager : BaseManager<Kernel>
|
||||
public class FFMpegManager : IDisposable
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets or sets the video image cache.
|
||||
|
@ -47,30 +45,66 @@ namespace MediaBrowser.Controller.MediaInfo
|
|||
/// Gets or sets the zip client.
|
||||
/// </summary>
|
||||
/// <value>The zip client.</value>
|
||||
private IZipClient ZipClient { get; set; }
|
||||
private readonly IZipClient _zipClient;
|
||||
|
||||
/// <summary>
|
||||
/// The _logger
|
||||
/// </summary>
|
||||
private readonly Kernel _kernel;
|
||||
|
||||
/// <summary>
|
||||
/// The _logger
|
||||
/// </summary>
|
||||
private readonly ILogger _logger;
|
||||
|
||||
/// <summary>
|
||||
/// Gets the json serializer.
|
||||
/// </summary>
|
||||
/// <value>The json serializer.</value>
|
||||
private readonly IJsonSerializer _jsonSerializer;
|
||||
|
||||
/// <summary>
|
||||
/// The _protobuf serializer
|
||||
/// </summary>
|
||||
private readonly IProtobufSerializer _protobufSerializer;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="FFMpegManager" /> class.
|
||||
/// </summary>
|
||||
/// <param name="kernel">The kernel.</param>
|
||||
/// <param name="zipClient">The zip client.</param>
|
||||
/// <param name="jsonSerializer">The json serializer.</param>
|
||||
/// <param name="protobufSerializer">The protobuf serializer.</param>
|
||||
/// <param name="logger">The logger.</param>
|
||||
/// <exception cref="System.ArgumentNullException">zipClient</exception>
|
||||
public FFMpegManager(Kernel kernel, IZipClient zipClient, ILogger logger)
|
||||
: base(kernel)
|
||||
public FFMpegManager(Kernel kernel, IZipClient zipClient, IJsonSerializer jsonSerializer, IProtobufSerializer protobufSerializer, ILogger logger)
|
||||
{
|
||||
if (kernel == null)
|
||||
{
|
||||
throw new ArgumentNullException("kernel");
|
||||
}
|
||||
if (zipClient == null)
|
||||
{
|
||||
throw new ArgumentNullException("zipClient");
|
||||
}
|
||||
if (jsonSerializer == null)
|
||||
{
|
||||
throw new ArgumentNullException("jsonSerializer");
|
||||
}
|
||||
if (protobufSerializer == null)
|
||||
{
|
||||
throw new ArgumentNullException("protobufSerializer");
|
||||
}
|
||||
if (logger == null)
|
||||
{
|
||||
throw new ArgumentNullException("logger");
|
||||
}
|
||||
|
||||
_kernel = kernel;
|
||||
_zipClient = zipClient;
|
||||
_jsonSerializer = jsonSerializer;
|
||||
_protobufSerializer = protobufSerializer;
|
||||
_logger = logger;
|
||||
ZipClient = zipClient;
|
||||
|
||||
// Not crazy about this but it's the only way to suppress ffmpeg crash dialog boxes
|
||||
SetErrorMode(ErrorModes.SEM_FAILCRITICALERRORS | ErrorModes.SEM_NOALIGNMENTFAULTEXCEPT | ErrorModes.SEM_NOGPFAULTERRORBOX | ErrorModes.SEM_NOOPENFILEERRORBOX);
|
||||
|
@ -82,11 +116,16 @@ namespace MediaBrowser.Controller.MediaInfo
|
|||
Task.Run(() => VersionedDirectoryPath = GetVersionedDirectoryPath());
|
||||
}
|
||||
|
||||
public void Dispose()
|
||||
{
|
||||
Dispose(true);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Releases unmanaged and - optionally - managed resources.
|
||||
/// </summary>
|
||||
/// <param name="dispose"><c>true</c> to release both managed and unmanaged resources; <c>false</c> to release only unmanaged resources.</param>
|
||||
protected override void Dispose(bool dispose)
|
||||
protected void Dispose(bool dispose)
|
||||
{
|
||||
if (dispose)
|
||||
{
|
||||
|
@ -95,8 +134,6 @@ namespace MediaBrowser.Controller.MediaInfo
|
|||
AudioImageCache.Dispose();
|
||||
VideoImageCache.Dispose();
|
||||
}
|
||||
|
||||
base.Dispose(dispose);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
@ -186,7 +223,7 @@ namespace MediaBrowser.Controller.MediaInfo
|
|||
{
|
||||
if (_videoImagesDataPath == null)
|
||||
{
|
||||
_videoImagesDataPath = Path.Combine(Kernel.ApplicationPaths.DataPath, "ffmpeg-video-images");
|
||||
_videoImagesDataPath = Path.Combine(_kernel.ApplicationPaths.DataPath, "ffmpeg-video-images");
|
||||
|
||||
if (!Directory.Exists(_videoImagesDataPath))
|
||||
{
|
||||
|
@ -212,7 +249,7 @@ namespace MediaBrowser.Controller.MediaInfo
|
|||
{
|
||||
if (_audioImagesDataPath == null)
|
||||
{
|
||||
_audioImagesDataPath = Path.Combine(Kernel.ApplicationPaths.DataPath, "ffmpeg-audio-images");
|
||||
_audioImagesDataPath = Path.Combine(_kernel.ApplicationPaths.DataPath, "ffmpeg-audio-images");
|
||||
|
||||
if (!Directory.Exists(_audioImagesDataPath))
|
||||
{
|
||||
|
@ -238,7 +275,7 @@ namespace MediaBrowser.Controller.MediaInfo
|
|||
{
|
||||
if (_subtitleCachePath == null)
|
||||
{
|
||||
_subtitleCachePath = Path.Combine(Kernel.ApplicationPaths.CachePath, "ffmpeg-subtitles");
|
||||
_subtitleCachePath = Path.Combine(_kernel.ApplicationPaths.CachePath, "ffmpeg-subtitles");
|
||||
|
||||
if (!Directory.Exists(_subtitleCachePath))
|
||||
{
|
||||
|
@ -265,7 +302,7 @@ namespace MediaBrowser.Controller.MediaInfo
|
|||
|
||||
var filename = resource.Substring(resource.IndexOf(prefix, StringComparison.OrdinalIgnoreCase) + prefix.Length);
|
||||
|
||||
var versionedDirectoryPath = Path.Combine(Kernel.ApplicationPaths.MediaToolsPath, Path.GetFileNameWithoutExtension(filename));
|
||||
var versionedDirectoryPath = Path.Combine(_kernel.ApplicationPaths.MediaToolsPath, Path.GetFileNameWithoutExtension(filename));
|
||||
|
||||
if (!Directory.Exists(versionedDirectoryPath))
|
||||
{
|
||||
|
@ -287,7 +324,7 @@ namespace MediaBrowser.Controller.MediaInfo
|
|||
{
|
||||
using (var resourceStream = assembly.GetManifestResourceStream(zipFileResourcePath))
|
||||
{
|
||||
ZipClient.ExtractAll(resourceStream, targetPath, false);
|
||||
_zipClient.ExtractAll(resourceStream, targetPath, false);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -353,7 +390,7 @@ namespace MediaBrowser.Controller.MediaInfo
|
|||
// Avoid File.Exists by just trying to deserialize
|
||||
try
|
||||
{
|
||||
return Task.FromResult(Kernel.ProtobufSerializer.DeserializeFromFile<FFProbeResult>(cacheFilePath));
|
||||
return Task.FromResult(_protobufSerializer.DeserializeFromFile<FFProbeResult>(cacheFilePath));
|
||||
}
|
||||
catch (FileNotFoundException)
|
||||
{
|
||||
|
@ -428,7 +465,7 @@ namespace MediaBrowser.Controller.MediaInfo
|
|||
process.BeginErrorReadLine();
|
||||
}
|
||||
|
||||
result = JsonSerializer.DeserializeFromStream<FFProbeResult>(process.StandardOutput.BaseStream);
|
||||
result = _jsonSerializer.DeserializeFromStream<FFProbeResult>(process.StandardOutput.BaseStream);
|
||||
|
||||
if (extractChapters)
|
||||
{
|
||||
|
@ -470,7 +507,7 @@ namespace MediaBrowser.Controller.MediaInfo
|
|||
AddChapters(result, standardError);
|
||||
}
|
||||
|
||||
Kernel.ProtobufSerializer.SerializeToFile(result, cacheFile);
|
||||
_protobufSerializer.SerializeToFile(result, cacheFile);
|
||||
|
||||
return result;
|
||||
}
|
||||
|
@ -595,7 +632,7 @@ namespace MediaBrowser.Controller.MediaInfo
|
|||
|
||||
if (saveItem && changesMade)
|
||||
{
|
||||
await Kernel.ItemRepository.SaveItem(video, CancellationToken.None).ConfigureAwait(false);
|
||||
await _kernel.ItemRepository.SaveItem(video, CancellationToken.None).ConfigureAwait(false);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -4,6 +4,7 @@ using MediaBrowser.Controller.Entities.Movies;
|
|||
using MediaBrowser.Controller.MediaInfo;
|
||||
using MediaBrowser.Model.Entities;
|
||||
using MediaBrowser.Model.MediaInfo;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
|
@ -28,29 +29,44 @@ namespace MediaBrowser.Controller.Providers.MediaInfo
|
|||
/// Gets or sets the bluray examiner.
|
||||
/// </summary>
|
||||
/// <value>The bluray examiner.</value>
|
||||
private IBlurayExaminer BlurayExaminer { get; set; }
|
||||
private readonly IBlurayExaminer _blurayExaminer;
|
||||
|
||||
/// <summary>
|
||||
/// <summary>
|
||||
/// The _iso manager
|
||||
/// </summary>
|
||||
private readonly IIsoManager _isoManager;
|
||||
|
||||
/// <summary>
|
||||
/// The _protobuf serializer
|
||||
/// </summary>
|
||||
private readonly IProtobufSerializer _protobufSerializer;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="FFProbeVideoInfoProvider" /> class.
|
||||
/// </summary>
|
||||
/// <param name="isoManager">The iso manager.</param>
|
||||
/// <param name="blurayExaminer">The bluray examiner.</param>
|
||||
/// <param name="protobufSerializer">The protobuf serializer.</param>
|
||||
/// <exception cref="System.ArgumentNullException">blurayExaminer</exception>
|
||||
public FFProbeVideoInfoProvider(IIsoManager isoManager, IBlurayExaminer blurayExaminer)
|
||||
public FFProbeVideoInfoProvider(IIsoManager isoManager, IBlurayExaminer blurayExaminer, IProtobufSerializer protobufSerializer)
|
||||
: base()
|
||||
{
|
||||
if (isoManager == null)
|
||||
{
|
||||
throw new ArgumentNullException("isoManager");
|
||||
}
|
||||
if (blurayExaminer == null)
|
||||
{
|
||||
throw new ArgumentNullException("blurayExaminer");
|
||||
}
|
||||
if (protobufSerializer == null)
|
||||
{
|
||||
throw new ArgumentNullException("protobufSerializer");
|
||||
}
|
||||
|
||||
BlurayExaminer = blurayExaminer;
|
||||
_blurayExaminer = blurayExaminer;
|
||||
_isoManager = isoManager;
|
||||
_protobufSerializer = protobufSerializer;
|
||||
|
||||
BdInfoCache = new FileSystemRepository(Path.Combine(Kernel.Instance.ApplicationPaths.CachePath, "bdinfo"));
|
||||
}
|
||||
|
@ -315,13 +331,13 @@ namespace MediaBrowser.Controller.Providers.MediaInfo
|
|||
|
||||
try
|
||||
{
|
||||
result = Kernel.Instance.ProtobufSerializer.DeserializeFromFile<BlurayDiscInfo>(cacheFile);
|
||||
result = _protobufSerializer.DeserializeFromFile<BlurayDiscInfo>(cacheFile);
|
||||
}
|
||||
catch (FileNotFoundException)
|
||||
{
|
||||
result = GetBDInfo(inputPath);
|
||||
|
||||
Kernel.Instance.ProtobufSerializer.SerializeToFile(result, cacheFile);
|
||||
_protobufSerializer.SerializeToFile(result, cacheFile);
|
||||
}
|
||||
|
||||
cancellationToken.ThrowIfCancellationRequested();
|
||||
|
@ -400,7 +416,7 @@ namespace MediaBrowser.Controller.Providers.MediaInfo
|
|||
/// <returns>VideoStream.</returns>
|
||||
private BlurayDiscInfo GetBDInfo(string path)
|
||||
{
|
||||
return BlurayExaminer.GetDiscInfo(path);
|
||||
return _blurayExaminer.GetDiscInfo(path);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
|
|
@ -1,5 +1,4 @@
|
|||
using MediaBrowser.Common.Extensions;
|
||||
using MediaBrowser.Common.Serialization;
|
||||
using MediaBrowser.Controller.Entities;
|
||||
using MediaBrowser.Controller.Entities.Movies;
|
||||
using MediaBrowser.Model.Entities;
|
||||
|
@ -15,6 +14,7 @@ using System.Text;
|
|||
using System.Text.RegularExpressions;
|
||||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
|
||||
namespace MediaBrowser.Controller.Providers.Movies
|
||||
{
|
||||
|
@ -30,6 +30,27 @@ namespace MediaBrowser.Controller.Providers.Movies
|
|||
/// </summary>
|
||||
public class MovieDbProvider : BaseMetadataProvider
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets the json serializer.
|
||||
/// </summary>
|
||||
/// <value>The json serializer.</value>
|
||||
protected IJsonSerializer JsonSerializer { get; private set; }
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="MovieDbProvider" /> class.
|
||||
/// </summary>
|
||||
/// <param name="jsonSerializer">The json serializer.</param>
|
||||
/// <exception cref="System.ArgumentNullException">jsonSerializer</exception>
|
||||
public MovieDbProvider(IJsonSerializer jsonSerializer)
|
||||
: base()
|
||||
{
|
||||
if (jsonSerializer == null)
|
||||
{
|
||||
throw new ArgumentNullException("jsonSerializer");
|
||||
}
|
||||
JsonSerializer = jsonSerializer;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the priority.
|
||||
/// </summary>
|
||||
|
@ -93,7 +114,7 @@ namespace MediaBrowser.Controller.Providers.Movies
|
|||
{
|
||||
get
|
||||
{
|
||||
LazyInitializer.EnsureInitialized(ref _tmdbSettingsTask, ref _tmdbSettingsTaskInitialized, ref _tmdbSettingsTaskSyncLock, GetTmdbSettings);
|
||||
LazyInitializer.EnsureInitialized(ref _tmdbSettingsTask, ref _tmdbSettingsTaskInitialized, ref _tmdbSettingsTaskSyncLock, () => GetTmdbSettings(JsonSerializer));
|
||||
return _tmdbSettingsTask;
|
||||
}
|
||||
}
|
||||
|
@ -102,13 +123,13 @@ namespace MediaBrowser.Controller.Providers.Movies
|
|||
/// Gets the TMDB settings.
|
||||
/// </summary>
|
||||
/// <returns>Task{TmdbSettingsResult}.</returns>
|
||||
private static async Task<TmdbSettingsResult> GetTmdbSettings()
|
||||
private static async Task<TmdbSettingsResult> GetTmdbSettings(IJsonSerializer jsonSerializer)
|
||||
{
|
||||
try
|
||||
{
|
||||
using (var json = await Kernel.Instance.HttpManager.Get(String.Format(TmdbConfigUrl, ApiKey), Kernel.Instance.ResourcePools.MovieDb, CancellationToken.None).ConfigureAwait(false))
|
||||
{
|
||||
return JsonSerializer.DeserializeFromStream<TmdbSettingsResult>(json);
|
||||
return jsonSerializer.DeserializeFromStream<TmdbSettingsResult>(json);
|
||||
}
|
||||
}
|
||||
catch (HttpException e)
|
||||
|
@ -168,7 +189,7 @@ namespace MediaBrowser.Controller.Providers.Movies
|
|||
{
|
||||
//in addition to ours, we need to set the last refreshed time for the local data provider
|
||||
//so it won't see the new files we download and process them all over again
|
||||
if (JsonProvider == null) JsonProvider = new MovieProviderFromJson();
|
||||
if (JsonProvider == null) JsonProvider = new MovieProviderFromJson(JsonSerializer);
|
||||
var data = item.ProviderData.GetValueOrDefault(JsonProvider.Id, new BaseProviderInfo { ProviderId = JsonProvider.Id });
|
||||
data.LastRefreshed = value;
|
||||
item.ProviderData[JsonProvider.Id] = data;
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
using MediaBrowser.Common.Serialization;
|
||||
using MediaBrowser.Controller.Entities;
|
||||
using MediaBrowser.Controller.Entities;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
using System;
|
||||
using System.IO;
|
||||
using System.Threading;
|
||||
|
@ -12,6 +12,10 @@ namespace MediaBrowser.Controller.Providers.Movies
|
|||
/// </summary>
|
||||
public class MovieProviderFromJson : MovieDbProvider
|
||||
{
|
||||
public MovieProviderFromJson(IJsonSerializer jsonSerializer) : base(jsonSerializer)
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the priority.
|
||||
/// </summary>
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
using MediaBrowser.Common.Serialization;
|
||||
using MediaBrowser.Controller.Entities;
|
||||
using MediaBrowser.Controller.Entities;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
using System;
|
||||
using System.IO;
|
||||
using System.Threading;
|
||||
|
@ -12,6 +12,10 @@ namespace MediaBrowser.Controller.Providers.Movies
|
|||
/// </summary>
|
||||
class PersonProviderFromJson : TmdbPersonProvider
|
||||
{
|
||||
public PersonProviderFromJson(IJsonSerializer jsonSerializer) : base(jsonSerializer)
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Supportses the specified item.
|
||||
/// </summary>
|
||||
|
|
|
@ -1,5 +1,4 @@
|
|||
using MediaBrowser.Common.Serialization;
|
||||
using MediaBrowser.Controller.Entities;
|
||||
using MediaBrowser.Controller.Entities;
|
||||
using MediaBrowser.Model.Entities;
|
||||
using MediaBrowser.Model.Net;
|
||||
using System;
|
||||
|
@ -10,6 +9,7 @@ using System.Linq;
|
|||
using System.Net;
|
||||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
|
||||
namespace MediaBrowser.Controller.Providers.Movies
|
||||
{
|
||||
|
@ -23,6 +23,27 @@ namespace MediaBrowser.Controller.Providers.Movies
|
|||
/// </summary>
|
||||
protected const string MetaFileName = "MBPerson.json";
|
||||
|
||||
/// <summary>
|
||||
/// Gets the json serializer.
|
||||
/// </summary>
|
||||
/// <value>The json serializer.</value>
|
||||
protected IJsonSerializer JsonSerializer { get; private set; }
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="MovieDbProvider" /> class.
|
||||
/// </summary>
|
||||
/// <param name="jsonSerializer">The json serializer.</param>
|
||||
/// <exception cref="System.ArgumentNullException">jsonSerializer</exception>
|
||||
public TmdbPersonProvider(IJsonSerializer jsonSerializer)
|
||||
: base()
|
||||
{
|
||||
if (jsonSerializer == null)
|
||||
{
|
||||
throw new ArgumentNullException("jsonSerializer");
|
||||
}
|
||||
JsonSerializer = jsonSerializer;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Supportses the specified item.
|
||||
/// </summary>
|
||||
|
@ -56,7 +77,7 @@ namespace MediaBrowser.Controller.Providers.Movies
|
|||
protected override async Task<bool> FetchAsyncInternal(BaseItem item, bool force, CancellationToken cancellationToken)
|
||||
{
|
||||
cancellationToken.ThrowIfCancellationRequested();
|
||||
|
||||
|
||||
var person = (Person)item;
|
||||
var tasks = new List<Task>();
|
||||
|
||||
|
@ -169,7 +190,7 @@ namespace MediaBrowser.Controller.Providers.Movies
|
|||
}
|
||||
|
||||
cancellationToken.ThrowIfCancellationRequested();
|
||||
|
||||
|
||||
if (searchResult != null && searchResult.Biography != null)
|
||||
{
|
||||
ProcessInfo(person, searchResult);
|
||||
|
|
|
@ -28,9 +28,9 @@ namespace MediaBrowser.Controller.ScheduledTasks
|
|||
/// Creates the triggers that define when the task will run
|
||||
/// </summary>
|
||||
/// <returns>IEnumerable{BaseTaskTrigger}.</returns>
|
||||
protected override IEnumerable<BaseTaskTrigger> GetDefaultTriggers()
|
||||
public override IEnumerable<ITaskTrigger> GetDefaultTriggers()
|
||||
{
|
||||
return new BaseTaskTrigger[]
|
||||
return new ITaskTrigger[]
|
||||
{
|
||||
new DailyTrigger { TimeOfDay = TimeSpan.FromHours(4) }
|
||||
};
|
||||
|
|
|
@ -20,7 +20,8 @@ namespace MediaBrowser.Controller.ScheduledTasks
|
|||
/// Initializes a new instance of the <see cref="ImageCleanupTask" /> class.
|
||||
/// </summary>
|
||||
/// <param name="kernel">The kernel.</param>
|
||||
/// <param name="logger"></param>
|
||||
/// <param name="taskManager">The task manager.</param>
|
||||
/// <param name="logger">The logger.</param>
|
||||
public ImageCleanupTask(Kernel kernel, ITaskManager taskManager, ILogger logger)
|
||||
: base(kernel, taskManager, logger)
|
||||
{
|
||||
|
@ -30,9 +31,9 @@ namespace MediaBrowser.Controller.ScheduledTasks
|
|||
/// Creates the triggers that define when the task will run
|
||||
/// </summary>
|
||||
/// <returns>IEnumerable{BaseTaskTrigger}.</returns>
|
||||
protected override IEnumerable<BaseTaskTrigger> GetDefaultTriggers()
|
||||
public override IEnumerable<ITaskTrigger> GetDefaultTriggers()
|
||||
{
|
||||
return new BaseTaskTrigger[]
|
||||
return new ITaskTrigger[]
|
||||
{
|
||||
new DailyTrigger { TimeOfDay = TimeSpan.FromHours(2) }
|
||||
};
|
||||
|
|
|
@ -26,9 +26,9 @@ namespace MediaBrowser.Controller.ScheduledTasks
|
|||
/// Creates the triggers that define when the task will run
|
||||
/// </summary>
|
||||
/// <returns>IEnumerable{BaseTaskTrigger}.</returns>
|
||||
protected override IEnumerable<BaseTaskTrigger> GetDefaultTriggers()
|
||||
public override IEnumerable<ITaskTrigger> GetDefaultTriggers()
|
||||
{
|
||||
return new BaseTaskTrigger[]
|
||||
return new ITaskTrigger[]
|
||||
{
|
||||
new DailyTrigger { TimeOfDay = TimeSpan.FromHours(2) },
|
||||
|
||||
|
|
|
@ -29,9 +29,9 @@ namespace MediaBrowser.Controller.ScheduledTasks
|
|||
/// Creates the triggers that define when the task will run
|
||||
/// </summary>
|
||||
/// <returns>IEnumerable{BaseTaskTrigger}.</returns>
|
||||
protected override IEnumerable<BaseTaskTrigger> GetDefaultTriggers()
|
||||
public override IEnumerable<ITaskTrigger> GetDefaultTriggers()
|
||||
{
|
||||
return new BaseTaskTrigger[] {
|
||||
return new ITaskTrigger[] {
|
||||
|
||||
// 1:30am
|
||||
new DailyTrigger { TimeOfDay = TimeSpan.FromHours(1.5) },
|
||||
|
|
|
@ -27,9 +27,9 @@ namespace MediaBrowser.Controller.ScheduledTasks
|
|||
/// Gets the default triggers.
|
||||
/// </summary>
|
||||
/// <returns>IEnumerable{BaseTaskTrigger}.</returns>
|
||||
protected override IEnumerable<BaseTaskTrigger> GetDefaultTriggers()
|
||||
public override IEnumerable<ITaskTrigger> GetDefaultTriggers()
|
||||
{
|
||||
return new BaseTaskTrigger[] {
|
||||
return new ITaskTrigger[] {
|
||||
|
||||
new StartupTrigger(),
|
||||
|
||||
|
|
|
@ -1,18 +1,17 @@
|
|||
using System.Security.Cryptography;
|
||||
using MediaBrowser.Common.Events;
|
||||
using MediaBrowser.Common.Kernel;
|
||||
using MediaBrowser.Common.Events;
|
||||
using MediaBrowser.Common.Net;
|
||||
using MediaBrowser.Common.Plugins;
|
||||
using MediaBrowser.Common.Progress;
|
||||
using MediaBrowser.Common.Serialization;
|
||||
using MediaBrowser.Model.IO;
|
||||
using MediaBrowser.Model.Logging;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
using MediaBrowser.Model.Updates;
|
||||
using System;
|
||||
using System.Collections.Concurrent;
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
using System.Linq;
|
||||
using System.Security.Cryptography;
|
||||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
|
@ -32,8 +31,8 @@ namespace MediaBrowser.Controller.Updates
|
|||
/// <summary>
|
||||
/// The completed installations
|
||||
/// </summary>
|
||||
public readonly ConcurrentBag<InstallationInfo> CompletedInstallations = new ConcurrentBag<InstallationInfo>();
|
||||
|
||||
public readonly ConcurrentBag<InstallationInfo> CompletedInstallations = new ConcurrentBag<InstallationInfo>();
|
||||
|
||||
#region PluginUninstalled Event
|
||||
/// <summary>
|
||||
/// Occurs when [plugin uninstalled].
|
||||
|
@ -68,7 +67,7 @@ namespace MediaBrowser.Controller.Updates
|
|||
_logger.Info("Plugin updated: {0} {1} {2}", newVersion.name, newVersion.version, newVersion.classification);
|
||||
|
||||
EventHelper.QueueEventIfNotNull(PluginUpdated, this, new GenericEventArgs<Tuple<IPlugin, PackageVersionInfo>> { Argument = new Tuple<IPlugin, PackageVersionInfo>(plugin, newVersion) }, _logger);
|
||||
|
||||
|
||||
Kernel.NotifyPendingRestart();
|
||||
}
|
||||
#endregion
|
||||
|
@ -108,15 +107,22 @@ namespace MediaBrowser.Controller.Updates
|
|||
/// </summary>
|
||||
private readonly INetworkManager _networkManager;
|
||||
|
||||
/// <summary>
|
||||
/// Gets the json serializer.
|
||||
/// </summary>
|
||||
/// <value>The json serializer.</value>
|
||||
protected IJsonSerializer JsonSerializer { get; private set; }
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="InstallationManager" /> class.
|
||||
/// </summary>
|
||||
/// <param name="kernel">The kernel.</param>
|
||||
/// <param name="zipClient">The zip client.</param>
|
||||
/// <param name="networkManager">The network manager.</param>
|
||||
/// <param name="jsonSerializer"></param>
|
||||
/// <param name="logger">The logger.</param>
|
||||
/// <exception cref="System.ArgumentNullException">zipClient</exception>
|
||||
public InstallationManager(Kernel kernel, IZipClient zipClient, INetworkManager networkManager, ILogger logger)
|
||||
public InstallationManager(Kernel kernel, IZipClient zipClient, INetworkManager networkManager, IJsonSerializer jsonSerializer, ILogger logger)
|
||||
: base(kernel)
|
||||
{
|
||||
if (zipClient == null)
|
||||
|
@ -131,6 +137,12 @@ namespace MediaBrowser.Controller.Updates
|
|||
{
|
||||
throw new ArgumentNullException("logger");
|
||||
}
|
||||
if (jsonSerializer == null)
|
||||
{
|
||||
throw new ArgumentNullException("jsonSerializer");
|
||||
}
|
||||
|
||||
JsonSerializer = jsonSerializer;
|
||||
|
||||
_networkManager = networkManager;
|
||||
_logger = logger;
|
||||
|
@ -161,7 +173,7 @@ namespace MediaBrowser.Controller.Updates
|
|||
package.versions = package.versions.Where(v => !string.IsNullOrWhiteSpace(v.sourceUrl))
|
||||
.OrderByDescending(v => v.version).ToList();
|
||||
}
|
||||
|
||||
|
||||
if (packageType.HasValue)
|
||||
{
|
||||
packages = packages.Where(p => p.type == packageType.Value).ToList();
|
||||
|
@ -178,7 +190,7 @@ namespace MediaBrowser.Controller.Updates
|
|||
|
||||
// Remove packages with no versions
|
||||
packages = packages.Where(p => p.versions.Any()).ToList();
|
||||
|
||||
|
||||
return packages;
|
||||
}
|
||||
}
|
||||
|
@ -320,7 +332,7 @@ namespace MediaBrowser.Controller.Updates
|
|||
var innerCancellationTokenSource = new CancellationTokenSource();
|
||||
|
||||
var tuple = new Tuple<InstallationInfo, CancellationTokenSource>(installationInfo, innerCancellationTokenSource);
|
||||
|
||||
|
||||
// Add it to the in-progress list
|
||||
lock (CurrentInstallations)
|
||||
{
|
||||
|
@ -364,7 +376,7 @@ namespace MediaBrowser.Controller.Updates
|
|||
_logger.Info("Package installation cancelled: {0} {1}", package.name, package.versionStr);
|
||||
|
||||
Kernel.TcpManager.SendWebSocketMessage("PackageInstallationCancelled", installationInfo);
|
||||
|
||||
|
||||
throw;
|
||||
}
|
||||
catch
|
||||
|
@ -373,7 +385,7 @@ namespace MediaBrowser.Controller.Updates
|
|||
{
|
||||
CurrentInstallations.Remove(tuple);
|
||||
}
|
||||
|
||||
|
||||
Kernel.TcpManager.SendWebSocketMessage("PackageInstallationFailed", installationInfo);
|
||||
|
||||
throw;
|
||||
|
@ -421,7 +433,7 @@ namespace MediaBrowser.Controller.Updates
|
|||
}
|
||||
|
||||
cancellationToken.ThrowIfCancellationRequested();
|
||||
|
||||
|
||||
// Success - move it to the real target based on type
|
||||
if (isArchive)
|
||||
{
|
||||
|
@ -435,7 +447,7 @@ namespace MediaBrowser.Controller.Updates
|
|||
throw;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
try
|
||||
|
@ -448,8 +460,8 @@ namespace MediaBrowser.Controller.Updates
|
|||
_logger.ErrorException("Error attempting to move file from {0} to {1}", e, tempFile, target);
|
||||
throw;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// Set last update time if we were installed before
|
||||
var plugin = Kernel.Plugins.FirstOrDefault(p => p.Name.Equals(package.name, StringComparison.OrdinalIgnoreCase));
|
||||
|
||||
|
|
|
@ -75,6 +75,9 @@
|
|||
<Compile Include="Net\HttpException.cs" />
|
||||
<Compile Include="Net\NetworkShare.cs" />
|
||||
<Compile Include="Net\NetworkShareType.cs" />
|
||||
<Compile Include="Serialization\IJsonSerializer.cs" />
|
||||
<Compile Include="Serialization\IProtobufSerializer.cs" />
|
||||
<Compile Include="Serialization\IXmlSerializer.cs" />
|
||||
<Compile Include="Updates\CheckForUpdateResult.cs" />
|
||||
<Compile Include="Updates\InstallationInfo.cs" />
|
||||
<Compile Include="Updates\PackageType.cs" />
|
||||
|
|
|
@ -0,0 +1,103 @@
|
|||
using System;
|
||||
using System.IO;
|
||||
|
||||
namespace MediaBrowser.Model.Serialization
|
||||
{
|
||||
public interface IJsonSerializer
|
||||
{
|
||||
/// <summary>
|
||||
/// Serializes to stream.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <param name="obj">The obj.</param>
|
||||
/// <param name="stream">The stream.</param>
|
||||
/// <exception cref="System.ArgumentNullException">obj</exception>
|
||||
void SerializeToStream<T>(T obj, Stream stream)
|
||||
where T : class;
|
||||
|
||||
/// <summary>
|
||||
/// Serializes to file.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <param name="obj">The obj.</param>
|
||||
/// <param name="file">The file.</param>
|
||||
/// <exception cref="System.ArgumentNullException">obj</exception>
|
||||
void SerializeToFile<T>(T obj, string file)
|
||||
where T : class;
|
||||
|
||||
/// <summary>
|
||||
/// Deserializes from file.
|
||||
/// </summary>
|
||||
/// <param name="type">The type.</param>
|
||||
/// <param name="file">The file.</param>
|
||||
/// <returns>System.Object.</returns>
|
||||
/// <exception cref="System.ArgumentNullException">type</exception>
|
||||
object DeserializeFromFile(Type type, string file);
|
||||
|
||||
/// <summary>
|
||||
/// Deserializes from file.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <param name="file">The file.</param>
|
||||
/// <returns>``0.</returns>
|
||||
/// <exception cref="System.ArgumentNullException">file</exception>
|
||||
T DeserializeFromFile<T>(string file)
|
||||
where T : class;
|
||||
|
||||
/// <summary>
|
||||
/// Deserializes from stream.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <param name="stream">The stream.</param>
|
||||
/// <returns>``0.</returns>
|
||||
/// <exception cref="System.ArgumentNullException">stream</exception>
|
||||
T DeserializeFromStream<T>(Stream stream);
|
||||
|
||||
/// <summary>
|
||||
/// Deserializes from string.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <param name="text">The text.</param>
|
||||
/// <returns>``0.</returns>
|
||||
/// <exception cref="System.ArgumentNullException">text</exception>
|
||||
T DeserializeFromString<T>(string text);
|
||||
|
||||
/// <summary>
|
||||
/// Deserializes from stream.
|
||||
/// </summary>
|
||||
/// <param name="stream">The stream.</param>
|
||||
/// <param name="type">The type.</param>
|
||||
/// <returns>System.Object.</returns>
|
||||
/// <exception cref="System.ArgumentNullException">stream</exception>
|
||||
object DeserializeFromStream(Stream stream, Type type);
|
||||
|
||||
/// <summary>
|
||||
/// Deserializes from string.
|
||||
/// </summary>
|
||||
/// <param name="json">The json.</param>
|
||||
/// <param name="type">The type.</param>
|
||||
/// <returns>System.Object.</returns>
|
||||
/// <exception cref="System.ArgumentNullException">json</exception>
|
||||
object DeserializeFromString(string json, Type type);
|
||||
|
||||
/// <summary>
|
||||
/// Serializes to string.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <param name="obj">The obj.</param>
|
||||
/// <returns>System.String.</returns>
|
||||
/// <exception cref="System.ArgumentNullException">obj</exception>
|
||||
string SerializeToString<T>(T obj)
|
||||
where T : class;
|
||||
|
||||
/// <summary>
|
||||
/// Serializes to bytes.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <param name="obj">The obj.</param>
|
||||
/// <returns>System.Byte[][].</returns>
|
||||
/// <exception cref="System.ArgumentNullException">obj</exception>
|
||||
byte[] SerializeToBytes<T>(T obj)
|
||||
where T : class;
|
||||
}
|
||||
}
|
|
@ -0,0 +1,63 @@
|
|||
using System;
|
||||
using System.IO;
|
||||
|
||||
namespace MediaBrowser.Model.Serialization
|
||||
{
|
||||
public interface IProtobufSerializer
|
||||
{
|
||||
/// <summary>
|
||||
/// Serializes to stream.
|
||||
/// </summary>
|
||||
/// <param name="obj">The obj.</param>
|
||||
/// <param name="stream">The stream.</param>
|
||||
/// <exception cref="System.ArgumentNullException">obj</exception>
|
||||
void SerializeToStream(object obj, Stream stream);
|
||||
|
||||
/// <summary>
|
||||
/// Deserializes from stream.
|
||||
/// </summary>
|
||||
/// <param name="stream">The stream.</param>
|
||||
/// <param name="type">The type.</param>
|
||||
/// <returns>System.Object.</returns>
|
||||
/// <exception cref="System.ArgumentNullException">stream</exception>
|
||||
object DeserializeFromStream(Stream stream, Type type);
|
||||
|
||||
/// <summary>
|
||||
/// Deserializes from stream.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <param name="stream">The stream.</param>
|
||||
/// <returns>``0.</returns>
|
||||
T DeserializeFromStream<T>(Stream stream)
|
||||
where T : class;
|
||||
|
||||
/// <summary>
|
||||
/// Serializes to file.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <param name="obj">The obj.</param>
|
||||
/// <param name="file">The file.</param>
|
||||
/// <exception cref="System.ArgumentNullException">file</exception>
|
||||
void SerializeToFile<T>(T obj, string file);
|
||||
|
||||
/// <summary>
|
||||
/// Deserializes from file.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <param name="file">The file.</param>
|
||||
/// <returns>``0.</returns>
|
||||
/// <exception cref="System.ArgumentNullException">file</exception>
|
||||
T DeserializeFromFile<T>(string file)
|
||||
where T : class;
|
||||
|
||||
/// <summary>
|
||||
/// Serializes to bytes.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <param name="obj">The obj.</param>
|
||||
/// <returns>System.Byte[][].</returns>
|
||||
/// <exception cref="System.ArgumentNullException">obj</exception>
|
||||
byte[] SerializeToBytes<T>(T obj)
|
||||
where T : class;
|
||||
}
|
||||
}
|
|
@ -0,0 +1,69 @@
|
|||
using System;
|
||||
using System.IO;
|
||||
|
||||
namespace MediaBrowser.Model.Serialization
|
||||
{
|
||||
public interface IXmlSerializer
|
||||
{
|
||||
/// <summary>
|
||||
/// Deserializes from stream.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <param name="stream">The stream.</param>
|
||||
/// <returns>``0.</returns>
|
||||
T DeserializeFromStream<T>(Stream stream);
|
||||
|
||||
/// <summary>
|
||||
/// Deserializes from stream.
|
||||
/// </summary>
|
||||
/// <param name="type">The type.</param>
|
||||
/// <param name="stream">The stream.</param>
|
||||
/// <returns>System.Object.</returns>
|
||||
object DeserializeFromStream(Type type, Stream stream);
|
||||
|
||||
/// <summary>
|
||||
/// Serializes to stream.
|
||||
/// </summary>
|
||||
/// <param name="obj">The obj.</param>
|
||||
/// <param name="stream">The stream.</param>
|
||||
void SerializeToStream(object obj, Stream stream);
|
||||
|
||||
/// <summary>
|
||||
/// Deserializes from file.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <param name="file">The file.</param>
|
||||
/// <returns>``0.</returns>
|
||||
T DeserializeFromFile<T>(string file);
|
||||
|
||||
/// <summary>
|
||||
/// Serializes to file.
|
||||
/// </summary>
|
||||
/// <param name="obj">The obj.</param>
|
||||
/// <param name="file">The file.</param>
|
||||
void SerializeToFile(object obj, string file);
|
||||
|
||||
/// <summary>
|
||||
/// Deserializes from file.
|
||||
/// </summary>
|
||||
/// <param name="type">The type.</param>
|
||||
/// <param name="file">The file.</param>
|
||||
/// <returns>System.Object.</returns>
|
||||
object DeserializeFromFile(Type type, string file);
|
||||
|
||||
/// <summary>
|
||||
/// Deserializes from bytes.
|
||||
/// </summary>
|
||||
/// <param name="type">The type.</param>
|
||||
/// <param name="buffer">The buffer.</param>
|
||||
/// <returns>System.Object.</returns>
|
||||
object DeserializeFromBytes(Type type, byte[] buffer);
|
||||
|
||||
/// <summary>
|
||||
/// Serializes to bytes.
|
||||
/// </summary>
|
||||
/// <param name="obj">The obj.</param>
|
||||
/// <returns>System.Byte[][].</returns>
|
||||
byte[] SerializeToBytes(object obj);
|
||||
}
|
||||
}
|
|
@ -112,6 +112,8 @@
|
|||
<Compile Include="Management\NetworkManager.cs" />
|
||||
<Compile Include="Management\NetworkShares.cs" />
|
||||
<Compile Include="Properties\AssemblyInfo.cs" />
|
||||
<Compile Include="Web\ServerFactory.cs" />
|
||||
<Compile Include="Web\NativeWebSocket.cs" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\MediaBrowser.Common\MediaBrowser.Common.csproj">
|
||||
|
|
|
@ -4,6 +4,7 @@ using MediaBrowser.Common.Extensions;
|
|||
using MediaBrowser.Common.Kernel;
|
||||
using MediaBrowser.Common.Net;
|
||||
using MediaBrowser.Model.Logging;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
using ServiceStack.Api.Swagger;
|
||||
using ServiceStack.Common.Web;
|
||||
using ServiceStack.Configuration;
|
||||
|
@ -60,6 +61,12 @@ namespace MediaBrowser.Networking.Web
|
|||
/// <value>The HTTP listener.</value>
|
||||
private IDisposable HttpListener { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the protobuf serializer.
|
||||
/// </summary>
|
||||
/// <value>The protobuf serializer.</value>
|
||||
private IProtobufSerializer ProtobufSerializer { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Occurs when [web socket connected].
|
||||
/// </summary>
|
||||
|
@ -82,17 +89,22 @@ namespace MediaBrowser.Networking.Web
|
|||
/// </summary>
|
||||
/// <param name="applicationHost">The application host.</param>
|
||||
/// <param name="kernel">The kernel.</param>
|
||||
/// <param name="protobufSerializer">The protobuf serializer.</param>
|
||||
/// <param name="logger">The logger.</param>
|
||||
/// <param name="serverName">Name of the server.</param>
|
||||
/// <param name="defaultRedirectpath">The default redirectpath.</param>
|
||||
/// <exception cref="System.ArgumentNullException">urlPrefix</exception>
|
||||
public HttpServer(IApplicationHost applicationHost, IKernel kernel, ILogger logger, string serverName, string defaultRedirectpath)
|
||||
public HttpServer(IApplicationHost applicationHost, IKernel kernel, IProtobufSerializer protobufSerializer, ILogger logger, string serverName, string defaultRedirectpath)
|
||||
: base()
|
||||
{
|
||||
if (kernel == null)
|
||||
{
|
||||
throw new ArgumentNullException("kernel");
|
||||
}
|
||||
if (protobufSerializer == null)
|
||||
{
|
||||
throw new ArgumentNullException("protobufSerializer");
|
||||
}
|
||||
if (logger == null)
|
||||
{
|
||||
throw new ArgumentNullException("logger");
|
||||
|
@ -112,6 +124,7 @@ namespace MediaBrowser.Networking.Web
|
|||
|
||||
ServerName = serverName;
|
||||
DefaultRedirectPath = defaultRedirectpath;
|
||||
ProtobufSerializer = protobufSerializer;
|
||||
_logger = logger;
|
||||
ApplicationHost = applicationHost;
|
||||
|
||||
|
@ -121,7 +134,7 @@ namespace MediaBrowser.Networking.Web
|
|||
Kernel = kernel;
|
||||
|
||||
EndpointHost.ConfigureHost(this, ServerName, CreateServiceManager());
|
||||
ContentTypeFilters.Register(ContentType.ProtoBuf, (reqCtx, res, stream) => Kernel.ProtobufSerializer.SerializeToStream(res, stream), (type, stream) => Kernel.ProtobufSerializer.DeserializeFromStream(stream, type));
|
||||
ContentTypeFilters.Register(ContentType.ProtoBuf, (reqCtx, res, stream) => ProtobufSerializer.SerializeToStream(res, stream), (type, stream) => ProtobufSerializer.DeserializeFromStream(stream, type));
|
||||
|
||||
Init();
|
||||
}
|
||||
|
@ -132,6 +145,10 @@ namespace MediaBrowser.Networking.Web
|
|||
/// <param name="container">The container.</param>
|
||||
public override void Configure(Container container)
|
||||
{
|
||||
JsConfig.DateHandler = JsonDateHandler.ISO8601;
|
||||
JsConfig.ExcludeTypeInfo = true;
|
||||
JsConfig.IncludeNullValues = false;
|
||||
|
||||
SetConfig(new EndpointHostConfig
|
||||
{
|
||||
DefaultRedirectPath = DefaultRedirectPath,
|
||||
|
|
|
@ -1,7 +1,5 @@
|
|||
using MediaBrowser.Common.Serialization;
|
||||
using MediaBrowser.Model.Logging;
|
||||
using MediaBrowser.Model.Logging;
|
||||
using System;
|
||||
using System.IO;
|
||||
using System.Net.WebSockets;
|
||||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
|
@ -79,19 +77,7 @@ namespace MediaBrowser.Common.Net
|
|||
|
||||
if (OnReceiveDelegate != null)
|
||||
{
|
||||
using (var memoryStream = new MemoryStream(bytes))
|
||||
{
|
||||
try
|
||||
{
|
||||
var messageResult = JsonSerializer.DeserializeFromStream<WebSocketMessageInfo>(memoryStream);
|
||||
|
||||
OnReceiveDelegate(messageResult);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
_logger.ErrorException("Error processing web socket message", ex);
|
||||
}
|
||||
}
|
||||
OnReceiveDelegate(bytes);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -154,6 +140,6 @@ namespace MediaBrowser.Common.Net
|
|||
/// Gets or sets the receive action.
|
||||
/// </summary>
|
||||
/// <value>The receive action.</value>
|
||||
public Action<WebSocketMessageInfo> OnReceiveDelegate { get; set; }
|
||||
public Action<byte[]> OnReceiveDelegate { get; set; }
|
||||
}
|
||||
}
|
|
@ -0,0 +1,28 @@
|
|||
using MediaBrowser.Common.Kernel;
|
||||
using MediaBrowser.Common.Net;
|
||||
using MediaBrowser.Model.Logging;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
|
||||
namespace MediaBrowser.Networking.Web
|
||||
{
|
||||
/// <summary>
|
||||
/// Class ServerFactory
|
||||
/// </summary>
|
||||
public static class ServerFactory
|
||||
{
|
||||
/// <summary>
|
||||
/// Creates the server.
|
||||
/// </summary>
|
||||
/// <param name="applicationHost">The application host.</param>
|
||||
/// <param name="kernel">The kernel.</param>
|
||||
/// <param name="protobufSerializer">The protobuf serializer.</param>
|
||||
/// <param name="logger">The logger.</param>
|
||||
/// <param name="serverName">Name of the server.</param>
|
||||
/// <param name="defaultRedirectpath">The default redirectpath.</param>
|
||||
/// <returns>IHttpServer.</returns>
|
||||
public static IHttpServer CreateServer(IApplicationHost applicationHost, IKernel kernel, IProtobufSerializer protobufSerializer, ILogger logger, string serverName, string defaultRedirectpath)
|
||||
{
|
||||
return new HttpServer(applicationHost, kernel, protobufSerializer, logger, serverName, defaultRedirectpath);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,9 +1,9 @@
|
|||
using Alchemy.Classes;
|
||||
using MediaBrowser.Common.Net;
|
||||
using MediaBrowser.Common.Serialization;
|
||||
using MediaBrowser.Model.Logging;
|
||||
using System;
|
||||
using System.Net.WebSockets;
|
||||
using System.Text;
|
||||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
|
@ -83,9 +83,9 @@ namespace MediaBrowser.Networking.WebSocket
|
|||
{
|
||||
try
|
||||
{
|
||||
var messageResult = JsonSerializer.DeserializeFromString<WebSocketMessageInfo>(json);
|
||||
var bytes = Encoding.UTF8.GetBytes(json);
|
||||
|
||||
OnReceiveDelegate(messageResult);
|
||||
OnReceiveDelegate(bytes);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
|
@ -128,6 +128,6 @@ namespace MediaBrowser.Networking.WebSocket
|
|||
/// Gets or sets the receive action.
|
||||
/// </summary>
|
||||
/// <value>The receive action.</value>
|
||||
public Action<WebSocketMessageInfo> OnReceiveDelegate { get; set; }
|
||||
public Action<byte[]> OnReceiveDelegate { get; set; }
|
||||
}
|
||||
}
|
||||
|
|
|
@ -4,11 +4,11 @@
|
|||
<PropertyGroup>
|
||||
<Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
|
||||
<Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform>
|
||||
<ProjectGuid>{8649ED6B-8504-4D00-BFA5-B8C73CC744DB}</ProjectGuid>
|
||||
<ProjectGuid>{2E781478-814D-4A48-9D80-BFF206441A65}</ProjectGuid>
|
||||
<OutputType>Library</OutputType>
|
||||
<AppDesignerFolder>Properties</AppDesignerFolder>
|
||||
<RootNamespace>MediaBrowser.Server.Sqlite</RootNamespace>
|
||||
<AssemblyName>MediaBrowser.Server.Sqlite</AssemblyName>
|
||||
<RootNamespace>MediaBrowser.Server.Implementations</RootNamespace>
|
||||
<AssemblyName>MediaBrowser.Server.Implementations</AssemblyName>
|
||||
<TargetFrameworkVersion>v4.5</TargetFrameworkVersion>
|
||||
<FileAlignment>512</FileAlignment>
|
||||
<SolutionDir Condition="$(SolutionDir) == '' Or $(SolutionDir) == '*Undefined*'">..\</SolutionDir>
|
||||
|
@ -31,9 +31,6 @@
|
|||
<ErrorReport>prompt</ErrorReport>
|
||||
<WarningLevel>4</WarningLevel>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup>
|
||||
<RunPostBuildEvent>Always</RunPostBuildEvent>
|
||||
</PropertyGroup>
|
||||
<ItemGroup>
|
||||
<Reference Include="System" />
|
||||
<Reference Include="System.Core" />
|
||||
|
@ -43,33 +40,31 @@
|
|||
<Reference Include="System.Data.SQLite.Linq">
|
||||
<HintPath>..\packages\System.Data.SQLite.1.0.84.0\lib\net45\System.Data.SQLite.Linq.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="System.Xml.Linq" />
|
||||
<Reference Include="System.Data.DataSetExtensions" />
|
||||
<Reference Include="Microsoft.CSharp" />
|
||||
<Reference Include="System.Data" />
|
||||
<Reference Include="System.Xml" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Compile Include="..\SharedVersion.cs">
|
||||
<Link>Properties\SharedVersion.cs</Link>
|
||||
</Compile>
|
||||
<Compile Include="Properties\AssemblyInfo.cs" />
|
||||
<Compile Include="SQLiteDisplayPreferencesRepository.cs" />
|
||||
<Compile Include="SQLiteExtensions.cs" />
|
||||
<Compile Include="SQLiteItemRepository.cs" />
|
||||
<Compile Include="SQLiteRepository.cs" />
|
||||
<Compile Include="SQLiteUserDataRepository.cs" />
|
||||
<Compile Include="SQLiteUserRepository.cs" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Content Include="x64\SQLite.Interop.dll">
|
||||
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
|
||||
</Content>
|
||||
<Content Include="x86\SQLite.Interop.dll">
|
||||
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
|
||||
</Content>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="packages.config" />
|
||||
<Compile Include="ServerApplicationPaths.cs" />
|
||||
<Compile Include="Sqlite\SQLiteDisplayPreferencesRepository.cs" />
|
||||
<Compile Include="Sqlite\SQLiteExtensions.cs" />
|
||||
<Compile Include="Sqlite\SQLiteItemRepository.cs" />
|
||||
<Compile Include="Sqlite\SQLiteRepository.cs" />
|
||||
<Compile Include="Sqlite\SQLiteUserDataRepository.cs" />
|
||||
<Compile Include="Sqlite\SQLiteUserRepository.cs" />
|
||||
<Compile Include="WorldWeatherOnline\WeatherProvider.cs" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\MediaBrowser.Common.Implementations\MediaBrowser.Common.Implementations.csproj">
|
||||
<Project>{c4d2573a-3fd3-441f-81af-174ac4cd4e1d}</Project>
|
||||
<Name>MediaBrowser.Common.Implementations</Name>
|
||||
</ProjectReference>
|
||||
<ProjectReference Include="..\MediaBrowser.Common\MediaBrowser.Common.csproj">
|
||||
<Project>{9142eefa-7570-41e1-bfcc-468bb571af2f}</Project>
|
||||
<Name>MediaBrowser.Common</Name>
|
||||
|
@ -83,11 +78,20 @@
|
|||
<Name>MediaBrowser.Model</Name>
|
||||
</ProjectReference>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Content Include="x64\SQLite.Interop.dll">
|
||||
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
|
||||
</Content>
|
||||
<Content Include="x86\SQLite.Interop.dll">
|
||||
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
|
||||
</Content>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="packages.config" />
|
||||
</ItemGroup>
|
||||
<ItemGroup />
|
||||
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
|
||||
<Import Project="$(SolutionDir)\.nuget\nuget.targets" />
|
||||
<PropertyGroup>
|
||||
<PostBuildEvent>xcopy "$(TargetPath)" "$(SolutionDir)\MediaBrowser.ServerApplication\CorePlugins\" /y</PostBuildEvent>
|
||||
</PropertyGroup>
|
||||
<!-- To modify your build process, add your task inside one of the targets below and uncomment it.
|
||||
Other similar extension points exist, see Microsoft.Common.targets.
|
||||
<Target Name="BeforeBuild">
|
|
@ -1,15 +1,14 @@
|
|||
using System.Reflection;
|
||||
using System.Runtime.CompilerServices;
|
||||
using System.Runtime.InteropServices;
|
||||
|
||||
// General Information about an assembly is controlled through the following
|
||||
// set of attributes. Change these attribute values to modify the information
|
||||
// associated with an assembly.
|
||||
[assembly: AssemblyTitle("MediaBrowser.Server.WorldWeatherOnline")]
|
||||
[assembly: AssemblyTitle("MediaBrowser.Server.Implementations")]
|
||||
[assembly: AssemblyDescription("")]
|
||||
[assembly: AssemblyConfiguration("")]
|
||||
[assembly: AssemblyCompany("")]
|
||||
[assembly: AssemblyProduct("MediaBrowser.Server.WorldWeatherOnline")]
|
||||
[assembly: AssemblyProduct("MediaBrowser.Server.Implementations")]
|
||||
[assembly: AssemblyCopyright("Copyright © 2013")]
|
||||
[assembly: AssemblyTrademark("")]
|
||||
[assembly: AssemblyCulture("")]
|
||||
|
@ -20,7 +19,7 @@ using System.Runtime.InteropServices;
|
|||
[assembly: ComVisible(false)]
|
||||
|
||||
// The following GUID is for the ID of the typelib if this project is exposed to COM
|
||||
[assembly: Guid("c7b294dc-b3fd-4925-9ac3-8dd16803200c")]
|
||||
[assembly: Guid("0537cdd3-a069-4d86-9318-d46d8b119903")]
|
||||
|
||||
// Version information for an assembly consists of the following four values:
|
||||
//
|
||||
|
@ -28,4 +27,4 @@ using System.Runtime.InteropServices;
|
|||
// Minor Version
|
||||
// Build Number
|
||||
// Revision
|
||||
//
|
||||
//
|
|
@ -1,12 +1,13 @@
|
|||
using MediaBrowser.Common.Kernel;
|
||||
using MediaBrowser.Common.Implementations;
|
||||
using MediaBrowser.Controller;
|
||||
using System.IO;
|
||||
|
||||
namespace MediaBrowser.Controller
|
||||
namespace MediaBrowser.Server.Implementations
|
||||
{
|
||||
/// <summary>
|
||||
/// Extends BaseApplicationPaths to add paths that are only applicable on the server
|
||||
/// </summary>
|
||||
public class ServerApplicationPaths : BaseApplicationPaths
|
||||
public class ServerApplicationPaths : BaseApplicationPaths, IServerApplicationPaths
|
||||
{
|
||||
/// <summary>
|
||||
/// The _root folder path
|
|
@ -1,8 +1,9 @@
|
|||
using MediaBrowser.Controller;
|
||||
using MediaBrowser.Common.Kernel;
|
||||
using MediaBrowser.Controller.Entities;
|
||||
using MediaBrowser.Controller.Persistence;
|
||||
using MediaBrowser.Model.Entities;
|
||||
using MediaBrowser.Model.Logging;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Data;
|
||||
|
@ -10,7 +11,7 @@ using System.IO;
|
|||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace MediaBrowser.Server.Sqlite
|
||||
namespace MediaBrowser.Server.Implementations.Sqlite
|
||||
{
|
||||
/// <summary>
|
||||
/// Class SQLiteDisplayPreferencesRepository
|
||||
|
@ -34,13 +35,37 @@ namespace MediaBrowser.Server.Sqlite
|
|||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// The _protobuf serializer
|
||||
/// </summary>
|
||||
private readonly IProtobufSerializer _protobufSerializer;
|
||||
|
||||
/// <summary>
|
||||
/// The _app paths
|
||||
/// </summary>
|
||||
private readonly IApplicationPaths _appPaths;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="SQLiteUserDataRepository" /> class.
|
||||
/// </summary>
|
||||
/// <param name="appPaths">The app paths.</param>
|
||||
/// <param name="protobufSerializer">The protobuf serializer.</param>
|
||||
/// <param name="logger">The logger.</param>
|
||||
public SQLiteDisplayPreferencesRepository(ILogger logger)
|
||||
/// <exception cref="System.ArgumentNullException">protobufSerializer</exception>
|
||||
public SQLiteDisplayPreferencesRepository(IApplicationPaths appPaths, IProtobufSerializer protobufSerializer, ILogger logger)
|
||||
: base(logger)
|
||||
{
|
||||
if (protobufSerializer == null)
|
||||
{
|
||||
throw new ArgumentNullException("protobufSerializer");
|
||||
}
|
||||
if (appPaths == null)
|
||||
{
|
||||
throw new ArgumentNullException("appPaths");
|
||||
}
|
||||
|
||||
_protobufSerializer = protobufSerializer;
|
||||
_appPaths = appPaths;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
@ -49,7 +74,7 @@ namespace MediaBrowser.Server.Sqlite
|
|||
/// <returns>Task.</returns>
|
||||
public async Task Initialize()
|
||||
{
|
||||
var dbFile = Path.Combine(Kernel.Instance.ApplicationPaths.DataPath, "displaypreferences.db");
|
||||
var dbFile = Path.Combine(_appPaths.DataPath, "displaypreferences.db");
|
||||
|
||||
await ConnectToDB(dbFile).ConfigureAwait(false);
|
||||
|
||||
|
@ -104,7 +129,7 @@ namespace MediaBrowser.Server.Sqlite
|
|||
cmd.AddParam("@1", item.DisplayPrefsId);
|
||||
cmd.AddParam("@2", data.UserId);
|
||||
|
||||
cmd.AddParam("@3", Kernel.Instance.ProtobufSerializer.SerializeToBytes(data));
|
||||
cmd.AddParam("@3", _protobufSerializer.SerializeToBytes(data));
|
||||
|
||||
QueueCommand(cmd);
|
||||
}
|
||||
|
@ -136,7 +161,7 @@ namespace MediaBrowser.Server.Sqlite
|
|||
{
|
||||
using (var stream = GetStream(reader, 0))
|
||||
{
|
||||
var data = Kernel.Instance.ProtobufSerializer.DeserializeFromStream<DisplayPreferences>(stream);
|
||||
var data = _protobufSerializer.DeserializeFromStream<DisplayPreferences>(stream);
|
||||
if (data != null)
|
||||
{
|
||||
yield return data;
|
|
@ -2,7 +2,7 @@
|
|||
using System.Data;
|
||||
using System.Data.SQLite;
|
||||
|
||||
namespace MediaBrowser.Server.Sqlite
|
||||
namespace MediaBrowser.Server.Implementations.Sqlite
|
||||
{
|
||||
/// <summary>
|
||||
/// Class SQLiteExtensions
|
|
@ -1,8 +1,8 @@
|
|||
using MediaBrowser.Common.Serialization;
|
||||
using MediaBrowser.Controller;
|
||||
using MediaBrowser.Common.Kernel;
|
||||
using MediaBrowser.Controller.Entities;
|
||||
using MediaBrowser.Controller.Persistence;
|
||||
using MediaBrowser.Model.Logging;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Data;
|
||||
|
@ -10,7 +10,7 @@ using System.IO;
|
|||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace MediaBrowser.Server.Sqlite
|
||||
namespace MediaBrowser.Server.Implementations.Sqlite
|
||||
{
|
||||
/// <summary>
|
||||
/// Class SQLiteItemRepository
|
||||
|
@ -39,13 +39,38 @@ namespace MediaBrowser.Server.Sqlite
|
|||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the json serializer.
|
||||
/// </summary>
|
||||
/// <value>The json serializer.</value>
|
||||
private readonly IJsonSerializer _jsonSerializer;
|
||||
|
||||
/// <summary>
|
||||
/// The _app paths
|
||||
/// </summary>
|
||||
private readonly IApplicationPaths _appPaths;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="SQLiteUserDataRepository" /> class.
|
||||
/// </summary>
|
||||
/// <param name="appPaths">The app paths.</param>
|
||||
/// <param name="jsonSerializer">The json serializer.</param>
|
||||
/// <param name="logger">The logger.</param>
|
||||
public SQLiteItemRepository(ILogger logger)
|
||||
/// <exception cref="System.ArgumentNullException">appPaths</exception>
|
||||
public SQLiteItemRepository(IApplicationPaths appPaths, IJsonSerializer jsonSerializer, ILogger logger)
|
||||
: base(logger)
|
||||
{
|
||||
if (appPaths == null)
|
||||
{
|
||||
throw new ArgumentNullException("appPaths");
|
||||
}
|
||||
if (jsonSerializer == null)
|
||||
{
|
||||
throw new ArgumentNullException("jsonSerializer");
|
||||
}
|
||||
|
||||
_appPaths = appPaths;
|
||||
_jsonSerializer = jsonSerializer;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
@ -54,7 +79,7 @@ namespace MediaBrowser.Server.Sqlite
|
|||
/// <returns>Task.</returns>
|
||||
public async Task Initialize()
|
||||
{
|
||||
var dbFile = Path.Combine(Kernel.Instance.ApplicationPaths.DataPath, "library.db");
|
||||
var dbFile = Path.Combine(_appPaths.DataPath, "library.db");
|
||||
|
||||
await ConnectToDB(dbFile).ConfigureAwait(false);
|
||||
|
||||
|
@ -111,7 +136,7 @@ namespace MediaBrowser.Server.Sqlite
|
|||
|
||||
return Task.Run(() =>
|
||||
{
|
||||
var serialized = JsonSerializer.SerializeToBytes(item);
|
||||
var serialized = _jsonSerializer.SerializeToBytes(item);
|
||||
|
||||
cancellationToken.ThrowIfCancellationRequested();
|
||||
|
||||
|
@ -173,7 +198,7 @@ namespace MediaBrowser.Server.Sqlite
|
|||
return null;
|
||||
}
|
||||
|
||||
var item = JsonSerializer.DeserializeFromStream(stream, itemType);
|
||||
var item = _jsonSerializer.DeserializeFromStream(stream, itemType);
|
||||
return item as BaseItem;
|
||||
}
|
||||
}
|
||||
|
@ -213,7 +238,7 @@ namespace MediaBrowser.Server.Sqlite
|
|||
Logger.Error("Cannot find type {0}. Probably belongs to plug-in that is no longer loaded.", type);
|
||||
continue;
|
||||
}
|
||||
var item = JsonSerializer.DeserializeFromStream(stream, itemType) as BaseItem;
|
||||
var item = _jsonSerializer.DeserializeFromStream(stream, itemType) as BaseItem;
|
||||
if (item != null)
|
||||
{
|
||||
item.Parent = parent;
|
|
@ -8,7 +8,7 @@ using System.IO;
|
|||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace MediaBrowser.Server.Sqlite
|
||||
namespace MediaBrowser.Server.Implementations.Sqlite
|
||||
{
|
||||
/// <summary>
|
||||
/// Class SqliteRepository
|
|
@ -1,7 +1,8 @@
|
|||
using MediaBrowser.Controller;
|
||||
using MediaBrowser.Common.Kernel;
|
||||
using MediaBrowser.Controller.Entities;
|
||||
using MediaBrowser.Controller.Persistence;
|
||||
using MediaBrowser.Model.Logging;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Data;
|
||||
|
@ -9,7 +10,7 @@ using System.IO;
|
|||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace MediaBrowser.Server.Sqlite
|
||||
namespace MediaBrowser.Server.Implementations.Sqlite
|
||||
{
|
||||
/// <summary>
|
||||
/// Class SQLiteUserDataRepository
|
||||
|
@ -33,13 +34,37 @@ namespace MediaBrowser.Server.Sqlite
|
|||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// The _protobuf serializer
|
||||
/// </summary>
|
||||
private readonly IProtobufSerializer _protobufSerializer;
|
||||
|
||||
/// <summary>
|
||||
/// The _app paths
|
||||
/// </summary>
|
||||
private readonly IApplicationPaths _appPaths;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="SQLiteUserDataRepository" /> class.
|
||||
/// </summary>
|
||||
/// <param name="appPaths">The app paths.</param>
|
||||
/// <param name="protobufSerializer">The protobuf serializer.</param>
|
||||
/// <param name="logger">The logger.</param>
|
||||
public SQLiteUserDataRepository(ILogger logger)
|
||||
/// <exception cref="System.ArgumentNullException">protobufSerializer</exception>
|
||||
public SQLiteUserDataRepository(IApplicationPaths appPaths, IProtobufSerializer protobufSerializer, ILogger logger)
|
||||
: base(logger)
|
||||
{
|
||||
if (protobufSerializer == null)
|
||||
{
|
||||
throw new ArgumentNullException("protobufSerializer");
|
||||
}
|
||||
if (appPaths == null)
|
||||
{
|
||||
throw new ArgumentNullException("appPaths");
|
||||
}
|
||||
|
||||
_protobufSerializer = protobufSerializer;
|
||||
_appPaths = appPaths;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
@ -48,7 +73,7 @@ namespace MediaBrowser.Server.Sqlite
|
|||
/// <returns>Task.</returns>
|
||||
public async Task Initialize()
|
||||
{
|
||||
var dbFile = Path.Combine(Kernel.Instance.ApplicationPaths.DataPath, "userdata.db");
|
||||
var dbFile = Path.Combine(_appPaths.DataPath, "userdata.db");
|
||||
|
||||
await ConnectToDB(dbFile).ConfigureAwait(false);
|
||||
|
||||
|
@ -103,7 +128,7 @@ namespace MediaBrowser.Server.Sqlite
|
|||
cmd.AddParam("@1", item.UserDataId);
|
||||
cmd.AddParam("@2", data.UserId);
|
||||
|
||||
cmd.AddParam("@3", Kernel.Instance.ProtobufSerializer.SerializeToBytes(data));
|
||||
cmd.AddParam("@3", _protobufSerializer.SerializeToBytes(data));
|
||||
|
||||
QueueCommand(cmd);
|
||||
}
|
||||
|
@ -135,7 +160,7 @@ namespace MediaBrowser.Server.Sqlite
|
|||
{
|
||||
using (var stream = GetStream(reader, 0))
|
||||
{
|
||||
var data = Kernel.Instance.ProtobufSerializer.DeserializeFromStream<UserItemData>(stream);
|
||||
var data = _protobufSerializer.DeserializeFromStream<UserItemData>(stream);
|
||||
if (data != null)
|
||||
{
|
||||
yield return data;
|
|
@ -1,16 +1,16 @@
|
|||
using MediaBrowser.Common.Serialization;
|
||||
using MediaBrowser.Controller;
|
||||
using MediaBrowser.Common.Kernel;
|
||||
using MediaBrowser.Controller.Entities;
|
||||
using MediaBrowser.Controller.Persistence;
|
||||
using MediaBrowser.Model.Logging;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Data;
|
||||
using System.IO;
|
||||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
using MediaBrowser.Model.Logging;
|
||||
|
||||
namespace MediaBrowser.Server.Sqlite
|
||||
namespace MediaBrowser.Server.Implementations.Sqlite
|
||||
{
|
||||
/// <summary>
|
||||
/// Class SQLiteUserRepository
|
||||
|
@ -34,13 +34,38 @@ namespace MediaBrowser.Server.Sqlite
|
|||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the json serializer.
|
||||
/// </summary>
|
||||
/// <value>The json serializer.</value>
|
||||
private readonly IJsonSerializer _jsonSerializer;
|
||||
|
||||
/// <summary>
|
||||
/// The _app paths
|
||||
/// </summary>
|
||||
private readonly IApplicationPaths _appPaths;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="SQLiteUserDataRepository" /> class.
|
||||
/// </summary>
|
||||
/// <param name="appPaths">The app paths.</param>
|
||||
/// <param name="jsonSerializer">The json serializer.</param>
|
||||
/// <param name="logger">The logger.</param>
|
||||
public SQLiteUserRepository(ILogger logger)
|
||||
/// <exception cref="System.ArgumentNullException">appPaths</exception>
|
||||
public SQLiteUserRepository(IApplicationPaths appPaths, IJsonSerializer jsonSerializer, ILogger logger)
|
||||
: base(logger)
|
||||
{
|
||||
if (appPaths == null)
|
||||
{
|
||||
throw new ArgumentNullException("appPaths");
|
||||
}
|
||||
if (jsonSerializer == null)
|
||||
{
|
||||
throw new ArgumentNullException("jsonSerializer");
|
||||
}
|
||||
|
||||
_appPaths = appPaths;
|
||||
_jsonSerializer = jsonSerializer;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
@ -49,7 +74,7 @@ namespace MediaBrowser.Server.Sqlite
|
|||
/// <returns>Task.</returns>
|
||||
public async Task Initialize()
|
||||
{
|
||||
var dbFile = Path.Combine(Kernel.Instance.ApplicationPaths.DataPath, "users.db");
|
||||
var dbFile = Path.Combine(_appPaths.DataPath, "users.db");
|
||||
|
||||
await ConnectToDB(dbFile).ConfigureAwait(false);
|
||||
|
||||
|
@ -88,7 +113,7 @@ namespace MediaBrowser.Server.Sqlite
|
|||
{
|
||||
cancellationToken.ThrowIfCancellationRequested();
|
||||
|
||||
var serialized = JsonSerializer.SerializeToBytes(user);
|
||||
var serialized = _jsonSerializer.SerializeToBytes(user);
|
||||
|
||||
cancellationToken.ThrowIfCancellationRequested();
|
||||
|
||||
|
@ -115,7 +140,7 @@ namespace MediaBrowser.Server.Sqlite
|
|||
{
|
||||
using (var stream = GetStream(reader, 0))
|
||||
{
|
||||
var user = JsonSerializer.DeserializeFromStream<User>(stream);
|
||||
var user = _jsonSerializer.DeserializeFromStream<User>(stream);
|
||||
yield return user;
|
||||
}
|
||||
}
|
|
@ -1,14 +1,14 @@
|
|||
using MediaBrowser.Common.Serialization;
|
||||
using MediaBrowser.Controller;
|
||||
using MediaBrowser.Controller;
|
||||
using MediaBrowser.Controller.Weather;
|
||||
using MediaBrowser.Model.Logging;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
using MediaBrowser.Model.Weather;
|
||||
using System;
|
||||
using System.Linq;
|
||||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace MediaBrowser.Server.WorldWeatherOnline
|
||||
namespace MediaBrowser.Server.Implementations.WorldWeatherOnline
|
||||
{
|
||||
/// <summary>
|
||||
/// Based on http://www.worldweatheronline.com/free-weather-feed.aspx
|
||||
|
@ -22,18 +22,31 @@ namespace MediaBrowser.Server.WorldWeatherOnline
|
|||
/// <value>The logger.</value>
|
||||
private ILogger Logger { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets the json serializer.
|
||||
/// </summary>
|
||||
/// <value>The json serializer.</value>
|
||||
protected IJsonSerializer JsonSerializer { get; private set; }
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="WeatherProvider" /> class.
|
||||
/// </summary>
|
||||
/// <param name="jsonSerializer">The json serializer.</param>
|
||||
/// <param name="logger">The logger.</param>
|
||||
/// <exception cref="System.ArgumentNullException">logger</exception>
|
||||
public WeatherProvider(ILogger logger)
|
||||
public WeatherProvider(IJsonSerializer jsonSerializer, ILogger logger)
|
||||
{
|
||||
if (logger == null)
|
||||
{
|
||||
throw new ArgumentNullException("logger");
|
||||
}
|
||||
|
||||
if (jsonSerializer == null)
|
||||
{
|
||||
throw new ArgumentNullException("jsonSerializer");
|
||||
}
|
||||
|
||||
JsonSerializer = jsonSerializer;
|
||||
Logger = logger;
|
||||
}
|
||||
|
|
@ -1,26 +1,13 @@
|
|||
using BDInfo;
|
||||
using MediaBrowser.ClickOnce;
|
||||
using MediaBrowser.Common.IO;
|
||||
using MediaBrowser.ClickOnce;
|
||||
using MediaBrowser.Common.Implementations.Serialization;
|
||||
using MediaBrowser.Common.Kernel;
|
||||
using MediaBrowser.Common.Net;
|
||||
using MediaBrowser.Controller;
|
||||
using MediaBrowser.IsoMounter;
|
||||
using MediaBrowser.Logging.Nlog;
|
||||
using MediaBrowser.Model.IO;
|
||||
using MediaBrowser.Model.Logging;
|
||||
using MediaBrowser.Model.MediaInfo;
|
||||
using MediaBrowser.Model.Updates;
|
||||
using MediaBrowser.Networking.Management;
|
||||
using MediaBrowser.Networking.Udp;
|
||||
using MediaBrowser.Networking.Web;
|
||||
using MediaBrowser.Networking.WebSocket;
|
||||
using MediaBrowser.Server.Uninstall;
|
||||
using MediaBrowser.ServerApplication.Implementations;
|
||||
using Microsoft.Win32;
|
||||
using SimpleInjector;
|
||||
using System;
|
||||
using System.Diagnostics;
|
||||
using System.IO;
|
||||
using System.Linq;
|
||||
using System.Net.Cache;
|
||||
using System.Threading;
|
||||
|
@ -35,7 +22,7 @@ namespace MediaBrowser.ServerApplication
|
|||
/// <summary>
|
||||
/// Interaction logic for App.xaml
|
||||
/// </summary>
|
||||
public partial class App : Application, IApplicationHost
|
||||
public partial class App : Application
|
||||
{
|
||||
/// <summary>
|
||||
/// Defines the entry point of the application.
|
||||
|
@ -78,16 +65,11 @@ namespace MediaBrowser.ServerApplication
|
|||
protected ILogger Logger { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the log file path.
|
||||
/// Gets or sets the composition root.
|
||||
/// </summary>
|
||||
/// <value>The log file path.</value>
|
||||
public string LogFilePath { get; private set; }
|
||||
|
||||
/// <summary>
|
||||
/// The container
|
||||
/// </summary>
|
||||
private Container _container = new Container();
|
||||
|
||||
/// <value>The composition root.</value>
|
||||
protected ApplicationHost CompositionRoot { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="App" /> class.
|
||||
/// </summary>
|
||||
|
@ -135,12 +117,6 @@ namespace MediaBrowser.ServerApplication
|
|||
get { return "MediaBrowser.Server.Uninstall.exe"; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the iso manager.
|
||||
/// </summary>
|
||||
/// <value>The iso manager.</value>
|
||||
private IIsoManager IsoManager { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets a value indicating whether [last run at startup value].
|
||||
/// </summary>
|
||||
|
@ -198,13 +174,13 @@ namespace MediaBrowser.ServerApplication
|
|||
/// </summary>
|
||||
protected async void LoadKernel()
|
||||
{
|
||||
Kernel = new Kernel(this, Logger);
|
||||
CompositionRoot = new ApplicationHost(Logger);
|
||||
|
||||
RegisterResources();
|
||||
Kernel = CompositionRoot.Kernel;
|
||||
|
||||
try
|
||||
{
|
||||
new MainWindow(Logger).Show();
|
||||
new MainWindow(new JsonSerializer(), Logger).Show();
|
||||
|
||||
var now = DateTime.UtcNow;
|
||||
|
||||
|
@ -281,6 +257,7 @@ namespace MediaBrowser.ServerApplication
|
|||
base.OnExit(e);
|
||||
|
||||
Kernel.Dispose();
|
||||
CompositionRoot.Dispose();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
@ -391,17 +368,6 @@ namespace MediaBrowser.ServerApplication
|
|||
Dispatcher.Invoke(Shutdown);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Reloads the logger.
|
||||
/// </summary>
|
||||
/// <exception cref="System.NotImplementedException"></exception>
|
||||
public void ReloadLogger()
|
||||
{
|
||||
LogFilePath = Path.Combine(Kernel.ApplicationPaths.LogDirectoryPath, "Server-" + DateTime.Now.Ticks + ".log");
|
||||
|
||||
NlogManager.AddFileTarget(LogFilePath, Kernel.Configuration.EnableDebugLevelLogging);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the image.
|
||||
/// </summary>
|
||||
|
@ -477,143 +443,5 @@ namespace MediaBrowser.ServerApplication
|
|||
RenderOptions.SetBitmapScalingMode(bitmap, BitmapScalingMode.Fant);
|
||||
return bitmap;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets a value indicating whether this instance can self update.
|
||||
/// </summary>
|
||||
/// <value><c>true</c> if this instance can self update; otherwise, <c>false</c>.</value>
|
||||
public bool CanSelfUpdate
|
||||
{
|
||||
get { return ClickOnceHelper.IsNetworkDeployed; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Checks for update.
|
||||
/// </summary>
|
||||
/// <param name="cancellationToken">The cancellation token.</param>
|
||||
/// <param name="progress">The progress.</param>
|
||||
/// <returns>Task{CheckForUpdateResult}.</returns>
|
||||
public Task<CheckForUpdateResult> CheckForApplicationUpdate(CancellationToken cancellationToken, IProgress<double> progress)
|
||||
{
|
||||
return new ApplicationUpdateCheck().CheckForApplicationUpdate(cancellationToken, progress);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Updates the application.
|
||||
/// </summary>
|
||||
/// <param name="cancellationToken">The cancellation token.</param>
|
||||
/// <param name="progress">The progress.</param>
|
||||
/// <returns>Task.</returns>
|
||||
public Task UpdateApplication(CancellationToken cancellationToken, IProgress<double> progress)
|
||||
{
|
||||
return new ApplicationUpdater().UpdateApplication(cancellationToken, progress);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Registers resources that classes will depend on
|
||||
/// </summary>
|
||||
private void RegisterResources()
|
||||
{
|
||||
RegisterSingleInstance<IApplicationHost>(this);
|
||||
RegisterSingleInstance(Logger);
|
||||
|
||||
IsoManager = new PismoIsoManager(Logger);
|
||||
|
||||
RegisterSingleInstance(IsoManager);
|
||||
RegisterSingleInstance<IBlurayExaminer>(() => new BdInfoExaminer());
|
||||
RegisterSingleInstance<INetworkManager>(() => new NetworkManager());
|
||||
RegisterSingleInstance<IZipClient>(() => new DotNetZipClient());
|
||||
RegisterSingleInstance<IWebSocketServer>(() => new AlchemyServer(Logger));
|
||||
Register(typeof(IUdpServer), typeof(UdpServer));
|
||||
RegisterSingleInstance<IHttpServer>(() => new HttpServer(this, Kernel, Logger, "Media Browser", "index.html"));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Creates an instance of type and resolves all constructor dependancies
|
||||
/// </summary>
|
||||
/// <param name="type">The type.</param>
|
||||
/// <returns>System.Object.</returns>
|
||||
public object CreateInstance(Type type)
|
||||
{
|
||||
try
|
||||
{
|
||||
return _container.GetInstance(type);
|
||||
}
|
||||
catch
|
||||
{
|
||||
Logger.Error("Error creating {0}", type.Name);
|
||||
|
||||
throw;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Registers the specified obj.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <param name="obj">The obj.</param>
|
||||
public void RegisterSingleInstance<T>(T obj)
|
||||
where T : class
|
||||
{
|
||||
_container.RegisterSingle(obj);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Registers the specified func.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <param name="func">The func.</param>
|
||||
public void Register<T>(Func<T> func)
|
||||
where T : class
|
||||
{
|
||||
_container.Register(func);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Registers the single instance.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <param name="func">The func.</param>
|
||||
public void RegisterSingleInstance<T>(Func<T> func)
|
||||
where T : class
|
||||
{
|
||||
_container.RegisterSingle(func);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Resolves this instance.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <returns>``0.</returns>
|
||||
public T Resolve<T>()
|
||||
{
|
||||
return (T)_container.GetRegistration(typeof(T), true).GetInstance();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Resolves this instance.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <returns>``0.</returns>
|
||||
public T TryResolve<T>()
|
||||
{
|
||||
var result = _container.GetRegistration(typeof(T), false);
|
||||
|
||||
if (result == null)
|
||||
{
|
||||
return default(T);
|
||||
}
|
||||
return (T)result.GetInstance();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Registers the specified service type.
|
||||
/// </summary>
|
||||
/// <param name="serviceType">Type of the service.</param>
|
||||
/// <param name="implementation">Type of the concrete.</param>
|
||||
public void Register(Type serviceType, Type implementation)
|
||||
{
|
||||
_container.Register(serviceType, implementation);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,498 @@
|
|||
using BDInfo;
|
||||
using MediaBrowser.ClickOnce;
|
||||
using MediaBrowser.Common.Implementations.ScheduledTasks;
|
||||
using MediaBrowser.Common.Implementations.Serialization;
|
||||
using MediaBrowser.Common.IO;
|
||||
using MediaBrowser.Common.Kernel;
|
||||
using MediaBrowser.Common.Net;
|
||||
using MediaBrowser.Common.ScheduledTasks;
|
||||
using MediaBrowser.Controller;
|
||||
using MediaBrowser.IsoMounter;
|
||||
using MediaBrowser.Logging.Nlog;
|
||||
using MediaBrowser.Model.IO;
|
||||
using MediaBrowser.Model.Logging;
|
||||
using MediaBrowser.Model.MediaInfo;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
using MediaBrowser.Model.System;
|
||||
using MediaBrowser.Model.Updates;
|
||||
using MediaBrowser.Networking.Management;
|
||||
using MediaBrowser.Networking.Udp;
|
||||
using MediaBrowser.Networking.Web;
|
||||
using MediaBrowser.Networking.WebSocket;
|
||||
using MediaBrowser.Server.Implementations;
|
||||
using MediaBrowser.ServerApplication.Implementations;
|
||||
using SimpleInjector;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Diagnostics;
|
||||
using System.IO;
|
||||
using System.Linq;
|
||||
using System.Reflection;
|
||||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace MediaBrowser.ServerApplication
|
||||
{
|
||||
/// <summary>
|
||||
/// Class CompositionRoot
|
||||
/// </summary>
|
||||
public class ApplicationHost : IApplicationHost, IDisposable
|
||||
{
|
||||
/// <summary>
|
||||
/// Gets or sets the logger.
|
||||
/// </summary>
|
||||
/// <value>The logger.</value>
|
||||
private ILogger Logger { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the iso manager.
|
||||
/// </summary>
|
||||
/// <value>The iso manager.</value>
|
||||
private IIsoManager IsoManager { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the log file path.
|
||||
/// </summary>
|
||||
/// <value>The log file path.</value>
|
||||
public string LogFilePath { get; private set; }
|
||||
|
||||
/// <summary>
|
||||
/// The container
|
||||
/// </summary>
|
||||
private readonly Container _container = new Container();
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets the kernel.
|
||||
/// </summary>
|
||||
/// <value>The kernel.</value>
|
||||
public Kernel Kernel { get; private set; }
|
||||
|
||||
private readonly List<string> _failedAssemblies = new List<string>();
|
||||
/// <summary>
|
||||
/// Gets assemblies that failed to load
|
||||
/// </summary>
|
||||
public IEnumerable<string> FailedAssemblies
|
||||
{
|
||||
get { return _failedAssemblies; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets all types within all running assemblies
|
||||
/// </summary>
|
||||
/// <value>All types.</value>
|
||||
public Type[] AllTypes { get; private set; }
|
||||
|
||||
/// <summary>
|
||||
/// Gets all concrete types.
|
||||
/// </summary>
|
||||
/// <value>All concrete types.</value>
|
||||
public Type[] AllConcreteTypes { get; private set; }
|
||||
|
||||
/// <summary>
|
||||
/// The disposable parts
|
||||
/// </summary>
|
||||
private readonly List<IDisposable> _disposableParts = new List<IDisposable>();
|
||||
|
||||
/// <summary>
|
||||
/// The json serializer
|
||||
/// </summary>
|
||||
private readonly IJsonSerializer _jsonSerializer = new JsonSerializer();
|
||||
|
||||
/// <summary>
|
||||
/// The _XML serializer
|
||||
/// </summary>
|
||||
private readonly IXmlSerializer _xmlSerializer = new XmlSerializer();
|
||||
|
||||
/// <summary>
|
||||
/// The _application paths
|
||||
/// </summary>
|
||||
private readonly IServerApplicationPaths _applicationPaths = new ServerApplicationPaths();
|
||||
|
||||
/// <summary>
|
||||
/// The _task manager
|
||||
/// </summary>
|
||||
private readonly ITaskManager _taskManager;
|
||||
|
||||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="ApplicationHost" /> class.
|
||||
/// </summary>
|
||||
/// <param name="logger">The logger.</param>
|
||||
public ApplicationHost(ILogger logger)
|
||||
{
|
||||
Logger = logger;
|
||||
|
||||
_taskManager = new TaskManager(_applicationPaths, _jsonSerializer, Logger);
|
||||
|
||||
Kernel = new Kernel(this, _applicationPaths, _xmlSerializer, _taskManager, Logger);
|
||||
|
||||
RegisterResources();
|
||||
|
||||
FindParts();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Registers resources that classes will depend on
|
||||
/// </summary>
|
||||
internal void RegisterResources()
|
||||
{
|
||||
DiscoverTypes();
|
||||
|
||||
RegisterSingleInstance<IKernel>(Kernel);
|
||||
RegisterSingleInstance(Kernel);
|
||||
|
||||
RegisterSingleInstance<IApplicationHost>(this);
|
||||
RegisterSingleInstance(Logger);
|
||||
|
||||
IsoManager = new PismoIsoManager(Logger);
|
||||
|
||||
RegisterSingleInstance(_applicationPaths);
|
||||
RegisterSingleInstance<IApplicationPaths>(_applicationPaths);
|
||||
|
||||
RegisterSingleInstance(IsoManager);
|
||||
RegisterSingleInstance(_taskManager);
|
||||
RegisterSingleInstance<IBlurayExaminer>(() => new BdInfoExaminer());
|
||||
RegisterSingleInstance<INetworkManager>(() => new NetworkManager());
|
||||
RegisterSingleInstance<IZipClient>(() => new DotNetZipClient());
|
||||
RegisterSingleInstance<IWebSocketServer>(() => new AlchemyServer(Logger));
|
||||
RegisterSingleInstance(_jsonSerializer);
|
||||
RegisterSingleInstance(_xmlSerializer);
|
||||
RegisterSingleInstance<IProtobufSerializer>(() => ProtobufSerializer);
|
||||
Register(typeof(IUdpServer), typeof(UdpServer));
|
||||
RegisterSingleInstance(() => ServerFactory.CreateServer(this, Kernel, ProtobufSerializer, Logger, "Media Browser", "index.html"));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Discovers the types.
|
||||
/// </summary>
|
||||
private void DiscoverTypes()
|
||||
{
|
||||
_failedAssemblies.Clear();
|
||||
|
||||
AllTypes = GetComposablePartAssemblies().SelectMany(GetTypes).ToArray();
|
||||
|
||||
AllConcreteTypes = AllTypes.Where(t => t.IsClass && !t.IsAbstract && !t.IsInterface && !t.IsGenericType).ToArray();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Finds the parts.
|
||||
/// </summary>
|
||||
private void FindParts()
|
||||
{
|
||||
_taskManager.AddTasks(GetExports<IScheduledTask>(false));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets a list of types within an assembly
|
||||
/// This will handle situations that would normally throw an exception - such as a type within the assembly that depends on some other non-existant reference
|
||||
/// </summary>
|
||||
/// <param name="assembly">The assembly.</param>
|
||||
/// <returns>IEnumerable{Type}.</returns>
|
||||
/// <exception cref="System.ArgumentNullException">assembly</exception>
|
||||
private IEnumerable<Type> GetTypes(Assembly assembly)
|
||||
{
|
||||
if (assembly == null)
|
||||
{
|
||||
throw new ArgumentNullException("assembly");
|
||||
}
|
||||
|
||||
try
|
||||
{
|
||||
return assembly.GetTypes();
|
||||
}
|
||||
catch (ReflectionTypeLoadException ex)
|
||||
{
|
||||
// If it fails we can still get a list of the Types it was able to resolve
|
||||
return ex.Types.Where(t => t != null);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// The _protobuf serializer initialized
|
||||
/// </summary>
|
||||
private bool _protobufSerializerInitialized;
|
||||
/// <summary>
|
||||
/// The _protobuf serializer sync lock
|
||||
/// </summary>
|
||||
private object _protobufSerializerSyncLock = new object();
|
||||
/// <summary>
|
||||
/// Gets a dynamically compiled generated serializer that can serialize protocontracts without reflection
|
||||
/// </summary>
|
||||
private ProtobufSerializer _protobufSerializer;
|
||||
/// <summary>
|
||||
/// Gets the protobuf serializer.
|
||||
/// </summary>
|
||||
/// <value>The protobuf serializer.</value>
|
||||
public ProtobufSerializer ProtobufSerializer
|
||||
{
|
||||
get
|
||||
{
|
||||
// Lazy load
|
||||
LazyInitializer.EnsureInitialized(ref _protobufSerializer, ref _protobufSerializerInitialized, ref _protobufSerializerSyncLock, () => ProtobufSerializer.Create(AllTypes));
|
||||
return _protobufSerializer;
|
||||
}
|
||||
private set
|
||||
{
|
||||
_protobufSerializer = value;
|
||||
_protobufSerializerInitialized = value != null;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Creates an instance of type and resolves all constructor dependancies
|
||||
/// </summary>
|
||||
/// <param name="type">The type.</param>
|
||||
/// <returns>System.Object.</returns>
|
||||
public object CreateInstance(Type type)
|
||||
{
|
||||
try
|
||||
{
|
||||
return _container.GetInstance(type);
|
||||
}
|
||||
catch
|
||||
{
|
||||
Logger.Error("Error creating {0}", type.Name);
|
||||
|
||||
throw;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Registers the specified obj.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <param name="obj">The obj.</param>
|
||||
public void RegisterSingleInstance<T>(T obj)
|
||||
where T : class
|
||||
{
|
||||
_container.RegisterSingle(obj);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Registers the specified func.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <param name="func">The func.</param>
|
||||
public void Register<T>(Func<T> func)
|
||||
where T : class
|
||||
{
|
||||
_container.Register(func);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Registers the single instance.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <param name="func">The func.</param>
|
||||
public void RegisterSingleInstance<T>(Func<T> func)
|
||||
where T : class
|
||||
{
|
||||
_container.RegisterSingle(func);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Resolves this instance.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <returns>``0.</returns>
|
||||
public T Resolve<T>()
|
||||
{
|
||||
return (T)_container.GetRegistration(typeof(T), true).GetInstance();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Resolves this instance.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <returns>``0.</returns>
|
||||
public T TryResolve<T>()
|
||||
{
|
||||
var result = _container.GetRegistration(typeof(T), false);
|
||||
|
||||
if (result == null)
|
||||
{
|
||||
return default(T);
|
||||
}
|
||||
return (T)result.GetInstance();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Registers the specified service type.
|
||||
/// </summary>
|
||||
/// <param name="serviceType">Type of the service.</param>
|
||||
/// <param name="implementation">Type of the concrete.</param>
|
||||
public void Register(Type serviceType, Type implementation)
|
||||
{
|
||||
_container.Register(serviceType, implementation);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Restarts this instance.
|
||||
/// </summary>
|
||||
/// <exception cref="System.NotImplementedException"></exception>
|
||||
public void Restart()
|
||||
{
|
||||
App.Instance.Restart();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Reloads the logger.
|
||||
/// </summary>
|
||||
/// <exception cref="System.NotImplementedException"></exception>
|
||||
public void ReloadLogger()
|
||||
{
|
||||
LogFilePath = Path.Combine(Kernel.ApplicationPaths.LogDirectoryPath, "Server-" + DateTime.Now.Ticks + ".log");
|
||||
|
||||
NlogManager.AddFileTarget(LogFilePath, Kernel.Configuration.EnableDebugLevelLogging);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets or sets a value indicating whether this instance can self update.
|
||||
/// </summary>
|
||||
/// <value><c>true</c> if this instance can self update; otherwise, <c>false</c>.</value>
|
||||
public bool CanSelfUpdate
|
||||
{
|
||||
get { return ClickOnceHelper.IsNetworkDeployed; }
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Checks for update.
|
||||
/// </summary>
|
||||
/// <param name="cancellationToken">The cancellation token.</param>
|
||||
/// <param name="progress">The progress.</param>
|
||||
/// <returns>Task{CheckForUpdateResult}.</returns>
|
||||
public Task<CheckForUpdateResult> CheckForApplicationUpdate(CancellationToken cancellationToken, IProgress<double> progress)
|
||||
{
|
||||
return new ApplicationUpdateCheck().CheckForApplicationUpdate(cancellationToken, progress);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Updates the application.
|
||||
/// </summary>
|
||||
/// <param name="cancellationToken">The cancellation token.</param>
|
||||
/// <param name="progress">The progress.</param>
|
||||
/// <returns>Task.</returns>
|
||||
public Task UpdateApplication(CancellationToken cancellationToken, IProgress<double> progress)
|
||||
{
|
||||
return new ApplicationUpdater().UpdateApplication(cancellationToken, progress);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the composable part assemblies.
|
||||
/// </summary>
|
||||
/// <returns>IEnumerable{Assembly}.</returns>
|
||||
private IEnumerable<Assembly> GetComposablePartAssemblies()
|
||||
{
|
||||
// Gets all plugin assemblies by first reading all bytes of the .dll and calling Assembly.Load against that
|
||||
// This will prevent the .dll file from getting locked, and allow us to replace it when needed
|
||||
foreach (var pluginAssembly in Directory
|
||||
.EnumerateFiles(Kernel.ApplicationPaths.PluginsPath, "*.dll", SearchOption.TopDirectoryOnly)
|
||||
.Select(LoadAssembly).Where(a => a != null))
|
||||
{
|
||||
yield return pluginAssembly;
|
||||
}
|
||||
|
||||
var runningDirectory = Path.GetDirectoryName(Process.GetCurrentProcess().MainModule.FileName);
|
||||
var corePluginDirectory = Path.Combine(runningDirectory, "CorePlugins");
|
||||
|
||||
// This will prevent the .dll file from getting locked, and allow us to replace it when needed
|
||||
foreach (var pluginAssembly in Directory
|
||||
.EnumerateFiles(corePluginDirectory, "*.dll", SearchOption.TopDirectoryOnly)
|
||||
.Select(LoadAssembly).Where(a => a != null))
|
||||
{
|
||||
yield return pluginAssembly;
|
||||
}
|
||||
|
||||
// Include composable parts in the Model assembly
|
||||
yield return typeof(SystemInfo).Assembly;
|
||||
|
||||
// Include composable parts in the Common assembly
|
||||
yield return typeof(IKernel).Assembly;
|
||||
|
||||
// Include composable parts in the Controller assembly
|
||||
yield return typeof(Kernel).Assembly;
|
||||
|
||||
// Common implementations
|
||||
yield return typeof(TaskManager).Assembly;
|
||||
|
||||
// Server implementations
|
||||
yield return typeof(ServerApplicationPaths).Assembly;
|
||||
|
||||
// Include composable parts in the running assembly
|
||||
yield return GetType().Assembly;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Loads the assembly.
|
||||
/// </summary>
|
||||
/// <param name="file">The file.</param>
|
||||
/// <returns>Assembly.</returns>
|
||||
private Assembly LoadAssembly(string file)
|
||||
{
|
||||
try
|
||||
{
|
||||
return Assembly.Load(File.ReadAllBytes((file)));
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
_failedAssemblies.Add(file);
|
||||
Logger.ErrorException("Error loading assembly {0}", ex, file);
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Gets the exports.
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <param name="allTypes">All types.</param>
|
||||
/// <param name="manageLiftime">if set to <c>true</c> [manage liftime].</param>
|
||||
/// <returns>IEnumerable{``0}.</returns>
|
||||
public IEnumerable<T> GetExports<T>(bool manageLiftime = true)
|
||||
{
|
||||
var currentType = typeof(T);
|
||||
|
||||
Logger.Info("Composing instances of " + currentType.Name);
|
||||
|
||||
var parts = AllConcreteTypes.Where(currentType.IsAssignableFrom).Select(CreateInstance).Cast<T>().ToArray();
|
||||
|
||||
if (manageLiftime)
|
||||
{
|
||||
_disposableParts.AddRange(parts.OfType<IDisposable>());
|
||||
}
|
||||
|
||||
return parts;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Performs application-defined tasks associated with freeing, releasing, or resetting unmanaged resources.
|
||||
/// </summary>
|
||||
public void Dispose()
|
||||
{
|
||||
Dispose(true);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Releases unmanaged and - optionally - managed resources.
|
||||
/// </summary>
|
||||
/// <param name="dispose"><c>true</c> to release both managed and unmanaged resources; <c>false</c> to release only unmanaged resources.</param>
|
||||
protected virtual void Dispose(bool dispose)
|
||||
{
|
||||
IsoManager.Dispose();
|
||||
|
||||
foreach (var part in _disposableParts)
|
||||
{
|
||||
part.Dispose();
|
||||
}
|
||||
|
||||
_disposableParts.Clear();
|
||||
}
|
||||
}
|
||||
|
||||
public class MyClass
|
||||
{
|
||||
public MyClass()
|
||||
{
|
||||
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,11 +1,12 @@
|
|||
using MediaBrowser.Common.Serialization;
|
||||
using MediaBrowser.Controller;
|
||||
using MediaBrowser.Controller;
|
||||
using MediaBrowser.Controller.Entities;
|
||||
using MediaBrowser.Controller.Entities.Movies;
|
||||
using MediaBrowser.Controller.Entities.TV;
|
||||
using MediaBrowser.Controller.Library;
|
||||
using MediaBrowser.Controller.Localization;
|
||||
using MediaBrowser.Model.Entities;
|
||||
using MediaBrowser.Model.Logging;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Globalization;
|
||||
|
@ -18,7 +19,6 @@ using System.Windows.Controls;
|
|||
using System.Windows.Data;
|
||||
using System.Windows.Input;
|
||||
using System.Windows.Media.Imaging;
|
||||
using MediaBrowser.Model.Logging;
|
||||
|
||||
namespace MediaBrowser.ServerApplication
|
||||
{
|
||||
|
@ -27,8 +27,10 @@ namespace MediaBrowser.ServerApplication
|
|||
/// </summary>
|
||||
public partial class LibraryExplorer : Window
|
||||
{
|
||||
private ILogger _logger;
|
||||
private readonly ILogger _logger;
|
||||
|
||||
private readonly IJsonSerializer _jsonSerializer;
|
||||
|
||||
/// <summary>
|
||||
/// The current user
|
||||
/// </summary>
|
||||
|
@ -36,9 +38,10 @@ namespace MediaBrowser.ServerApplication
|
|||
/// <summary>
|
||||
/// Initializes a new instance of the <see cref="LibraryExplorer" /> class.
|
||||
/// </summary>
|
||||
public LibraryExplorer(ILogger logger)
|
||||
public LibraryExplorer(IJsonSerializer jsonSerializer, ILogger logger)
|
||||
{
|
||||
_logger = logger;
|
||||
_jsonSerializer = jsonSerializer;
|
||||
|
||||
InitializeComponent();
|
||||
lblVersion.Content = "Version: " + Kernel.Instance.ApplicationVersion;
|
||||
|
@ -161,7 +164,7 @@ namespace MediaBrowser.ServerApplication
|
|||
lblIndexBy.Visibility = ddlIndexBy.Visibility = ddlSortBy.Visibility = lblSortBy.Visibility = Visibility.Hidden;
|
||||
|
||||
}
|
||||
txtData.Text = FormatJson(JsonSerializer.SerializeToString(item)) + trailers + features;
|
||||
txtData.Text = FormatJson(_jsonSerializer.SerializeToString(item)) + trailers + features;
|
||||
|
||||
var previews = new List<PreviewItem>();
|
||||
await Task.Run(() =>
|
||||
|
|
|
@ -2,6 +2,7 @@
|
|||
using MediaBrowser.Controller.Entities;
|
||||
using MediaBrowser.Controller.Library;
|
||||
using MediaBrowser.Model.Logging;
|
||||
using MediaBrowser.Model.Serialization;
|
||||
using MediaBrowser.ServerApplication.Controls;
|
||||
using MediaBrowser.ServerApplication.Logging;
|
||||
using System;
|
||||
|
@ -38,6 +39,11 @@ namespace MediaBrowser.ServerApplication
|
|||
/// <value>The new item timer.</value>
|
||||
private Timer NewItemTimer { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// The _json serializer
|
||||
/// </summary>
|
||||
private readonly IJsonSerializer _jsonSerializer;
|
||||
|
||||
/// <summary>
|
||||
/// The _logger
|
||||
/// </summary>
|
||||
|
@ -48,13 +54,18 @@ namespace MediaBrowser.ServerApplication
|
|||
/// </summary>
|
||||
/// <param name="logger">The logger.</param>
|
||||
/// <exception cref="System.ArgumentNullException">logger</exception>
|
||||
public MainWindow(ILogger logger)
|
||||
public MainWindow(IJsonSerializer jsonSerializer, ILogger logger)
|
||||
{
|
||||
if (jsonSerializer == null)
|
||||
{
|
||||
throw new ArgumentNullException("jsonSerializer");
|
||||
}
|
||||
if (logger == null)
|
||||
{
|
||||
throw new ArgumentNullException("logger");
|
||||
}
|
||||
|
||||
_jsonSerializer = jsonSerializer;
|
||||
_logger = logger;
|
||||
|
||||
InitializeComponent();
|
||||
|
@ -282,7 +293,7 @@ namespace MediaBrowser.ServerApplication
|
|||
/// <param name="e">The <see cref="RoutedEventArgs" /> instance containing the event data.</param>
|
||||
private void cmOpenExplorer_click(object sender, RoutedEventArgs e)
|
||||
{
|
||||
(new LibraryExplorer(_logger)).Show();
|
||||
(new LibraryExplorer(_jsonSerializer, _logger)).Show();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
|
|
@ -128,36 +128,6 @@
|
|||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>..\ThirdParty\UPnP\Libs\Platinum.Managed.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="ServiceStack, Version=3.9.37.0, Culture=neutral, processorArchitecture=MSIL">
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>..\packages\ServiceStack.3.9.37\lib\net35\ServiceStack.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="ServiceStack.Common, Version=3.9.37.0, Culture=neutral, processorArchitecture=MSIL">
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>..\packages\ServiceStack.Common.3.9.37\lib\net35\ServiceStack.Common.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="ServiceStack.Interfaces, Version=3.9.37.0, Culture=neutral, processorArchitecture=MSIL">
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>..\packages\ServiceStack.Common.3.9.37\lib\net35\ServiceStack.Interfaces.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="ServiceStack.OrmLite, Version=3.9.37.0, Culture=neutral, processorArchitecture=MSIL">
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>..\packages\ServiceStack.OrmLite.SqlServer.3.9.37\lib\ServiceStack.OrmLite.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="ServiceStack.OrmLite.SqlServer">
|
||||
<HintPath>..\packages\ServiceStack.OrmLite.SqlServer.3.9.37\lib\ServiceStack.OrmLite.SqlServer.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="ServiceStack.Redis">
|
||||
<HintPath>..\packages\ServiceStack.Redis.3.9.37\lib\net35\ServiceStack.Redis.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="ServiceStack.ServiceInterface, Version=1.0.0.0, Culture=neutral, processorArchitecture=MSIL">
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>..\packages\ServiceStack.3.9.37\lib\net35\ServiceStack.ServiceInterface.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="ServiceStack.Text, Version=3.9.37.0, Culture=neutral, processorArchitecture=MSIL">
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>..\packages\ServiceStack.Text.3.9.37\lib\net35\ServiceStack.Text.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="SimpleInjector, Version=2.0.0.0, Culture=neutral, PublicKeyToken=984cb50dea722e99, processorArchitecture=MSIL">
|
||||
<SpecificVersion>False</SpecificVersion>
|
||||
<HintPath>..\packages\SimpleInjector.2.0.0-beta5\lib\net40-client\SimpleInjector.dll</HintPath>
|
||||
|
@ -220,6 +190,7 @@
|
|||
<DependentUpon>App.xaml</DependentUpon>
|
||||
<SubType>Code</SubType>
|
||||
</Compile>
|
||||
<Compile Include="ApplicationHost.cs" />
|
||||
<Compile Include="Controls\ItemUpdateNotification.xaml.cs">
|
||||
<DependentUpon>ItemUpdateNotification.xaml</DependentUpon>
|
||||
</Compile>
|
||||
|
@ -279,6 +250,10 @@
|
|||
<Project>{cc96bf3e-0bda-4809-bc4b-bb6d418f4a84}</Project>
|
||||
<Name>MediaBrowser.ClickOnce</Name>
|
||||
</ProjectReference>
|
||||
<ProjectReference Include="..\MediaBrowser.Common.Implementations\MediaBrowser.Common.Implementations.csproj">
|
||||
<Project>{c4d2573a-3fd3-441f-81af-174ac4cd4e1d}</Project>
|
||||
<Name>MediaBrowser.Common.Implementations</Name>
|
||||
</ProjectReference>
|
||||
<ProjectReference Include="..\MediaBrowser.Common\MediaBrowser.Common.csproj">
|
||||
<Project>{9142eefa-7570-41e1-bfcc-468bb571af2f}</Project>
|
||||
<Name>MediaBrowser.Common</Name>
|
||||
|
@ -303,6 +278,10 @@
|
|||
<Project>{7c11010e-179a-49b7-bfb2-f1656f5e71ad}</Project>
|
||||
<Name>MediaBrowser.Networking</Name>
|
||||
</ProjectReference>
|
||||
<ProjectReference Include="..\MediaBrowser.Server.Implementations\MediaBrowser.Server.Implementations.csproj">
|
||||
<Project>{2e781478-814d-4a48-9d80-bff206441a65}</Project>
|
||||
<Name>MediaBrowser.Server.Implementations</Name>
|
||||
</ProjectReference>
|
||||
<ProjectReference Include="..\MediaBrowser.Server.Uninstall\MediaBrowser.Server.Uninstall.csproj">
|
||||
<Project>{5443422f-9548-417a-90dd-2fc91f2b5999}</Project>
|
||||
<Name>MediaBrowser.Server.Uninstall</Name>
|
||||
|
|
|
@ -3,11 +3,6 @@
|
|||
<package id="DotNetZip" version="1.9.1.8" targetFramework="net45" />
|
||||
<package id="Hardcodet.Wpf.TaskbarNotification" version="1.0.4.0" targetFramework="net45" />
|
||||
<package id="NLog" version="2.0.0.2000" targetFramework="net45" />
|
||||
<package id="ServiceStack" version="3.9.37" targetFramework="net45" />
|
||||
<package id="ServiceStack.Common" version="3.9.37" targetFramework="net45" />
|
||||
<package id="ServiceStack.OrmLite.SqlServer" version="3.9.37" targetFramework="net45" />
|
||||
<package id="ServiceStack.Redis" version="3.9.37" targetFramework="net45" />
|
||||
<package id="ServiceStack.Text" version="3.9.37" targetFramework="net45" />
|
||||
<package id="SimpleInjector" version="2.0.0-beta5" targetFramework="net45" />
|
||||
<package id="System.Data.SQLite" version="1.0.84.0" targetFramework="net45" />
|
||||
</packages>
|
|
@ -1,7 +1,6 @@
|
|||
using MediaBrowser.Common.Extensions;
|
||||
using MediaBrowser.Common.Net;
|
||||
using MediaBrowser.Common.ScheduledTasks;
|
||||
using MediaBrowser.Common.ScheduledTasks.Tasks;
|
||||
using MediaBrowser.Controller;
|
||||
using MediaBrowser.Controller.Library;
|
||||
using MediaBrowser.Controller.Plugins;
|
||||
|
@ -137,7 +136,7 @@ namespace MediaBrowser.WebDashboard.Api
|
|||
.Select(ScheduledTaskHelpers.GetTaskInfo)
|
||||
.ToArray(),
|
||||
|
||||
ApplicationUpdateTaskId = taskManager.ScheduledTasks.OfType<SystemUpdateTask>().First().Id,
|
||||
ApplicationUpdateTaskId = taskManager.ScheduledTasks.First(t => t.GetType().Name.Equals("SystemUpdateTask", StringComparison.OrdinalIgnoreCase)).Id,
|
||||
|
||||
ActiveConnections = connections,
|
||||
|
||||
|
|
|
@ -20,8 +20,6 @@ Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Solution Items", "Solution
|
|||
Performance19.psess = Performance19.psess
|
||||
EndProjectSection
|
||||
EndProject
|
||||
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "MediaBrowser.ApiInteraction.Javascript", "MediaBrowser.ApiInteraction.Javascript\MediaBrowser.ApiInteraction.Javascript.csproj", "{767B536E-D90C-4D74-A14B-8564B16F3499}"
|
||||
EndProject
|
||||
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "MediaBrowser.ApiInteraction", "MediaBrowser.ApiInteraction\MediaBrowser.ApiInteraction.csproj", "{921C0F64-FDA7-4E9F-9E73-0CB0EEDB2422}"
|
||||
EndProject
|
||||
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "MediaBrowser.ApiInteraction.Portable", "MediaBrowser.ApiInteraction.Portable\MediaBrowser.ApiInteraction.Portable.csproj", "{52E0C440-85C0-4A99-ACFE-07C87B2600BE}"
|
||||
|
@ -41,10 +39,6 @@ Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "MediaBrowser.IsoMounter", "
|
|||
EndProject
|
||||
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "MediaBrowser.Installer", "MediaBrowser.Installer\MediaBrowser.Installer.csproj", "{3879F78A-D6F6-45E5-B2A8-D8DCF2DABB74}"
|
||||
EndProject
|
||||
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "MediaBrowser.Server.Sqlite", "MediaBrowser.Server.Sqlite\MediaBrowser.Server.Sqlite.csproj", "{8649ED6B-8504-4D00-BFA5-B8C73CC744DB}"
|
||||
EndProject
|
||||
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "MediaBrowser.Server.WorldWeatherOnline", "MediaBrowser.Server.WorldWeatherOnline\MediaBrowser.Server.WorldWeatherOnline.csproj", "{973CA45C-8362-490B-8327-C68098FD4891}"
|
||||
EndProject
|
||||
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "MediaBrowser.Logging.NLog", "MediaBrowser.Logging.NLog\MediaBrowser.Logging.NLog.csproj", "{67310740-0EC4-4DC2-9921-33DF38B20167}"
|
||||
EndProject
|
||||
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "MediaBrowser.ClickOnce", "MediaBrowser.ClickOnce\MediaBrowser.ClickOnce.csproj", "{CC96BF3E-0BDA-4809-BC4B-BB6D418F4A84}"
|
||||
|
@ -53,6 +47,10 @@ Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "MediaBrowser.Networking", "
|
|||
EndProject
|
||||
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "MediaBrowser.Uninstaller", "MediaBrowser.Uninstaller\MediaBrowser.Uninstaller.csproj", "{FACAF749-3E28-46DD-B613-654FCD434959}"
|
||||
EndProject
|
||||
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "MediaBrowser.Common.Implementations", "MediaBrowser.Common.Implementations\MediaBrowser.Common.Implementations.csproj", "{C4D2573A-3FD3-441F-81AF-174AC4CD4E1D}"
|
||||
EndProject
|
||||
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "MediaBrowser.Server.Implementations", "MediaBrowser.Server.Implementations\MediaBrowser.Server.Implementations.csproj", "{2E781478-814D-4A48-9D80-BFF206441A65}"
|
||||
EndProject
|
||||
Global
|
||||
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||
Debug|Any CPU = Debug|Any CPU
|
||||
|
@ -163,21 +161,6 @@ Global
|
|||
{5624B7B5-B5A7-41D8-9F10-CC5611109619}.Release|x64.ActiveCfg = Release|Any CPU
|
||||
{5624B7B5-B5A7-41D8-9F10-CC5611109619}.Release|x86.ActiveCfg = Release|Any CPU
|
||||
{5624B7B5-B5A7-41D8-9F10-CC5611109619}.Release|x86.Build.0 = Release|Any CPU
|
||||
{767B536E-D90C-4D74-A14B-8564B16F3499}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{767B536E-D90C-4D74-A14B-8564B16F3499}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{767B536E-D90C-4D74-A14B-8564B16F3499}.Debug|Mixed Platforms.ActiveCfg = Debug|Any CPU
|
||||
{767B536E-D90C-4D74-A14B-8564B16F3499}.Debug|Mixed Platforms.Build.0 = Debug|Any CPU
|
||||
{767B536E-D90C-4D74-A14B-8564B16F3499}.Debug|Win32.ActiveCfg = Debug|Any CPU
|
||||
{767B536E-D90C-4D74-A14B-8564B16F3499}.Debug|x64.ActiveCfg = Debug|Any CPU
|
||||
{767B536E-D90C-4D74-A14B-8564B16F3499}.Debug|x86.ActiveCfg = Debug|Any CPU
|
||||
{767B536E-D90C-4D74-A14B-8564B16F3499}.Debug|x86.Build.0 = Debug|Any CPU
|
||||
{767B536E-D90C-4D74-A14B-8564B16F3499}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{767B536E-D90C-4D74-A14B-8564B16F3499}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{767B536E-D90C-4D74-A14B-8564B16F3499}.Release|Mixed Platforms.ActiveCfg = Release|Any CPU
|
||||
{767B536E-D90C-4D74-A14B-8564B16F3499}.Release|Mixed Platforms.Build.0 = Release|Any CPU
|
||||
{767B536E-D90C-4D74-A14B-8564B16F3499}.Release|Win32.ActiveCfg = Release|Any CPU
|
||||
{767B536E-D90C-4D74-A14B-8564B16F3499}.Release|x64.ActiveCfg = Release|Any CPU
|
||||
{767B536E-D90C-4D74-A14B-8564B16F3499}.Release|x86.ActiveCfg = Release|Any CPU
|
||||
{921C0F64-FDA7-4E9F-9E73-0CB0EEDB2422}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{921C0F64-FDA7-4E9F-9E73-0CB0EEDB2422}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{921C0F64-FDA7-4E9F-9E73-0CB0EEDB2422}.Debug|Mixed Platforms.ActiveCfg = Debug|Any CPU
|
||||
|
@ -266,34 +249,6 @@ Global
|
|||
{3879F78A-D6F6-45E5-B2A8-D8DCF2DABB74}.Release|Win32.ActiveCfg = Release|Any CPU
|
||||
{3879F78A-D6F6-45E5-B2A8-D8DCF2DABB74}.Release|x64.ActiveCfg = Release|Any CPU
|
||||
{3879F78A-D6F6-45E5-B2A8-D8DCF2DABB74}.Release|x86.ActiveCfg = Release|Any CPU
|
||||
{8649ED6B-8504-4D00-BFA5-B8C73CC744DB}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{8649ED6B-8504-4D00-BFA5-B8C73CC744DB}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{8649ED6B-8504-4D00-BFA5-B8C73CC744DB}.Debug|Mixed Platforms.ActiveCfg = Debug|Any CPU
|
||||
{8649ED6B-8504-4D00-BFA5-B8C73CC744DB}.Debug|Mixed Platforms.Build.0 = Debug|Any CPU
|
||||
{8649ED6B-8504-4D00-BFA5-B8C73CC744DB}.Debug|Win32.ActiveCfg = Debug|Any CPU
|
||||
{8649ED6B-8504-4D00-BFA5-B8C73CC744DB}.Debug|x64.ActiveCfg = Debug|Any CPU
|
||||
{8649ED6B-8504-4D00-BFA5-B8C73CC744DB}.Debug|x86.ActiveCfg = Debug|Any CPU
|
||||
{8649ED6B-8504-4D00-BFA5-B8C73CC744DB}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{8649ED6B-8504-4D00-BFA5-B8C73CC744DB}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{8649ED6B-8504-4D00-BFA5-B8C73CC744DB}.Release|Mixed Platforms.ActiveCfg = Release|Any CPU
|
||||
{8649ED6B-8504-4D00-BFA5-B8C73CC744DB}.Release|Mixed Platforms.Build.0 = Release|Any CPU
|
||||
{8649ED6B-8504-4D00-BFA5-B8C73CC744DB}.Release|Win32.ActiveCfg = Release|Any CPU
|
||||
{8649ED6B-8504-4D00-BFA5-B8C73CC744DB}.Release|x64.ActiveCfg = Release|Any CPU
|
||||
{8649ED6B-8504-4D00-BFA5-B8C73CC744DB}.Release|x86.ActiveCfg = Release|Any CPU
|
||||
{973CA45C-8362-490B-8327-C68098FD4891}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{973CA45C-8362-490B-8327-C68098FD4891}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{973CA45C-8362-490B-8327-C68098FD4891}.Debug|Mixed Platforms.ActiveCfg = Debug|Any CPU
|
||||
{973CA45C-8362-490B-8327-C68098FD4891}.Debug|Mixed Platforms.Build.0 = Debug|Any CPU
|
||||
{973CA45C-8362-490B-8327-C68098FD4891}.Debug|Win32.ActiveCfg = Debug|Any CPU
|
||||
{973CA45C-8362-490B-8327-C68098FD4891}.Debug|x64.ActiveCfg = Debug|Any CPU
|
||||
{973CA45C-8362-490B-8327-C68098FD4891}.Debug|x86.ActiveCfg = Debug|Any CPU
|
||||
{973CA45C-8362-490B-8327-C68098FD4891}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{973CA45C-8362-490B-8327-C68098FD4891}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{973CA45C-8362-490B-8327-C68098FD4891}.Release|Mixed Platforms.ActiveCfg = Release|Any CPU
|
||||
{973CA45C-8362-490B-8327-C68098FD4891}.Release|Mixed Platforms.Build.0 = Release|Any CPU
|
||||
{973CA45C-8362-490B-8327-C68098FD4891}.Release|Win32.ActiveCfg = Release|Any CPU
|
||||
{973CA45C-8362-490B-8327-C68098FD4891}.Release|x64.ActiveCfg = Release|Any CPU
|
||||
{973CA45C-8362-490B-8327-C68098FD4891}.Release|x86.ActiveCfg = Release|Any CPU
|
||||
{67310740-0EC4-4DC2-9921-33DF38B20167}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{67310740-0EC4-4DC2-9921-33DF38B20167}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{67310740-0EC4-4DC2-9921-33DF38B20167}.Debug|Mixed Platforms.ActiveCfg = Debug|Any CPU
|
||||
|
@ -350,6 +305,34 @@ Global
|
|||
{FACAF749-3E28-46DD-B613-654FCD434959}.Release|Win32.ActiveCfg = Release|Any CPU
|
||||
{FACAF749-3E28-46DD-B613-654FCD434959}.Release|x64.ActiveCfg = Release|Any CPU
|
||||
{FACAF749-3E28-46DD-B613-654FCD434959}.Release|x86.ActiveCfg = Release|Any CPU
|
||||
{C4D2573A-3FD3-441F-81AF-174AC4CD4E1D}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{C4D2573A-3FD3-441F-81AF-174AC4CD4E1D}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{C4D2573A-3FD3-441F-81AF-174AC4CD4E1D}.Debug|Mixed Platforms.ActiveCfg = Debug|Any CPU
|
||||
{C4D2573A-3FD3-441F-81AF-174AC4CD4E1D}.Debug|Mixed Platforms.Build.0 = Debug|Any CPU
|
||||
{C4D2573A-3FD3-441F-81AF-174AC4CD4E1D}.Debug|Win32.ActiveCfg = Debug|Any CPU
|
||||
{C4D2573A-3FD3-441F-81AF-174AC4CD4E1D}.Debug|x64.ActiveCfg = Debug|Any CPU
|
||||
{C4D2573A-3FD3-441F-81AF-174AC4CD4E1D}.Debug|x86.ActiveCfg = Debug|Any CPU
|
||||
{C4D2573A-3FD3-441F-81AF-174AC4CD4E1D}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{C4D2573A-3FD3-441F-81AF-174AC4CD4E1D}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{C4D2573A-3FD3-441F-81AF-174AC4CD4E1D}.Release|Mixed Platforms.ActiveCfg = Release|Any CPU
|
||||
{C4D2573A-3FD3-441F-81AF-174AC4CD4E1D}.Release|Mixed Platforms.Build.0 = Release|Any CPU
|
||||
{C4D2573A-3FD3-441F-81AF-174AC4CD4E1D}.Release|Win32.ActiveCfg = Release|Any CPU
|
||||
{C4D2573A-3FD3-441F-81AF-174AC4CD4E1D}.Release|x64.ActiveCfg = Release|Any CPU
|
||||
{C4D2573A-3FD3-441F-81AF-174AC4CD4E1D}.Release|x86.ActiveCfg = Release|Any CPU
|
||||
{2E781478-814D-4A48-9D80-BFF206441A65}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{2E781478-814D-4A48-9D80-BFF206441A65}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{2E781478-814D-4A48-9D80-BFF206441A65}.Debug|Mixed Platforms.ActiveCfg = Debug|Any CPU
|
||||
{2E781478-814D-4A48-9D80-BFF206441A65}.Debug|Mixed Platforms.Build.0 = Debug|Any CPU
|
||||
{2E781478-814D-4A48-9D80-BFF206441A65}.Debug|Win32.ActiveCfg = Debug|Any CPU
|
||||
{2E781478-814D-4A48-9D80-BFF206441A65}.Debug|x64.ActiveCfg = Debug|Any CPU
|
||||
{2E781478-814D-4A48-9D80-BFF206441A65}.Debug|x86.ActiveCfg = Debug|Any CPU
|
||||
{2E781478-814D-4A48-9D80-BFF206441A65}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{2E781478-814D-4A48-9D80-BFF206441A65}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{2E781478-814D-4A48-9D80-BFF206441A65}.Release|Mixed Platforms.ActiveCfg = Release|Any CPU
|
||||
{2E781478-814D-4A48-9D80-BFF206441A65}.Release|Mixed Platforms.Build.0 = Release|Any CPU
|
||||
{2E781478-814D-4A48-9D80-BFF206441A65}.Release|Win32.ActiveCfg = Release|Any CPU
|
||||
{2E781478-814D-4A48-9D80-BFF206441A65}.Release|x64.ActiveCfg = Release|Any CPU
|
||||
{2E781478-814D-4A48-9D80-BFF206441A65}.Release|x86.ActiveCfg = Release|Any CPU
|
||||
EndGlobalSection
|
||||
GlobalSection(SolutionProperties) = preSolution
|
||||
HideSolutionNode = FALSE
|
||||
|
|
Loading…
Reference in New Issue