diff --git a/src/NzbDrone.Common/EnvironmentInfo/OsInfo.cs b/src/NzbDrone.Common/EnvironmentInfo/OsInfo.cs
index cad3d3002..abe4070c6 100644
--- a/src/NzbDrone.Common/EnvironmentInfo/OsInfo.cs
+++ b/src/NzbDrone.Common/EnvironmentInfo/OsInfo.cs
@@ -82,6 +82,9 @@ namespace NzbDrone.Common.EnvironmentInfo
Name = Os.ToString();
FullName = Name;
}
+
+ Environment.SetEnvironmentVariable("OS_NAME", Name);
+ Environment.SetEnvironmentVariable("OS_VERSION", Version);
}
}
diff --git a/src/NzbDrone.Common/Instrumentation/NzbDroneLogger.cs b/src/NzbDrone.Common/Instrumentation/NzbDroneLogger.cs
index 19bf34157..55a7071ae 100644
--- a/src/NzbDrone.Common/Instrumentation/NzbDroneLogger.cs
+++ b/src/NzbDrone.Common/Instrumentation/NzbDroneLogger.cs
@@ -7,6 +7,7 @@ using NLog.Config;
using NLog.Targets;
using NzbDrone.Common.EnvironmentInfo;
using NzbDrone.Common.Extensions;
+using NzbDrone.Common.Instrumentation.Sentry;
namespace NzbDrone.Common.Instrumentation
{
@@ -38,6 +39,8 @@ namespace NzbDrone.Common.Instrumentation
RegisterDebugger();
}
+ RegisterSentry(updateApp);
+
if (updateApp)
{
RegisterUpdateFile(appFolderInfo);
@@ -69,6 +72,35 @@ namespace NzbDrone.Common.Instrumentation
LogManager.Configuration.LoggingRules.Add(loggingRule);
}
+ private static void RegisterSentry(bool updateClient)
+ {
+ string dsn;
+
+ if (updateClient)
+ {
+ dsn = RuntimeInfo.IsProduction
+ ? "https://b85aa82c65b84b0e99e3b7c281438357:392b5bc007974147a922c5d841c47cf9@sentry.sonarr.tv/11"
+ : "https://6168f0946aba4e60ac23e469ac08eac5:bd59e8454ccc454ea27a90cff1f814ca@sentry.sonarr.tv/9";
+
+ }
+ else
+ {
+ dsn = RuntimeInfo.IsProduction
+ ? "https://fed3f47e8bea4527831e96edfa02d495:8ed11e4878614d8e87b1e1b15d890dc9@sentry.sonarr.tv/8"
+ : "https://4ee3580e01d8407c96a7430fbc953512:5f2d07227a0b4fde99dea07041a3ff93@sentry.sonarr.tv/10";
+ }
+
+ var target = new SentryTarget(dsn)
+ {
+ Name = "sentryTarget",
+ Layout = "${message}"
+ };
+
+ var loggingRule = new LoggingRule("*", updateClient ? LogLevel.Trace : LogLevel.Error, target);
+ LogManager.Configuration.AddTarget("logentries", target);
+ LogManager.Configuration.LoggingRules.Add(loggingRule);
+ }
+
private static void RegisterDebugger()
{
DebuggerTarget target = new DebuggerTarget();
diff --git a/src/NzbDrone.Common/Instrumentation/Sentry/SentryTarget.cs b/src/NzbDrone.Common/Instrumentation/Sentry/SentryTarget.cs
new file mode 100644
index 000000000..8d236ddbd
--- /dev/null
+++ b/src/NzbDrone.Common/Instrumentation/Sentry/SentryTarget.cs
@@ -0,0 +1,89 @@
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Threading;
+using NLog;
+using NLog.Common;
+using NLog.Targets;
+using NzbDrone.Common.EnvironmentInfo;
+using SharpRaven;
+using SharpRaven.Data;
+
+namespace NzbDrone.Common.Instrumentation.Sentry
+{
+
+ public class SentryUserFactory : ISentryUserFactory
+ {
+ public SentryUser Create()
+ {
+ return new SentryUser((string)null);
+ }
+ }
+
+ [Target("Sentry")]
+ public class SentryTarget : TargetWithLayout
+ {
+ private readonly RavenClient _client;
+
+ ///
+ /// Map of NLog log levels to Raven/Sentry log levels
+ ///
+ private static readonly IDictionary LoggingLevelMap = new Dictionary
+ {
+ {LogLevel.Debug, ErrorLevel.Debug},
+ {LogLevel.Error, ErrorLevel.Error},
+ {LogLevel.Fatal, ErrorLevel.Fatal},
+ {LogLevel.Info, ErrorLevel.Info},
+ {LogLevel.Trace, ErrorLevel.Debug},
+ {LogLevel.Warn, ErrorLevel.Warning},
+ };
+
+ public SentryTarget(string dsn)
+ {
+ _client = new RavenClient(new Dsn(dsn), new JsonPacketFactory(), new SentryRequestFactory(), new SentryUserFactory())
+ {
+ Compression = true,
+ Environment = RuntimeInfo.IsProduction ? "production" : "development",
+ Release = BuildInfo.Version.ToString(),
+ };
+
+ _client.Tags.Add("osfamily", OsInfo.Os.ToString());
+ _client.Tags.Add("runtime", PlatformInfo.Platform.ToString().ToLower());
+ _client.Tags.Add("culture", Thread.CurrentThread.CurrentCulture.Name);
+ }
+
+ protected override void Write(LogEventInfo logEvent)
+ {
+ try
+ {
+ // don't report non-critical events without exceptions
+ if (logEvent.Exception == null && logEvent.Level < LogLevel.Warn)
+ {
+ return;
+ }
+
+
+ var extras = logEvent.Properties.ToDictionary(x => x.Key.ToString(), x => x.Value.ToString());
+ _client.Logger = logEvent.LoggerName;
+
+ var sentryMessage = new SentryMessage(Layout.Render(logEvent));
+ var sentryEvent = new SentryEvent(logEvent.Exception)
+ {
+ Level = LoggingLevelMap[logEvent.Level],
+ Message = sentryMessage,
+ Extra = extras,
+ };
+
+ sentryEvent.Tags.Add("os_name", Environment.GetEnvironmentVariable("OS_NAME"));
+ sentryEvent.Tags.Add("os_version", Environment.GetEnvironmentVariable("OS_VERSION"));
+ sentryEvent.Tags.Add("runtime_version", Environment.GetEnvironmentVariable("RUNTIME_VERSION"));
+
+ _client.Capture(sentryEvent);
+ }
+ catch (Exception e)
+ {
+ InternalLogger.Error("Unable to send Sentry request: {0}", e.Message);
+ }
+ }
+ }
+}
diff --git a/src/NzbDrone.Common/NzbDrone.Common.csproj b/src/NzbDrone.Common/NzbDrone.Common.csproj
index 766a7c669..c8f98dd84 100644
--- a/src/NzbDrone.Common/NzbDrone.Common.csproj
+++ b/src/NzbDrone.Common/NzbDrone.Common.csproj
@@ -51,6 +51,10 @@
..\packages\DotNet4.SocksProxy.1.3.2.0\lib\net40\Org.Mentalis.dll
True
+
+ ..\packages\SharpRaven.2.1.0\lib\net40\SharpRaven.dll
+ True
+
..\packages\DotNet4.SocksProxy.1.3.2.0\lib\net40\SocksWebProxy.dll
True
@@ -178,6 +182,7 @@
+
diff --git a/src/NzbDrone.Common/packages.config b/src/NzbDrone.Common/packages.config
index 359d382e8..91e117688 100644
--- a/src/NzbDrone.Common/packages.config
+++ b/src/NzbDrone.Common/packages.config
@@ -4,4 +4,5 @@
+
\ No newline at end of file
diff --git a/src/NzbDrone.Mono/EnvironmentInfo/MonoPlatformInfo.cs b/src/NzbDrone.Mono/EnvironmentInfo/MonoPlatformInfo.cs
index 32079d7cd..8fe776f07 100644
--- a/src/NzbDrone.Mono/EnvironmentInfo/MonoPlatformInfo.cs
+++ b/src/NzbDrone.Mono/EnvironmentInfo/MonoPlatformInfo.cs
@@ -30,6 +30,7 @@ namespace NzbDrone.Mono.EnvironmentInfo
if (versionMatch.Success)
{
runTimeVersion = new Version(versionMatch.Groups["version"].Value);
+ Environment.SetEnvironmentVariable("RUNTIME_VERSION", runTimeVersion.ToString());
}
}
}
@@ -39,7 +40,6 @@ namespace NzbDrone.Mono.EnvironmentInfo
logger.Error(ex, "Unable to get mono version: " + ex.Message);
}
-
Version = runTimeVersion;
}
}
diff --git a/src/NzbDrone.Windows/EnvironmentInfo/DotNetPlatformInfo.cs b/src/NzbDrone.Windows/EnvironmentInfo/DotNetPlatformInfo.cs
index 921e2de10..f5cf9c583 100644
--- a/src/NzbDrone.Windows/EnvironmentInfo/DotNetPlatformInfo.cs
+++ b/src/NzbDrone.Windows/EnvironmentInfo/DotNetPlatformInfo.cs
@@ -8,7 +8,9 @@ namespace NzbDrone.Windows.EnvironmentInfo
{
public DotNetPlatformInfo()
{
- Version = GetFrameworkVersion();
+ var version = GetFrameworkVersion();
+ Environment.SetEnvironmentVariable("RUNTIME_VERSION", version.ToString());
+ Version = version;
}
public override Version Version { get; }
@@ -27,27 +29,27 @@ namespace NzbDrone.Windows.EnvironmentInfo
if (releaseKey >= 394802)
{
- return new Version(4,6,2);
+ return new Version(4, 6, 2);
}
if (releaseKey >= 394254)
{
- return new Version(4,6,1);
+ return new Version(4, 6, 1);
}
if (releaseKey >= 393295)
{
- return new Version(4,6);
+ return new Version(4, 6);
}
if (releaseKey >= 379893)
{
- return new Version(4,5,2);
+ return new Version(4, 5, 2);
}
if (releaseKey >= 378675)
{
- return new Version(4,5,1);
+ return new Version(4, 5, 1);
}
if (releaseKey >= 378389)
{
- return new Version(4,5);
+ return new Version(4, 5);
}
return new Version(4, 0);