Disable heartbeat warning when debugger is attached (#2258)

This commit is contained in:
Stephen Halter 2018-01-16 18:11:11 -08:00 committed by GitHub
parent f4d27e67bb
commit cf371a4e74
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
4 changed files with 45 additions and 8 deletions

View File

@ -13,14 +13,16 @@ namespace Microsoft.AspNetCore.Server.Kestrel.Core.Internal.Infrastructure
private readonly IHeartbeatHandler[] _callbacks; private readonly IHeartbeatHandler[] _callbacks;
private readonly ISystemClock _systemClock; private readonly ISystemClock _systemClock;
private readonly IDebugger _debugger;
private readonly IKestrelTrace _trace; private readonly IKestrelTrace _trace;
private Timer _timer; private Timer _timer;
private int _executingOnHeartbeat; private int _executingOnHeartbeat;
public Heartbeat(IHeartbeatHandler[] callbacks, ISystemClock systemClock, IKestrelTrace trace) public Heartbeat(IHeartbeatHandler[] callbacks, ISystemClock systemClock, IDebugger debugger, IKestrelTrace trace)
{ {
_callbacks = callbacks; _callbacks = callbacks;
_systemClock = systemClock; _systemClock = systemClock;
_debugger = debugger;
_trace = trace; _trace = trace;
} }
@ -59,7 +61,10 @@ namespace Microsoft.AspNetCore.Server.Kestrel.Core.Internal.Infrastructure
} }
else else
{ {
_trace.HeartbeatSlow(Interval, now); if (!_debugger.IsAttached)
{
_trace.HeartbeatSlow(Interval, now);
}
} }
} }

View File

@ -3,6 +3,7 @@
using System; using System;
using System.Collections.Generic; using System.Collections.Generic;
using System.Diagnostics;
using System.Threading; using System.Threading;
using System.Threading.Tasks; using System.Threading.Tasks;
using Microsoft.AspNetCore.Hosting.Server; using Microsoft.AspNetCore.Hosting.Server;
@ -47,7 +48,9 @@ namespace Microsoft.AspNetCore.Server.Kestrel.Core
var httpHeartbeatManager = new HttpHeartbeatManager(serviceContext.ConnectionManager); var httpHeartbeatManager = new HttpHeartbeatManager(serviceContext.ConnectionManager);
_heartbeat = new Heartbeat( _heartbeat = new Heartbeat(
new IHeartbeatHandler[] { serviceContext.DateHeaderValueManager, httpHeartbeatManager }, new IHeartbeatHandler[] { serviceContext.DateHeaderValueManager, httpHeartbeatManager },
serviceContext.SystemClock, Trace); serviceContext.SystemClock,
DebuggerWrapper.Singleton,
Trace);
Features = new FeatureCollection(); Features = new FeatureCollection();
_serverAddresses = new ServerAddressesFeature(); _serverAddresses = new ServerAddressesFeature();

View File

