mirror of
https://github.com/lidarr/lidarr.git
synced 2025-07-06 21:12:15 -07:00
Fixed: Multiple SignalR Improvements
Support for serverSentEvents, connection optimizations Co-Authored-By: taloth <taloth@users.noreply.github.com>
This commit is contained in:
parent
184ab745ae
commit
3ebbf6ff83
5 changed files with 53 additions and 7 deletions
|
@ -84,7 +84,7 @@ class SignalRConnector extends Component {
|
||||||
constructor(props, context) {
|
constructor(props, context) {
|
||||||
super(props, context);
|
super(props, context);
|
||||||
|
|
||||||
this.signalRconnectionOptions = { transport: ['webSockets', 'longPolling'] };
|
this.signalRconnectionOptions = { transport: ['webSockets', 'serverSentEvents', 'longPolling'] };
|
||||||
this.signalRconnection = null;
|
this.signalRconnection = null;
|
||||||
this.retryInterval = 1;
|
this.retryInterval = 1;
|
||||||
this.retryTimeoutId = null;
|
this.retryTimeoutId = null;
|
||||||
|
|
|
@ -25,6 +25,8 @@ namespace Lidarr.Http
|
||||||
|
|
||||||
public void Handle(ModelEvent<TModel> message)
|
public void Handle(ModelEvent<TModel> message)
|
||||||
{
|
{
|
||||||
|
if (!_signalRBroadcaster.IsConnected) return;
|
||||||
|
|
||||||
if (message.Action == ModelAction.Deleted || message.Action == ModelAction.Sync)
|
if (message.Action == ModelAction.Deleted || message.Action == ModelAction.Sync)
|
||||||
{
|
{
|
||||||
BroadcastResourceChange(message.Action);
|
BroadcastResourceChange(message.Action);
|
||||||
|
@ -35,6 +37,8 @@ namespace Lidarr.Http
|
||||||
|
|
||||||
protected void BroadcastResourceChange(ModelAction action, int id)
|
protected void BroadcastResourceChange(ModelAction action, int id)
|
||||||
{
|
{
|
||||||
|
if (!_signalRBroadcaster.IsConnected) return;
|
||||||
|
|
||||||
if (action == ModelAction.Deleted)
|
if (action == ModelAction.Deleted)
|
||||||
{
|
{
|
||||||
BroadcastResourceChange(action, new TResource { Id = id });
|
BroadcastResourceChange(action, new TResource { Id = id });
|
||||||
|
@ -48,6 +52,8 @@ namespace Lidarr.Http
|
||||||
|
|
||||||
protected void BroadcastResourceChange(ModelAction action, TResource resource)
|
protected void BroadcastResourceChange(ModelAction action, TResource resource)
|
||||||
{
|
{
|
||||||
|
if (!_signalRBroadcaster.IsConnected) return;
|
||||||
|
|
||||||
if (GetType().Namespace.Contains("V1"))
|
if (GetType().Namespace.Contains("V1"))
|
||||||
{
|
{
|
||||||
var signalRMessage = new SignalRMessage
|
var signalRMessage = new SignalRMessage
|
||||||
|
@ -64,6 +70,8 @@ namespace Lidarr.Http
|
||||||
|
|
||||||
protected void BroadcastResourceChange(ModelAction action)
|
protected void BroadcastResourceChange(ModelAction action)
|
||||||
{
|
{
|
||||||
|
if (!_signalRBroadcaster.IsConnected) return;
|
||||||
|
|
||||||
if (GetType().Namespace.Contains("V1"))
|
if (GetType().Namespace.Contains("V1"))
|
||||||
{
|
{
|
||||||
var signalRMessage = new SignalRMessage
|
var signalRMessage = new SignalRMessage
|
||||||
|
|
|
@ -16,9 +16,14 @@ namespace NzbDrone.Host.Owin.MiddleWare
|
||||||
SignalRDependencyResolver.Register(container);
|
SignalRDependencyResolver.Register(container);
|
||||||
SignalRJsonSerializer.Register();
|
SignalRJsonSerializer.Register();
|
||||||
|
|
||||||
// Half the default time (110s) to get under nginx's default 60 proxy_read_timeout
|
// Note there are some important timeouts involved here:
|
||||||
GlobalHost.Configuration.ConnectionTimeout = TimeSpan.FromSeconds(55);
|
// nginx has a default 60 sec proxy_read_timeout, this means the connection will be terminated if the server doesn't send anything within that time.
|
||||||
GlobalHost.Configuration.DisconnectTimeout = TimeSpan.FromMinutes(3);
|
// Previously we lowered the ConnectionTimeout from 110s to 55s to remedy that, however all we should've done is set an appropriate KeepAlive.
|
||||||
|
// By default KeepAlive is 1/3rd of the DisconnectTimeout, which we set incredibly high 5 years ago, resulting in KeepAlive being 1 minute.
|
||||||
|
// So when adjusting these values in the future, please keep that all in mind.
|
||||||
|
GlobalHost.Configuration.ConnectionTimeout = TimeSpan.FromSeconds(110);
|
||||||
|
GlobalHost.Configuration.DisconnectTimeout = TimeSpan.FromSeconds(180);
|
||||||
|
GlobalHost.Configuration.KeepAlive = TimeSpan.FromSeconds(30);
|
||||||
}
|
}
|
||||||
|
|
||||||
public void Attach(IAppBuilder appBuilder)
|
public void Attach(IAppBuilder appBuilder)
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Threading.Tasks;
|
using System.Threading.Tasks;
|
||||||
using Microsoft.AspNet.SignalR;
|
using Microsoft.AspNet.SignalR;
|
||||||
using Microsoft.AspNet.SignalR.Infrastructure;
|
using Microsoft.AspNet.SignalR.Infrastructure;
|
||||||
|
@ -12,6 +12,7 @@ namespace NzbDrone.SignalR
|
||||||
{
|
{
|
||||||
public interface IBroadcastSignalRMessage
|
public interface IBroadcastSignalRMessage
|
||||||
{
|
{
|
||||||
|
bool IsConnected { get; }
|
||||||
void BroadcastMessage(SignalRMessage message);
|
void BroadcastMessage(SignalRMessage message);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -21,6 +22,7 @@ namespace NzbDrone.SignalR
|
||||||
|
|
||||||
private static string API_KEY;
|
private static string API_KEY;
|
||||||
private readonly Dictionary<string, string> _messageHistory;
|
private readonly Dictionary<string, string> _messageHistory;
|
||||||
|
private HashSet<string> _connections = new HashSet<string>();
|
||||||
|
|
||||||
public NzbDronePersistentConnection(IConfigFileProvider configFileProvider)
|
public NzbDronePersistentConnection(IConfigFileProvider configFileProvider)
|
||||||
{
|
{
|
||||||
|
@ -28,6 +30,16 @@ namespace NzbDrone.SignalR
|
||||||
_messageHistory = new Dictionary<string, string>();
|
_messageHistory = new Dictionary<string, string>();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public bool IsConnected
|
||||||
|
{
|
||||||
|
get
|
||||||
|
{
|
||||||
|
lock (_connections)
|
||||||
|
{
|
||||||
|
return _connections.Count != 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
public void BroadcastMessage(SignalRMessage message)
|
public void BroadcastMessage(SignalRMessage message)
|
||||||
{
|
{
|
||||||
|
@ -59,14 +71,34 @@ namespace NzbDrone.SignalR
|
||||||
|
|
||||||
protected override Task OnConnected(IRequest request, string connectionId)
|
protected override Task OnConnected(IRequest request, string connectionId)
|
||||||
{
|
{
|
||||||
|
lock (_connections)
|
||||||
|
{
|
||||||
|
_connections.Add(connectionId);
|
||||||
|
}
|
||||||
|
|
||||||
return SendVersion(connectionId);
|
return SendVersion(connectionId);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected override Task OnReconnected(IRequest request, string connectionId)
|
protected override Task OnReconnected(IRequest request, string connectionId)
|
||||||
{
|
{
|
||||||
|
lock (_connections)
|
||||||
|
{
|
||||||
|
_connections.Add(connectionId);
|
||||||
|
}
|
||||||
|
|
||||||
return SendVersion(connectionId);
|
return SendVersion(connectionId);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
protected override Task OnDisconnected(IRequest request, string connectionId, bool stopCalled)
|
||||||
|
{
|
||||||
|
lock (_connections)
|
||||||
|
{
|
||||||
|
_connections.Remove(connectionId);
|
||||||
|
}
|
||||||
|
|
||||||
|
return base.OnDisconnected(request, connectionId, stopCalled);
|
||||||
|
}
|
||||||
|
|
||||||
private Task SendVersion(string connectionId)
|
private Task SendVersion(string connectionId)
|
||||||
{
|
{
|
||||||
return Context.Connection.Send(connectionId, new SignalRMessage
|
return Context.Connection.Send(connectionId, new SignalRMessage
|
||||||
|
|
|
@ -13,6 +13,7 @@ namespace NzbDrone.SignalR
|
||||||
{
|
{
|
||||||
_serializerSettings = Json.GetSerializerSettings();
|
_serializerSettings = Json.GetSerializerSettings();
|
||||||
_serializerSettings.ContractResolver = new SignalRContractResolver();
|
_serializerSettings.ContractResolver = new SignalRContractResolver();
|
||||||
|
_serializerSettings.Formatting = Formatting.None; // ServerSentEvents doesn't like newlines
|
||||||
|
|
||||||
_serializer = JsonSerializer.Create(_serializerSettings);
|
_serializer = JsonSerializer.Create(_serializerSettings);
|
||||||
|
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue