Skip to content

Commit 6e6ab3e

Browse files
committed
introduce performance counters
1 parent 091722e commit 6e6ab3e

File tree

9 files changed

+147
-39
lines changed

9 files changed

+147
-39
lines changed

projects/RabbitMQ.Client/client/impl/CommandAssembler.cs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,7 @@
3434

3535
using RabbitMQ.Client.Exceptions;
3636
using RabbitMQ.Client.Framing.Impl;
37+
using RabbitMQ.Client.Logging;
3738
using RabbitMQ.Util;
3839

3940
namespace RabbitMQ.Client.Impl
@@ -91,6 +92,7 @@ public bool HandleFrame(in InboundFrame frame, out IncomingCommand command)
9192
return true;
9293
}
9394

95+
RabbitMqClientEventSource.Log.CommandReceived();
9496
command = new IncomingCommand(_method, _header, _body, _bodyBytes);
9597
Reset();
9698
return shallReturn;

projects/RabbitMQ.Client/client/impl/Connection.Commands.cs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,7 @@
3535
using RabbitMQ.Client.Events;
3636
using RabbitMQ.Client.Exceptions;
3737
using RabbitMQ.Client.Impl;
38+
using RabbitMQ.Client.Logging;
3839
using RabbitMQ.Util;
3940

4041
namespace RabbitMQ.Client.Framing.Impl
@@ -71,6 +72,7 @@ internal void HandleConnectionUnblocked()
7172

7273
private void Open()
7374
{
75+
RabbitMqClientEventSource.Log.ConnectionOpened();
7476
StartAndTune();
7577
_model0.ConnectionOpen(_factory.VirtualHost);
7678
}

projects/RabbitMQ.Client/client/impl/Connection.cs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -339,6 +339,7 @@ private void FinishClose()
339339
_frameHandler.Close();
340340
_model0.SetCloseReason(CloseReason);
341341
_model0.FinishClose();
342+
RabbitMqClientEventSource.Log.ConnectionClosed();
342343
}
343344

344345
///<summary>Broadcasts notification of the final shutdown of the connection.</summary>

projects/RabbitMQ.Client/client/impl/Frame.cs

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -37,6 +37,7 @@
3737
using System.Runtime.ExceptionServices;
3838

3939
using RabbitMQ.Client.Exceptions;
40+
using RabbitMQ.Client.Logging;
4041
using RabbitMQ.Util;
4142

4243
namespace RabbitMQ.Client.Impl
@@ -49,9 +50,6 @@ internal static class Framing
4950
* | 1 byte | 2 bytes | 4 bytes | x bytes | 1 byte |
5051
* +------------+---------+----------------+---------+------------------+ */
5152
internal const int BaseFrameSize = 1 + 2 + 4 + 1;
52-
internal const int StartFrameType = 0;
53-
internal const int StartChannel = 1;
54-
internal const int StartPayloadSize = 3;
5553
private const int StartPayload = 7;
5654

5755
internal static class Method
@@ -248,6 +246,7 @@ internal static InboundFrame ReadFrom(Stream reader, byte[] frameHeaderBuffer)
248246
throw new MalformedFrameException($"Bad frame end marker: {payloadBytes[payloadSize]}");
249247
}
250248

249+
RabbitMqClientEventSource.Log.DataReceived(payloadSize + Framing.BaseFrameSize);
251250
return new InboundFrame(type, channel, new Memory<byte>(payloadBytes, 0, payloadSize), payloadBytes);
252251
}
253252

projects/RabbitMQ.Client/client/impl/SessionBase.cs

Lines changed: 8 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -31,9 +31,10 @@
3131

3232
using System;
3333
using System.Threading;
34-
34+
using RabbitMQ.Client.client.framing;
3535
using RabbitMQ.Client.Exceptions;
3636
using RabbitMQ.Client.Framing.Impl;
37+
using RabbitMQ.Client.Logging;
3738