@ -46,7 +46,7 @@ namespace Microsoft.AspNetCore.Server.Kestrel.Core.Tests
var dateHeaderValueManager = new DateHeaderValueManager(systemClock); var dateHeaderValueManager = new DateHeaderValueManager(systemClock);
var testKestrelTrace = new TestKestrelTrace(); var testKestrelTrace = new TestKestrelTrace();
using (var heartbeat = new Heartbeat(new IHeartbeatHandler[] { dateHeaderValueManager }, systemClock, testKestrelTrace)) using (var heartbeat = new Heartbeat(new IHeartbeatHandler[] { dateHeaderValueManager }, systemClock, DebuggerWrapper.Singleton, testKestrelTrace))
{ {
Assert.Equal(now.ToString(Rfc1123DateFormat), dateHeaderValueManager.GetDateHeaderValues().String); Assert.Equal(now.ToString(Rfc1123DateFormat), dateHeaderValueManager.GetDateHeaderValues().String);
systemClock.UtcNow = future; systemClock.UtcNow = future;
@ -71,7 +71,7 @@ namespace Microsoft.AspNetCore.Server.Kestrel.Core.Tests
var mockHeartbeatHandler = new Mock<IHeartbeatHandler>(); var mockHeartbeatHandler = new Mock<IHeartbeatHandler>();
using (var heartbeat = new Heartbeat(new[] { dateHeaderValueManager, mockHeartbeatHandler.Object }, systemClock, testKestrelTrace)) using (var heartbeat = new Heartbeat(new[] { dateHeaderValueManager, mockHeartbeatHandler.Object }, systemClock, DebuggerWrapper.Singleton, testKestrelTrace))
{ {
heartbeat.OnHeartbeat(); heartbeat.OnHeartbeat();
@ -100,7 +100,7 @@ namespace Microsoft.AspNetCore.Server.Kestrel.Core.Tests
var dateHeaderValueManager = new DateHeaderValueManager(systemClock); var dateHeaderValueManager = new DateHeaderValueManager(systemClock);
var testKestrelTrace = new TestKestrelTrace(); var testKestrelTrace = new TestKestrelTrace();
using (var heatbeat = new Heartbeat(new IHeartbeatHandler[] { dateHeaderValueManager }, systemClock, testKestrelTrace)) using (var heatbeat = new Heartbeat(new IHeartbeatHandler[] { dateHeaderValueManager }, systemClock, DebuggerWrapper.Singleton, testKestrelTrace))
{ {
heatbeat.OnHeartbeat(); heatbeat.OnHeartbeat();
Assert.Equal(now.ToString(Rfc1123DateFormat), dateHeaderValueManager.GetDateHeaderValues().String); Assert.Equal(now.ToString(Rfc1123DateFormat), dateHeaderValueManager.GetDateHeaderValues().String);

View File

@ -26,14 +26,16 @@ namespace Microsoft.AspNetCore.Server.Kestrel.Core.Tests
{ {
var systemClock = new MockSystemClock(); var systemClock = new MockSystemClock();
var heartbeatHandler = new Mock<IHeartbeatHandler>(); var heartbeatHandler = new Mock<IHeartbeatHandler>();
var debugger = new Mock<IDebugger>();
var kestrelTrace = new Mock<IKestrelTrace>(); var kestrelTrace = new Mock<IKestrelTrace>();
var handlerMre = new ManualResetEventSlim(); var handlerMre = new ManualResetEventSlim();
var traceMre = new ManualResetEventSlim(); var traceMre = new ManualResetEventSlim();
heartbeatHandler.Setup(h => h.OnHeartbeat(systemClock.UtcNow)).Callback(() => handlerMre.Wait()); heartbeatHandler.Setup(h => h.OnHeartbeat(systemClock.UtcNow)).Callback(() => handlerMre.Wait());
debugger.Setup(d => d.IsAttached).Returns(false);
kestrelTrace.Setup(t => t.HeartbeatSlow(Heartbeat.Interval, systemClock.UtcNow)).Callback(() => traceMre.Set()); kestrelTrace.Setup(t => t.HeartbeatSlow(Heartbeat.Interval, systemClock.UtcNow)).Callback(() => traceMre.Set());
using (var heartbeat = new Heartbeat(new[] { heartbeatHandler.Object }, systemClock, kestrelTrace.Object)) using (var heartbeat = new Heartbeat(new[] { heartbeatHandler.Object }, systemClock, debugger.Object, kestrelTrace.Object))
{ {
Task.Run(() => heartbeat.OnHeartbeat()); Task.Run(() => heartbeat.OnHeartbeat());
Task.Run(() => heartbeat.OnHeartbeat()); Task.Run(() => heartbeat.OnHeartbeat());
@ -46,6 +48,33 @@ namespace Microsoft.AspNetCore.Server.Kestrel.Core.Tests
kestrelTrace.Verify(t => t.HeartbeatSlow(Heartbeat.Interval, systemClock.UtcNow), Times.Once()); kestrelTrace.Verify(t => t.HeartbeatSlow(Heartbeat.Interval, systemClock.UtcNow), Times.Once());
} }
[Fact]
public void BlockedHeartbeatIsNotLoggedAsErrorIfDebuggerAttached()
{
var systemClock = new MockSystemClock();
var heartbeatHandler = new Mock<IHeartbeatHandler>();
var debugger = new Mock<IDebugger>();
var kestrelTrace = new Mock<IKestrelTrace>();
var handlerMre = new ManualResetEventSlim();
var traceMre = new ManualResetEventSlim();
heartbeatHandler.Setup(h => h.OnHeartbeat(systemClock.UtcNow)).Callback(() => handlerMre.Wait());
debugger.Setup(d => d.IsAttached).Returns(true);
kestrelTrace.Setup(t => t.HeartbeatSlow(Heartbeat.Interval, systemClock.UtcNow)).Callback(() => traceMre.Set());
using (var heartbeat = new Heartbeat(new[] { heartbeatHandler.Object }, systemClock, debugger.Object, kestrelTrace.Object))
{
Task.Run(() => heartbeat.OnHeartbeat());
Task.Run(() => heartbeat.OnHeartbeat());
Assert.False(traceMre.Wait(TimeSpan.FromSeconds(10)));
}
handlerMre.Set();
heartbeatHandler.Verify(h => h.OnHeartbeat(systemClock.UtcNow), Times.Once());
kestrelTrace.Verify(t => t.HeartbeatSlow(Heartbeat.Interval, systemClock.UtcNow), Times.Never());
}
[Fact] [Fact]
public void ExceptionFromHeartbeatHandlerIsLoggedAsError() public void ExceptionFromHeartbeatHandlerIsLoggedAsError()
{ {
@ -56,7 +85,7 @@ namespace Microsoft.AspNetCore.Server.Kestrel.Core.Tests
heartbeatHandler.Setup(h => h.OnHeartbeat(systemClock.UtcNow)).Throws(ex); heartbeatHandler.Setup(h => h.OnHeartbeat(systemClock.UtcNow)).Throws(ex);
using (var heartbeat = new Heartbeat(new[] { heartbeatHandler.Object }, systemClock, kestrelTrace)) using (var heartbeat = new Heartbeat(new[] { heartbeatHandler.Object }, systemClock, DebuggerWrapper.Singleton, kestrelTrace))
{ {
heartbeat.OnHeartbeat(); heartbeat.OnHeartbeat();
} }