SignalR/Nancy/Owin/Mono

This commit is contained in:
kay.one 2013-05-05 14:24:33 -07:00
parent 45b4972091
commit 87a5dc7869
40 changed files with 2375 additions and 76 deletions

View File

@ -16,6 +16,9 @@ module.exports = function (grunt) {
'UI/JsLibraries/jquery.cookie.js' : 'http://raw.github.com/carhartl/jquery-cookie/master/jquery.cookie.js', 'UI/JsLibraries/jquery.cookie.js' : 'http://raw.github.com/carhartl/jquery-cookie/master/jquery.cookie.js',
'UI/JsLibraries/jquery.js' : 'http://code.jquery.com/jquery.js', 'UI/JsLibraries/jquery.js' : 'http://code.jquery.com/jquery.js',
'UI/JsLibraries/jquery.backstretch.js' : 'http://raw.github.com/srobbin/jquery-backstretch/master/jquery.backstretch.js', 'UI/JsLibraries/jquery.backstretch.js' : 'http://raw.github.com/srobbin/jquery-backstretch/master/jquery.backstretch.js',
'UI/JsLibraries/jquery.signalR.js' : 'https://raw.github.com/SignalR/SignalR/master/samples/Microsoft.AspNet.SignalR.Hosting.AspNet.Samples/Scripts/jquery.signalR.js',
'UI/JsLibraries/require.js' : 'http://raw.github.com/jrburke/requirejs/master/require.js', 'UI/JsLibraries/require.js' : 'http://raw.github.com/jrburke/requirejs/master/require.js',
'UI/JsLibraries/sugar.js' : 'http://raw.github.com/andrewplummer/Sugar/master/release/sugar-full.development.js', 'UI/JsLibraries/sugar.js' : 'http://raw.github.com/andrewplummer/Sugar/master/release/sugar-full.development.js',
'UI/JsLibraries/underscore.js' : 'http://underscorejs.org/underscore.js', 'UI/JsLibraries/underscore.js' : 'http://underscorejs.org/underscore.js',

View File

@ -16,7 +16,8 @@ namespace NzbDrone.Api.Frontend
if( if(
Request.Path.Contains(".") Request.Path.Contains(".")
|| Request.Path.StartsWith("/static", StringComparison.CurrentCultureIgnoreCase) || Request.Path.StartsWith("/static", StringComparison.CurrentCultureIgnoreCase)
|| Request.Path.StartsWith("/api", StringComparison.CurrentCultureIgnoreCase)) || Request.Path.StartsWith("/api", StringComparison.CurrentCultureIgnoreCase)
|| Request.Path.StartsWith("/signalr", StringComparison.CurrentCultureIgnoreCase))
{ {
return new NotFoundResponse(); return new NotFoundResponse();
} }

View File

@ -63,6 +63,9 @@
<SpecificVersion>False</SpecificVersion> <SpecificVersion>False</SpecificVersion>
<HintPath>..\packages\FluentValidation.4.0.0.0\lib\Net40\FluentValidation.dll</HintPath> <HintPath>..\packages\FluentValidation.4.0.0.0\lib\Net40\FluentValidation.dll</HintPath>
</Reference> </Reference>
<Reference Include="Microsoft.AspNet.SignalR.Core">
<HintPath>..\packages\Microsoft.AspNet.SignalR.Core.1.0.1\lib\net40\Microsoft.AspNet.SignalR.Core.dll</HintPath>
</Reference>
<Reference Include="Nancy, Version=0.16.1.0, Culture=neutral, processorArchitecture=MSIL"> <Reference Include="Nancy, Version=0.16.1.0, Culture=neutral, processorArchitecture=MSIL">
<SpecificVersion>False</SpecificVersion> <SpecificVersion>False</SpecificVersion>
<HintPath>..\packages\Nancy.0.16.1\lib\net40\Nancy.dll</HintPath> <HintPath>..\packages\Nancy.0.16.1\lib\net40\Nancy.dll</HintPath>
@ -119,6 +122,7 @@
<Compile Include="RootFolders\RootFolderModule.cs" /> <Compile Include="RootFolders\RootFolderModule.cs" />
<Compile Include="RootFolders\RootFolderResource.cs" /> <Compile Include="RootFolders\RootFolderResource.cs" />
<Compile Include="Seasons\SeasonModule.cs" /> <Compile Include="Seasons\SeasonModule.cs" />
<Compile Include="Series\SeriesConnection.cs" />
<Compile Include="Series\SeriesResource.cs" /> <Compile Include="Series\SeriesResource.cs" />
<Compile Include="Series\SeriesModule.cs" /> <Compile Include="Series\SeriesModule.cs" />
<Compile Include="Series\SeriesLookupModule.cs" /> <Compile Include="Series\SeriesLookupModule.cs" />
@ -139,6 +143,9 @@
<Compile Include="Resolvers\QualitiesToAllowedResolver.cs" /> <Compile Include="Resolvers\QualitiesToAllowedResolver.cs" />
<Compile Include="Resolvers\QualityTypesToIntResolver.cs" /> <Compile Include="Resolvers\QualityTypesToIntResolver.cs" />
<Compile Include="Config\SettingsModule.cs" /> <Compile Include="Config\SettingsModule.cs" />
<Compile Include="SignalR\BasicResourceConnection.cs" />
<Compile Include="SignalR\SignalrDependencyResolver.cs" />
<Compile Include="SignalR\NzbDronePersistentConnection.cs" />
<Compile Include="TinyIoCNancyBootstrapper.cs" /> <Compile Include="TinyIoCNancyBootstrapper.cs" />
<Compile Include="Validation\IdValidationRule.cs" /> <Compile Include="Validation\IdValidationRule.cs" />
</ItemGroup> </ItemGroup>

View File

@ -0,0 +1,13 @@
using NLog;
using NzbDrone.Api.SignalR;
namespace NzbDrone.Api.Series
{
public class SeriesConnection : BasicResourceConnection<Core.Tv.Series>
{
public override string Resource
{
get { return "/Series"; }
}
}
}

View File

@ -0,0 +1,39 @@
using System.Threading.Tasks;
using Microsoft.AspNet.SignalR;
using NLog;
using NzbDrone.Common.Messaging;
using NzbDrone.Core.Datastore;
using NzbDrone.Core.Datastore.Events;
namespace NzbDrone.Api.SignalR
{
public abstract class BasicResourceConnection<T> :
NzbDronePersistentConnection,
IHandleAsync<ModelEvent<T>>
where T : ModelBase
{
private readonly Logger _logger;
public BasicResourceConnection()
{
_logger = LogManager.GetCurrentClassLogger();
}
protected override Task OnConnected(IRequest request, string connectionId)
{
_logger.Debug("SignalR client connected. ID:{0}", connectionId);
return base.OnConnected(request, connectionId);
}
public override Task ProcessRequest(Microsoft.AspNet.SignalR.Hosting.HostContext context)
{
_logger.Debug("Request: {0}", context);
return base.ProcessRequest(context);
}
public void HandleAsync(ModelEvent<T> message)
{
Connection.Broadcast(message);
}
}
}

View File

@ -0,0 +1,9 @@
using Microsoft.AspNet.SignalR;
namespace NzbDrone.Api.SignalR
{
public abstract class NzbDronePersistentConnection : PersistentConnection
{
public abstract string Resource { get; }
}
}

View File

@ -0,0 +1,34 @@
using System;
using System.Collections.Generic;
using System.Linq;
using Microsoft.AspNet.SignalR;
using TinyIoC;
namespace NzbDrone.Api.SignalR
{
public class SignalrDependencyResolver : DefaultDependencyResolver
{
private readonly TinyIoCContainer _container;
public static void Register(TinyIoCContainer container)
{
GlobalHost.DependencyResolver = new SignalrDependencyResolver(container);
}
private SignalrDependencyResolver(TinyIoCContainer container)
{
_container = container;
}
public override object GetService(Type serviceType)
{
return _container.CanResolve(serviceType) ? _container.Resolve(serviceType) : base.GetService(serviceType);
}
public override IEnumerable<object> GetServices(Type serviceType)
{
var objects = _container.CanResolve(serviceType) ? _container.ResolveAll(serviceType) : new object[] { };
return objects.Concat(base.GetServices(serviceType));
}
}
}

View File

@ -2,6 +2,7 @@
<packages> <packages>
<package id="AutoMapper" version="2.2.1" targetFramework="net40" /> <package id="AutoMapper" version="2.2.1" targetFramework="net40" />
<package id="FluentValidation" version="4.0.0.0" targetFramework="net40" /> <package id="FluentValidation" version="4.0.0.0" targetFramework="net40" />
<package id="Microsoft.AspNet.SignalR.Core" version="1.0.1" targetFramework="net40" />
<package id="Nancy" version="0.16.1" targetFramework="net40" /> <package id="Nancy" version="0.16.1" targetFramework="net40" />
<package id="Newtonsoft.Json" version="5.0.3" targetFramework="net40" /> <package id="Newtonsoft.Json" version="5.0.3" targetFramework="net40" />
<package id="NLog" version="2.0.1.2" targetFramework="net40" /> <package id="NLog" version="2.0.1.2" targetFramework="net40" />

View File

@ -8,7 +8,7 @@ namespace NzbDrone.Common
{ {
public abstract class ContainerBuilderBase public abstract class ContainerBuilderBase
{ {
protected TinyIoCContainer Container; protected readonly TinyIoCContainer Container;
private readonly List<Type> _loadedTypes; private readonly List<Type> _loadedTypes;
protected ContainerBuilderBase(params string[] assemblies) protected ContainerBuilderBase(params string[] assemblies)

View File

@ -140,7 +140,9 @@
<Compile Include="UdpProvider.cs" /> <Compile Include="UdpProvider.cs" />
</ItemGroup> </ItemGroup>
<ItemGroup> <ItemGroup>
<None Include="packages.config" /> <None Include="packages.config">
<SubType>Designer</SubType>
</None>
</ItemGroup> </ItemGroup>
<ItemGroup> <ItemGroup>
<COMReference Include="NetFwTypeLib"> <COMReference Include="NetFwTypeLib">

View File

@ -3,7 +3,9 @@ using System.Collections.Generic;
using System.IO; using System.IO;
using System.Linq; using System.Linq;
using Marr.Data; using Marr.Data;
using Moq;
using NUnit.Framework; using NUnit.Framework;
using NzbDrone.Common.Messaging;
using NzbDrone.Core.Datastore; using NzbDrone.Core.Datastore;
using NzbDrone.Core.Datastore.Migration.Framework; using NzbDrone.Core.Datastore.Migration.Framework;
@ -140,25 +142,27 @@ namespace NzbDrone.Core.Test.Framework
public class TestTestDatabase : ITestDatabase public class TestTestDatabase : ITestDatabase
{ {
private readonly IDatabase _dbConnection; private readonly IDatabase _dbConnection;
private IMessageAggregator _messageAggregator;
public TestTestDatabase(IDatabase dbConnection) public TestTestDatabase(IDatabase dbConnection)
{ {
_messageAggregator = new Mock<IMessageAggregator>().Object;
_dbConnection = dbConnection; _dbConnection = dbConnection;
} }
public void InsertMany<T>(IEnumerable<T> items) where T : ModelBase, new() public void InsertMany<T>(IEnumerable<T> items) where T : ModelBase, new()
{ {
new BasicRepository<T>(_dbConnection).InsertMany(items.ToList()); new BasicRepository<T>(_dbConnection, _messageAggregator).InsertMany(items.ToList());
} }
public T Insert<T>(T item) where T : ModelBase, new() public T Insert<T>(T item) where T : ModelBase, new()
{ {
return new BasicRepository<T>(_dbConnection).Insert(item); return new BasicRepository<T>(_dbConnection, _messageAggregator).Insert(item);
} }
public List<T> All<T>() where T : ModelBase, new() public List<T> All<T>() where T : ModelBase, new()
{ {
return new BasicRepository<T>(_dbConnection).All().ToList(); return new BasicRepository<T>(_dbConnection, _messageAggregator).All().ToList();
} }
public T Single<T>() where T : ModelBase, new() public T Single<T>() where T : ModelBase, new()
@ -168,12 +172,12 @@ namespace NzbDrone.Core.Test.Framework
public void Update<T>(T childModel) where T : ModelBase, new() public void Update<T>(T childModel) where T : ModelBase, new()
{ {
new BasicRepository<T>(_dbConnection).Update(childModel); new BasicRepository<T>(_dbConnection, _messageAggregator).Update(childModel);
} }
public void Delete<T>(T childModel) where T : ModelBase, new() public void Delete<T>(T childModel) where T : ModelBase, new()
{ {
new BasicRepository<T>(_dbConnection).Delete(childModel); new BasicRepository<T>(_dbConnection, _messageAggregator).Delete(childModel);
} }
} }
} }

View File

@ -1,5 +1,6 @@
using System.Data; using System.Data;
using System.Linq; using System.Linq;
using NzbDrone.Common.Messaging;
using NzbDrone.Core.Datastore; using NzbDrone.Core.Datastore;
namespace NzbDrone.Core.Configuration namespace NzbDrone.Core.Configuration
@ -12,8 +13,8 @@ namespace NzbDrone.Core.Configuration
public class ConfigRepository : BasicRepository<Config>, IConfigRepository public class ConfigRepository : BasicRepository<Config>, IConfigRepository
{ {
public ConfigRepository(IDatabase database) public ConfigRepository(IDatabase database, IMessageAggregator messageAggregator)
: base(database) : base(database, messageAggregator)
{ {
} }

View File

@ -1,4 +1,5 @@
using System.Linq; using System.Linq;
using NzbDrone.Common.Messaging;
using NzbDrone.Core.Datastore; using NzbDrone.Core.Datastore;
namespace NzbDrone.Core.DataAugmentation.Scene namespace NzbDrone.Core.DataAugmentation.Scene
@ -12,8 +13,8 @@ namespace NzbDrone.Core.DataAugmentation.Scene
public class SceneMappingRepository : BasicRepository<SceneMapping>, ISceneMappingRepository public class SceneMappingRepository : BasicRepository<SceneMapping>, ISceneMappingRepository
{ {
public SceneMappingRepository(IDatabase database) public SceneMappingRepository(IDatabase database, IMessageAggregator messageAggregator)
: base(database) : base(database, messageAggregator)
{ {
} }

View File

@ -5,6 +5,8 @@ using System.Linq;
using System.Linq.Expressions; using System.Linq.Expressions;
using Marr.Data; using Marr.Data;
using Marr.Data.QGen; using Marr.Data.QGen;
using NzbDrone.Common.Messaging;
using NzbDrone.Core.Datastore.Events;
using NzbDrone.Core.Tv; using NzbDrone.Core.Tv;
@ -34,14 +36,16 @@ namespace NzbDrone.Core.Datastore
public class BasicRepository<TModel> : IBasicRepository<TModel> where TModel : ModelBase, new() public class BasicRepository<TModel> : IBasicRepository<TModel> where TModel : ModelBase, new()
{ {
private readonly IMessageAggregator _messageAggregator;
//TODO: add assertion to make sure model properly mapped //TODO: add assertion to make sure model properly mapped
private readonly IDataMapper _dataMapper; private readonly IDataMapper _dataMapper;
public BasicRepository(IDatabase database) public BasicRepository(IDatabase database, IMessageAggregator messageAggregator)
{ {
_messageAggregator = messageAggregator;
_dataMapper = database.DataMapper; _dataMapper = database.DataMapper;
} }
@ -99,7 +103,9 @@ namespace NzbDrone.Core.Datastore
throw new InvalidOperationException("Can't insert model with existing ID"); throw new InvalidOperationException("Can't insert model with existing ID");
} }
var id = _dataMapper.Insert(model); _dataMapper.Insert(model);
_messageAggregator.PublishEvent(new ModelEvent<TModel>(model, ModelEvent<TModel>.RepositoryAction.Created));
return model; return model;
} }

View File

@ -0,0 +1,27 @@
using System;
using NzbDrone.Common.Messaging;
namespace NzbDrone.Core.Datastore.Events
{
public class ModelEvent<T> : IEvent where T : ModelBase
{
public T Model { get; set; }
public RepositoryAction Action { get; set; }
public ModelEvent(T model, RepositoryAction action)
{
Model = model;
Action = action;
}
public enum RepositoryAction
{
Created,
Updated,
Deleted
}
}
}

View File

@ -1,5 +1,6 @@
using System.Data; using System.Data;
using System.Linq; using System.Linq;
using NzbDrone.Common.Messaging;
using NzbDrone.Core.Datastore; using NzbDrone.Core.Datastore;
namespace NzbDrone.Core.ExternalNotification namespace NzbDrone.Core.ExternalNotification
@ -11,8 +12,8 @@ namespace NzbDrone.Core.ExternalNotification
public class ExternalNotificationRepository : BasicRepository<ExternalNotificationDefinition>, IExternalNotificationRepository public class ExternalNotificationRepository : BasicRepository<ExternalNotificationDefinition>, IExternalNotificationRepository
{ {
public ExternalNotificationRepository(IDatabase database) public ExternalNotificationRepository(IDatabase database, IMessageAggregator messageAggregator)
: base(database) : base(database, messageAggregator)
{ {
} }

View File

@ -1,6 +1,7 @@
using System; using System;
using System.Data; using System.Data;
using System.Linq; using System.Linq;
using NzbDrone.Common.Messaging;
using NzbDrone.Core.Datastore; using NzbDrone.Core.Datastore;
using NzbDrone.Core.Tv; using NzbDrone.Core.Tv;
@ -14,8 +15,8 @@ namespace NzbDrone.Core.History
public class HistoryRepository : BasicRepository<History>, IHistoryRepository public class HistoryRepository : BasicRepository<History>, IHistoryRepository
{ {
public HistoryRepository(IDatabase database) public HistoryRepository(IDatabase database, IMessageAggregator messageAggregator)
: base(database) : base(database, messageAggregator)
{ {
} }

View File

@ -1,5 +1,6 @@
using System; using System;
using System.Linq; using System.Linq;
using NzbDrone.Common.Messaging;
using NzbDrone.Core.Datastore; using NzbDrone.Core.Datastore;
namespace NzbDrone.Core.Indexers namespace NzbDrone.Core.Indexers
@ -12,8 +13,8 @@ namespace NzbDrone.Core.Indexers
public class IndexerRepository : BasicRepository<IndexerDefinition>, IIndexerRepository public class IndexerRepository : BasicRepository<IndexerDefinition>, IIndexerRepository
{ {
public IndexerRepository(IDatabase database) public IndexerRepository(IDatabase database, IMessageAggregator messageAggregator)
: base(database) : base(database, messageAggregator)
{ {
} }

View File

@ -1,6 +1,7 @@
using System; using System;
using System.Data; using System.Data;
using System.Linq; using System.Linq;
using NzbDrone.Common.Messaging;
using NzbDrone.Core.Datastore; using NzbDrone.Core.Datastore;
namespace NzbDrone.Core.Instrumentation namespace NzbDrone.Core.Instrumentation
@ -12,8 +13,8 @@ namespace NzbDrone.Core.Instrumentation
public class LogRepository : BasicRepository<Log>, ILogRepository public class LogRepository : BasicRepository<Log>, ILogRepository
{ {
public LogRepository(IDatabase database) public LogRepository(IDatabase database, IMessageAggregator messageAggregator)
: base(database) : base(database, messageAggregator)
{ {
} }

View File

@ -19,8 +19,8 @@ namespace NzbDrone.Core.Jobs
private readonly IEnumerable<IJob> _jobs; private readonly IEnumerable<IJob> _jobs;
private readonly Logger _logger; private readonly Logger _logger;
public JobRepository(IDatabase database, IEnumerable<IJob> jobs, Logger logger) public JobRepository(IDatabase database, IEnumerable<IJob> jobs, Logger logger, IMessageAggregator messageAggregator)
: base(database) : base(database, messageAggregator)
{ {
_jobs = jobs; _jobs = jobs;
_logger = logger; _logger = logger;

View File

@ -1,6 +1,7 @@
using System.Collections.Generic; using System.Collections.Generic;
using System.Data; using System.Data;
using System.Linq; using System.Linq;
using NzbDrone.Common.Messaging;
using NzbDrone.Core.Datastore; using NzbDrone.Core.Datastore;
namespace NzbDrone.Core.MediaFiles namespace NzbDrone.Core.MediaFiles
@ -15,8 +16,8 @@ namespace NzbDrone.Core.MediaFiles
public class MediaFileRepository : BasicRepository<EpisodeFile>, IMediaFileRepository public class MediaFileRepository : BasicRepository<EpisodeFile>, IMediaFileRepository
{ {
public MediaFileRepository(IDatabase database) public MediaFileRepository(IDatabase database, IMessageAggregator messageAggregator)
: base(database) : base(database, messageAggregator)
{ {
} }

View File

@ -195,6 +195,7 @@
<Compile Include="Datastore\Database.cs" /> <Compile Include="Datastore\Database.cs" />
<Compile Include="Datastore\DbFactory.cs" /> <Compile Include="Datastore\DbFactory.cs" />
<Compile Include="Datastore\Converters\EnumIntConverter.cs" /> <Compile Include="Datastore\Converters\EnumIntConverter.cs" />
<Compile Include="Datastore\Events\ModelEvent.cs" />
<Compile Include="Datastore\IEmbeddedDocument.cs" /> <Compile Include="Datastore\IEmbeddedDocument.cs" />
<Compile Include="Datastore\IReadModels.cs" /> <Compile Include="Datastore\IReadModels.cs" />
<Compile Include="Datastore\IWriteModels.cs" /> <Compile Include="Datastore\IWriteModels.cs" />

View File

@ -1,4 +1,5 @@
using NzbDrone.Core.Datastore; using NzbDrone.Common.Messaging;
using NzbDrone.Core.Datastore;
namespace NzbDrone.Core.Qualities namespace NzbDrone.Core.Qualities
{ {
@ -9,8 +10,8 @@ namespace NzbDrone.Core.Qualities
public class QualityProfileRepository : BasicRepository<QualityProfile>, IQualityProfileRepository public class QualityProfileRepository : BasicRepository<QualityProfile>, IQualityProfileRepository
{ {
public QualityProfileRepository(IDatabase database) public QualityProfileRepository(IDatabase database, IMessageAggregator messageAggregator)
: base(database) : base(database, messageAggregator)
{ {
} }
} }

View File

@ -1,5 +1,6 @@
using System.Data; using System.Data;
using System.Linq; using System.Linq;
using NzbDrone.Common.Messaging;
using NzbDrone.Core.Datastore; using NzbDrone.Core.Datastore;
namespace NzbDrone.Core.Qualities namespace NzbDrone.Core.Qualities
@ -11,8 +12,8 @@ namespace NzbDrone.Core.Qualities
public class QualitySizeRepository : BasicRepository<QualitySize>, IQualitySizeRepository public class QualitySizeRepository : BasicRepository<QualitySize>, IQualitySizeRepository
{ {
public QualitySizeRepository(IDatabase database) public QualitySizeRepository(IDatabase database, IMessageAggregator messageAggregator)
: base(database) : base(database, messageAggregator)
{ {
} }

View File

@ -5,6 +5,7 @@ using System.Data;
using System.Linq; using System.Linq;
using Marr.Data; using Marr.Data;
using Marr.Data.QGen; using Marr.Data.QGen;
using NzbDrone.Common.Messaging;
using NzbDrone.Core.Datastore; using NzbDrone.Core.Datastore;
using NzbDrone.Core.Model; using NzbDrone.Core.Model;
@ -31,8 +32,8 @@ namespace NzbDrone.Core.Tv
{ {
private readonly IDataMapper _dataMapper; private readonly IDataMapper _dataMapper;
public EpisodeRepository(IDatabase database) public EpisodeRepository(IDatabase database, IMessageAggregator messageAggregator)
: base(database) : base(database, messageAggregator)
{ {
_dataMapper = database.DataMapper; _dataMapper = database.DataMapper;
} }

View File

@ -1,6 +1,6 @@
using System.Collections.Generic; using System.Collections.Generic;
using System.Data;
using System.Linq; using System.Linq;
using NzbDrone.Common.Messaging;
using NzbDrone.Core.Datastore; using NzbDrone.Core.Datastore;
@ -16,10 +16,9 @@ namespace NzbDrone.Core.Tv
public class SeasonRepository : BasicRepository<Season>, ISeasonRepository public class SeasonRepository : BasicRepository<Season>, ISeasonRepository
{ {
private readonly IDbConnection _database;
public SeasonRepository(IDatabase database) public SeasonRepository(IDatabase database, IMessageAggregator messageAggregator)
: base(database) : base(database, messageAggregator)
{ {
} }

View File

@ -1,6 +1,7 @@
using System; using System;
using System.Collections.Generic; using System.Collections.Generic;
using System.Linq; using System.Linq;
using NzbDrone.Common.Messaging;
using NzbDrone.Core.Datastore; using NzbDrone.Core.Datastore;
namespace NzbDrone.Core.Tv namespace NzbDrone.Core.Tv
@ -18,8 +19,8 @@ namespace NzbDrone.Core.Tv
public class SeriesRepository : BasicRepository<Series>, ISeriesRepository public class SeriesRepository : BasicRepository<Series>, ISeriesRepository
{ {
public SeriesRepository(IDatabase database) public SeriesRepository(IDatabase database, IMessageAggregator messageAggregator)
: base(database) : base(database, messageAggregator)
{ {
} }

View File

@ -3,6 +3,7 @@ using FluentMigrator.Runner;
using NLog; using NLog;
using Nancy.Bootstrapper; using Nancy.Bootstrapper;
using NzbDrone.Api; using NzbDrone.Api;
using NzbDrone.Api.SignalR;
using NzbDrone.Common; using NzbDrone.Common;
using NzbDrone.Common.Messaging; using NzbDrone.Common.Messaging;
using NzbDrone.Core.Datastore; using NzbDrone.Core.Datastore;
@ -37,6 +38,8 @@ namespace NzbDrone
Container.Register(typeof(IBasicRepository<RootFolder>), typeof(BasicRepository<RootFolder>)).AsMultiInstance(); Container.Register(typeof(IBasicRepository<RootFolder>), typeof(BasicRepository<RootFolder>)).AsMultiInstance();
Container.Register(typeof(IBasicRepository<NamingConfig>), typeof(BasicRepository<NamingConfig>)).AsMultiInstance(); Container.Register(typeof(IBasicRepository<NamingConfig>), typeof(BasicRepository<NamingConfig>)).AsMultiInstance();
AutoRegisterImplementations<NzbDronePersistentConnection>();
InitDatabase(); InitDatabase();
ReportingService.RestProvider = Container.Resolve<RestProvider>(); ReportingService.RestProvider = Container.Resolve<RestProvider>();

View File

@ -1,4 +1,4 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<Project ToolsVersion="4.0" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003"> <Project ToolsVersion="4.0" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<PropertyGroup> <PropertyGroup>
<Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration> <Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
@ -91,6 +91,12 @@
<SpecificVersion>False</SpecificVersion> <SpecificVersion>False</SpecificVersion>
<HintPath>..\packages\FluentMigrator.1.0.6.0\tools\FluentMigrator.Runner.dll</HintPath> <HintPath>..\packages\FluentMigrator.1.0.6.0\tools\FluentMigrator.Runner.dll</HintPath>
</Reference> </Reference>
<Reference Include="Microsoft.AspNet.SignalR.Core">
<HintPath>..\packages\Microsoft.AspNet.SignalR.Core.1.0.1\lib\net40\Microsoft.AspNet.SignalR.Core.dll</HintPath>
</Reference>
<Reference Include="Microsoft.AspNet.SignalR.Owin">
<HintPath>..\packages\Microsoft.AspNet.SignalR.Owin.1.0.1\lib\net40\Microsoft.AspNet.SignalR.Owin.dll</HintPath>
</Reference>
<Reference Include="Microsoft.CSharp" /> <Reference Include="Microsoft.CSharp" />
<Reference Include="Microsoft.Owin.Host.HttpListener"> <Reference Include="Microsoft.Owin.Host.HttpListener">
<HintPath>..\packages\Microsoft.Owin.Host.HttpListener.0.21.0-pre\lib\net40\Microsoft.Owin.Host.HttpListener.dll</HintPath> <HintPath>..\packages\Microsoft.Owin.Host.HttpListener.0.21.0-pre\lib\net40\Microsoft.Owin.Host.HttpListener.dll</HintPath>
@ -106,6 +112,10 @@
<SpecificVersion>False</SpecificVersion> <SpecificVersion>False</SpecificVersion>
<HintPath>..\packages\Nancy.Owin.0.16.1\lib\net40\Nancy.Owin.dll</HintPath> <HintPath>..\packages\Nancy.Owin.0.16.1\lib\net40\Nancy.Owin.dll</HintPath>
</Reference> </Reference>
<Reference Include="Newtonsoft.Json, Version=4.5.0.0, Culture=neutral, PublicKeyToken=30ad4fe6b2a6aeed, processorArchitecture=MSIL">
<SpecificVersion>False</SpecificVersion>
<HintPath>..\packages\Newtonsoft.Json.4.5.11\lib\net35\Newtonsoft.Json.dll</HintPath>
</Reference>
<Reference Include="NLog, Version=2.0.1.0, Culture=neutral, PublicKeyToken=5120e14c03d0593c, processorArchitecture=MSIL"> <Reference Include="NLog, Version=2.0.1.0, Culture=neutral, PublicKeyToken=5120e14c03d0593c, processorArchitecture=MSIL">
<SpecificVersion>False</SpecificVersion> <SpecificVersion>False</SpecificVersion>
<HintPath>..\packages\NLog.2.0.1.2\lib\net40\NLog.dll</HintPath> <HintPath>..\packages\NLog.2.0.1.2\lib\net40\NLog.dll</HintPath>

View File

@ -4,6 +4,7 @@ namespace NzbDrone.Owin.MiddleWare
{ {
public interface IOwinMiddleWare public interface IOwinMiddleWare
{ {
int Order { get; }
void Attach(IAppBuilder appBuilder); void Attach(IAppBuilder appBuilder);
} }
} }

View File

@ -16,6 +16,8 @@ namespace NzbDrone.Owin.MiddleWare
_nancyBootstrapper = nancyBootstrapper; _nancyBootstrapper = nancyBootstrapper;
} }
public int Order { get { return 1; } }
public void Attach(IAppBuilder appBuilder) public void Attach(IAppBuilder appBuilder)
{ {
var nancyOwinHost = new NancyOwinHost(null, _nancyBootstrapper); var nancyOwinHost = new NancyOwinHost(null, _nancyBootstrapper);

View File

@ -1,26 +1,31 @@
using System;
using System.Collections.Generic; using System.Collections.Generic;
using System.Threading.Tasks; using Microsoft.AspNet.SignalR;
using Nancy.Bootstrapper; using NzbDrone.Api.SignalR;
using Nancy.Owin;
using Owin; using Owin;
using TinyIoC;
namespace NzbDrone.Owin.MiddleWare namespace NzbDrone.Owin.MiddleWare
{ {
public class SignalRMiddleWare : IOwinMiddleWare public class SignalRMiddleWare : IOwinMiddleWare
{ {
private readonly INancyBootstrapper _nancyBootstrapper; private readonly IEnumerable<NzbDronePersistentConnection> _persistentConnections;
public SignalRMiddleWare(INancyBootstrapper nancyBootstrapper) public int Order { get { return 0; } }
public SignalRMiddleWare(IEnumerable<NzbDronePersistentConnection> persistentConnections, TinyIoCContainer container)
{ {
_nancyBootstrapper = nancyBootstrapper; _persistentConnections = persistentConnections;
SignalrDependencyResolver.Register(container);
} }
public void Attach(IAppBuilder appBuilder) public void Attach(IAppBuilder appBuilder)
{ {
return; foreach (var nzbDronePersistentConnection in _persistentConnections)
var nancyOwinHost = new NancyOwinHost(null, _nancyBootstrapper); {
appBuilder.Use((Func<Func<IDictionary<string, object>, Task>, Func<IDictionary<string, object>, Task>>)(next => (Func<IDictionary<string, object>, Task>)nancyOwinHost.Invoke), new object[0]); appBuilder.MapConnection("signalr/series", nzbDronePersistentConnection.GetType(), new ConnectionConfiguration { EnableCrossDomain = true });
}
} }
} }
} }

View File

@ -8,6 +8,7 @@ using Nancy.Owin;
using NzbDrone.Common; using NzbDrone.Common;
using NzbDrone.Owin.MiddleWare; using NzbDrone.Owin.MiddleWare;
using Owin; using Owin;
using System.Linq;
namespace NzbDrone.Owin namespace NzbDrone.Owin
{ {
@ -27,13 +28,20 @@ namespace NzbDrone.Owin
public void StartServer() public void StartServer()
{ {
_host = WebApplication.Start(AppUrl, BuildApp); var options = new StartOptions
{
App = GetType().AssemblyQualifiedName,
Port = _configFileProvider.Port
};
_host = WebApplication.Start(options, BuildApp);
} }
private void BuildApp(IAppBuilder appBuilder) private void BuildApp(IAppBuilder appBuilder)
{ {
foreach (var middleWare in _owinMiddleWares) foreach (var middleWare in _owinMiddleWares.OrderBy(c => c.Order))
{ {
_logger.Debug("Attaching {0} to host", middleWare.GetType().Name);
middleWare.Attach(appBuilder); middleWare.Attach(appBuilder);
} }
} }

View File

@ -1,10 +1,13 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<packages> <packages>
<package id="FluentMigrator" version="1.0.6.0" targetFramework="net40" /> <package id="FluentMigrator" version="1.0.6.0" targetFramework="net40" />
<package id="Microsoft.AspNet.SignalR.Core" version="1.0.1" targetFramework="net40" />
<package id="Microsoft.AspNet.SignalR.Owin" version="1.0.1" targetFramework="net40" />
<package id="Microsoft.Owin.Host.HttpListener" version="0.21.0-pre" targetFramework="net40" /> <package id="Microsoft.Owin.Host.HttpListener" version="0.21.0-pre" targetFramework="net40" />
<package id="Microsoft.Owin.Hosting" version="0.21.0-pre" targetFramework="net40" /> <package id="Microsoft.Owin.Hosting" version="0.21.0-pre" targetFramework="net40" />
<package id="Nancy" version="0.16.1" targetFramework="net40" /> <package id="Nancy" version="0.16.1" targetFramework="net40" />
<package id="Nancy.Owin" version="0.16.1" targetFramework="net40" /> <package id="Nancy.Owin" version="0.16.1" targetFramework="net40" />
<package id="Newtonsoft.Json" version="4.5.11" targetFramework="net40" />
<package id="NLog" version="2.0.1.2" targetFramework="net40" /> <package id="NLog" version="2.0.1.2" targetFramework="net40" />
<package id="NLog.Config" version="2.0.1.2" targetFramework="net40" /> <package id="NLog.Config" version="2.0.1.2" targetFramework="net40" />
<package id="NLog.Schema" version="2.0.1.2" targetFramework="net40" /> <package id="NLog.Schema" version="2.0.1.2" targetFramework="net40" />

View File

@ -52,17 +52,6 @@
</div> </div>
</div> </div>
</div> </div>
<!--<div style="background: red">
awdawdawdawdawdawdadaw
<br/>
<br/>
<br/>
<br/>
<br/>
<br/>
</div>-->
<div class="page"> <div class="page">
<div class="page-container"> <div class="page-container">
<div class="container"> <div class="container">
@ -85,12 +74,15 @@
</footer> </footer>
</body> </body>
<script src="/JsLibraries/jquery.js"></script> <script src="/JsLibraries/jquery.js"></script>
<script src="/JsLibraries/messenger.js"></script>
<script src="/Instrumentation/StringFormat.js"></script>
<script src="/Instrumentation/ErrorHandler.js"></script>
<script src="/JsLibraries/jquery.signalR.js"></script>
<script src="/JsLibraries/bootstrap.js"></script> <script src="/JsLibraries/bootstrap.js"></script>
<script src="/JsLibraries/bootstrap.slider.js"></script> <script src="/JsLibraries/bootstrap.slider.js"></script>
<script src="/JsLibraries/underscore.js"></script> <script src="/JsLibraries/underscore.js"></script>
<script src="/JsLibraries/handlebars.runtime.js"></script> <script src="/JsLibraries/handlebars.runtime.js"></script>
<script src="/JsLibraries/backbone.js"></script> <script src="/JsLibraries/backbone.js"></script>
<script src="/JsLibraries/messenger.js"></script>
<script src="/JsLibraries/backbone.modelbinder.js"></script> <script src="/JsLibraries/backbone.modelbinder.js"></script>
<script src="/JsLibraries/backbone.deep.model.js"></script> <script src="/JsLibraries/backbone.deep.model.js"></script>
<script src="/JsLibraries/backbone.mutators.js"></script> <script src="/JsLibraries/backbone.mutators.js"></script>
@ -110,9 +102,6 @@
<script src="/templates.js"></script> <script src="/templates.js"></script>
<script src="/Instrumentation/StringFormat.js"></script>
<script src="/Mixins/backbone.marionette.templates.js"></script> <script src="/Mixins/backbone.marionette.templates.js"></script>
<script src="/Mixins/backbone.ajax.js"></script> <script src="/Mixins/backbone.ajax.js"></script>
<script src="/Mixins/tablesorter.extensions.js"></script> <script src="/Mixins/tablesorter.extensions.js"></script>
@ -120,6 +109,7 @@
<script src="/Mixins/backbone.modelbinder.mixin.js"></script> <script src="/Mixins/backbone.modelbinder.mixin.js"></script>
<script src="/Mixins/backbone.backgrid.mixin.js"></script> <script src="/Mixins/backbone.backgrid.mixin.js"></script>
<script src="/Mixins/handlebars.mixin.js"></script> <script src="/Mixins/handlebars.mixin.js"></script>
<script src="/Mixins/backbone.signalr.mixin.js"></script>
<script data-main="/app" src="/JsLibraries/require.js"></script> <script data-main="/app" src="/JsLibraries/require.js"></script>
<script src="/Routing.js"></script> <script src="/Routing.js"></script>

View File

@ -1,5 +1,5 @@
"use strict"; "use strict";
define(function () { (function () {
/* var model = new NzbDrone.Shared.NotificationModel(); /* var model = new NzbDrone.Shared.NotificationModel();
model.set('title','test notification'); model.set('title','test notification');
@ -12,9 +12,6 @@ define(function () {
window.Messenger().post(message); window.Messenger().post(message);
}; };
var self = this;
window.onerror = function (msg, url, line) { window.onerror = function (msg, url, line) {
try { try {
@ -69,5 +66,5 @@ define(function () {
return false; return false;
}); });
}); })();

View File

@ -354,4 +354,4 @@
}); });
}(jQuery, _, Backbone, Backgrid)); }(jQuery, _, Backbone, Backgrid, lunr));

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,36 @@
"use strict";
(function ($) {
var connection = $.connection('/signalr/series');
var _getStatus = function (status) {
switch (status) {
case 0:
return 'connecting';
case 1:
return 'connected';
case 2:
return 'reconnecting';
case 4:
return 'disconnected';
default:
throw 'invalid status ' + status;
}
};
connection.stateChanged(function (change) {
console.log('signalR [{0}]'.format(_getStatus(change.newState)));
});
connection.received(function (data) {
console.log(data);
});
connection.error(function (error) {
console.warn(error);
});
connection.start();
})(jQuery);

View File

@ -26,7 +26,7 @@ require.config({
} }
}); });
define('app', ['Instrumentation/ErrorHandler'], function () { define('app', function () {
window.NzbDrone = new Backbone.Marionette.Application(); window.NzbDrone = new Backbone.Marionette.Application();
window.NzbDrone.Config = {}; window.NzbDrone.Config = {};