3839
namespace RabbitMQ.Client.Impl
3940
{
@@ -50,6 +51,7 @@ protected SessionBase(Connection connection, ushort channelNumber)
5051
{
5152
connection.ConnectionShutdown += OnConnectionShutdown;
5253
}
54+
RabbitMqClientEventSource.Log.ChannelOpened();
5355
}
5456

5557
public event EventHandler<ShutdownEventArgs> SessionShutdown
@@ -102,7 +104,10 @@ public void Close(ShutdownEventArgs reason)
102104

103105
public void Close(ShutdownEventArgs reason, bool notify)
104106
{
105-
Interlocked.CompareExchange(ref _closeReason, reason, null);
107+
if (Interlocked.CompareExchange(ref _closeReason, reason, null) is null)
108+
{
109+
RabbitMqClientEventSource.Log.ChannelClosed();
110+
}
106111
if (notify)
107112
{
108113
OnSessionShutdown(CloseReason);
@@ -126,7 +131,7 @@ public void Notify()
126131

127132
public virtual void Transmit<T>(in T cmd) where T : struct, IOutgoingCommand
128133
{
129-
if (!IsOpen && cmd.Method.ProtocolCommandId != client.framing.ProtocolCommandId.ChannelCloseOk)
134+
if (!IsOpen && cmd.Method.ProtocolCommandId != ProtocolCommandId.ChannelCloseOk)
130135
{
131136
throw new AlreadyClosedException(CloseReason);
132137
}

projects/RabbitMQ.Client/client/impl/SocketFrameHandler.cs

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,7 @@
4040
using System.Threading.Tasks;
4141

4242
using RabbitMQ.Client.Exceptions;
43+
using RabbitMQ.Client.Logging;
4344

4445
namespace RabbitMQ.Client.Impl
4546
{
@@ -59,7 +60,7 @@ public static async Task TimeoutAfter(this Task task, TimeSpan timeout)
5960
}
6061
}
6162

62-
internal class SocketFrameHandler : IFrameHandler
63+
internal sealed class SocketFrameHandler : IFrameHandler
6364
{
6465
private readonly ITcpClient _socket;
6566
private readonly Stream _reader;
@@ -282,6 +283,7 @@ private async Task WriteLoop()
282283
#else
283284
await _writer.WriteAsync(memory).ConfigureAwait(false);
284285
#endif
286+
RabbitMqClientEventSource.Log.CommandSent(segment.Count);
285287
ArrayPool<byte>.Shared.Return(segment.Array);
286288
}
287289

Lines changed: 121 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,121 @@
1+
// This source code is dual-licensed under the Apache License, version
2+
// 2.0, and the Mozilla Public License, version 2.0.
3+
//
4+
// The APL v2.0:
5+
//
6+
//---------------------------------------------------------------------------
7+
// Copyright (c) 2007-2020 VMware, Inc.
8+
//
9+
// Licensed under the Apache License, Version 2.0 (the "License");
10+
// you may not use this file except in compliance with the License.
11+
// You may obtain a copy of the License at
12+
//
13+
// https://www.apache.org/licenses/LICENSE-2.0
14+
//
15+
// Unless required by applicable law or agreed to in writing, software
16+
// distributed under the License is distributed on an "AS IS" BASIS,
17+
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
18+
// See the License for the specific language governing permissions and
19+
// limitations under the License.
20+
//---------------------------------------------------------------------------
21+
//
22+
// The MPL v2.0:
23+
//
24+
//---------------------------------------------------------------------------
25+
// This Source Code Form is subject to the terms of the Mozilla Public
26+
// License, v. 2.0. If a copy of the MPL was not distributed with this
27+
// file, You can obtain one at https://mozilla.org/MPL/2.0/.
28+
//
29+
// Copyright (c) 2007-2020 VMware, Inc. All rights reserved.
30+
//---------------------------------------------------------------------------
31+
32+
using System;
33+
using System.Diagnostics.Tracing;
34+
using System.Threading;
35+
36+
namespace RabbitMQ.Client.Logging
37+
{
38+
#nullable enable
39+
internal sealed partial class RabbitMqClientEventSource
40+
{
41+
private static int ConnectionsOpened;
42+
private static int ConnectionsClosed;
43+
private static int ChannelsOpened;
44+
private static int ChannelsClosed;
45+
private static long BytesSent;
46+
private static long BytesReceived;
47+
private static long CommandsSent;
48+
private static long CommandsReceived;
49+
50+
#if !NETSTANDARD
51+
private PollingCounter? _connectionOpenedCounter;
52+
private PollingCounter? _openConnectionCounter;
53+
private PollingCounter? _channelOpenedCounter;
54+
private PollingCounter? _openChannelCounter;
55+
private IncrementingPollingCounter? _bytesSentCounter;
56+
private IncrementingPollingCounter? _bytesReceivedCounter;
57+
private IncrementingPollingCounter? _commandSentCounter;
58+
private IncrementingPollingCounter? _commandReceivedCounter;
59+
60+
protected override void OnEventCommand(EventCommandEventArgs command)
61+
{
62+
if (command.Command == EventCommand.Enable)
63+
{
64+
_connectionOpenedCounter ??= new PollingCounter("total-connections-opened", this, () => ConnectionsOpened) { DisplayName = "Total connections opened" };
65+
_openConnectionCounter ??= new PollingCounter("current-open-connections", this, () => ConnectionsOpened - ConnectionsClosed) { DisplayName = "Current open connections count" };
66+
67+
_channelOpenedCounter ??= new PollingCounter("total-channels-opened", this, () => ChannelsOpened) { DisplayName = "Total channels opened" };
68+
_openChannelCounter ??= new PollingCounter("current-open-channels", this, () => ChannelsOpened - ChannelsClosed) { DisplayName = "Current open channels count" };
69+
70+
_bytesSentCounter ??= new IncrementingPollingCounter("bytes-sent-rate", this, () => Interlocked.Read(ref BytesSent)) { DisplayName = "Byte sending rate", DisplayUnits = "B", DisplayRateTimeScale = new TimeSpan(0, 0, 1) };
71+
_bytesReceivedCounter ??= new IncrementingPollingCounter("bytes-received-rate", this, () => Interlocked.Read(ref BytesReceived)) { DisplayName = "Byte receiving rate", DisplayUnits = "B", DisplayRateTimeScale = new TimeSpan(0, 0, 1) };
72+
73+
_commandSentCounter ??= new IncrementingPollingCounter("AMQP-method-sent-rate", this, () => Interlocked.Read(ref CommandsSent)) { DisplayName = "AMQP method sending rate", DisplayUnits = "B", DisplayRateTimeScale = new TimeSpan(0, 0, 1) };
74+
_commandReceivedCounter ??= new IncrementingPollingCounter("AMQP-method-received-rate", this, () => Interlocked.Read(ref CommandsReceived)) { DisplayName = "AMQP method receiving rate", DisplayUnits = "B", DisplayRateTimeScale = new TimeSpan(0, 0, 1) };
75+
}
76+
}
77+
#endif
78+
[NonEvent]
79+
public void ConnectionOpened()
80+
{
81+
Interlocked.Increment(ref ConnectionsOpened);
82+
}
83+
84+
[NonEvent]
85+
public void ConnectionClosed()
86+
{
87+
Interlocked.Increment(ref ConnectionsClosed);
88+
}
89+
90+
[NonEvent]
91+
public void ChannelOpened()
92+
{
93+
Interlocked.Increment(ref ChannelsOpened);
94+
}
95+
96+
[NonEvent]
97+
public void ChannelClosed()
98+
{
99+
Interlocked.Increment(ref ChannelsClosed);
100+
}
101+
102+
[NonEvent]
103+
public void DataReceived(int byteCount)
104+
{
105+
Interlocked.Add(ref BytesReceived, byteCount);
106+
}
107+
108+
[NonEvent]
109+
public void CommandSent(int byteCount)
110+
{
111+
Interlocked.Increment(ref CommandsSent);
112+
Interlocked.Add(ref BytesSent, byteCount);
113+
}
114+
115+
[NonEvent]
116+
public void CommandReceived()
117+
{
118+
Interlocked.Increment(ref CommandsReceived);
119+
}
120+
}
121+
}

projects/RabbitMQ.Client/client/logging/RabbitMqClientEventSource.cs

Lines changed: 8 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -34,25 +34,20 @@
3434

3535
namespace RabbitMQ.Client.Logging
3636
{
37-
[EventSource(Name="rabbitmq-dotnet-client")]
38-
public sealed class RabbitMqClientEventSource : EventSource
37+
#nullable enable
38+
internal sealed partial class RabbitMqClientEventSource : EventSource
3939
{
40-
public class Keywords
40+
public static readonly RabbitMqClientEventSource Log = new RabbitMqClientEventSource();
41+
42+
public RabbitMqClientEventSource()
43+
: base("rabbitmq-client")
4144
{
42-
public const EventKeywords Log = (EventKeywords)1;
4345
}
44-
#if NET452
45-
public RabbitMqClientEventSource() : base()
46-
{
4746

48-
}
49-
#else
50-
public RabbitMqClientEventSource() : base(EventSourceSettings.EtwSelfDescribingEventFormat)
47+
public class Keywords
5148
{
49+
public const EventKeywords Log = (EventKeywords)1;
5250
}
53-
#endif
54-
55-
public static RabbitMqClientEventSource Log = new RabbitMqClientEventSource ();
5651

5752
[Event(1, Message = "INFO", Keywords = Keywords.Log, Level = EventLevel.Informational)]
5853
public void Info(string message)

projects/Unit/APIApproval.Approve.verified.txt

Lines changed: 0 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -808,25 +808,6 @@ namespace RabbitMQ.Client.Exceptions
808808
}
809809
namespace RabbitMQ.Client.Logging
810810
{
811-
[System.Diagnostics.Tracing.EventSource(Name="rabbitmq-dotnet-client")]
812-
public sealed class RabbitMqClientEventSource : System.Diagnostics.Tracing.EventSource
813-
{
814-
public static RabbitMQ.Client.Logging.RabbitMqClientEventSource Log;
815-
public RabbitMqClientEventSource() { }
816-
[System.Diagnostics.Tracing.Event(3, Keywords=System.Diagnostics.Tracing.EventKeywords.None | System.Diagnostics.Tracing.EventKeywords.All, Level=System.Diagnostics.Tracing.EventLevel.Error, Message="ERROR")]
817-
public void Error(string message, RabbitMQ.Client.Logging.RabbitMqExceptionDetail ex) { }
818-
[System.Diagnostics.Tracing.NonEvent]
819-
public void Error(string message, System.Exception ex) { }
820-
[System.Diagnostics.Tracing.Event(1, Keywords=System.Diagnostics.Tracing.EventKeywords.None | System.Diagnostics.Tracing.EventKeywords.All, Level=System.Diagnostics.Tracing.EventLevel.Informational, Message="INFO")]
821-
public void Info(string message) { }
822-
[System.Diagnostics.Tracing.Event(2, Keywords=System.Diagnostics.Tracing.EventKeywords.None | System.Diagnostics.Tracing.EventKeywords.All, Level=System.Diagnostics.Tracing.EventLevel.Warning, Message="WARN")]
823-
public void Warn(string message) { }
824-
public class Keywords
825-
{
826-
public const System.Diagnostics.Tracing.EventKeywords Log = 1;
827-
public Keywords() { }
828-
}
829-
}
830811
[System.Diagnostics.Tracing.EventData]
831812
public class RabbitMqExceptionDetail
832813
{

0 commit comments

Comments
 (0)