Monitor.Client 1.1.2
Monitor.Client
The client library an application references to report its own system status and notifications to a Monitor
Dashboard. Monitor.ClientDemo in the same repository is a console application exercising everything below.
Example Usage
Set up the Monitor Client
First the MonitorClient needs to be set up with the URL of the monitor service, the application name, and the system name. This is typically done at the start of your application.
Here we use the Resilient API connection to ensure that the client can handle transient errors gracefully.
var monitorUrl = "https://localhost:7277/";
var clientKey = "…"; // issued in the Dashboard's management area
var applicationName = "Monitor";
var systemName = "Client Demo";
// Start notifier
MonitorClient.Instance = new MonitorClientConnection(
new ResilientClientKeyApiConnection(monitorUrl, clientKey), applicationName, systemName);
The client key
The Dashboard identifies a reporting application by a key, issued per application in its management area
and sent as the x-client-key header by ClientKeyApiConnection / ResilientClientKeyApiConnection.
- The key is shown once, when it is issued, and stored hashed. A lost key is reissued, never recovered.
- The
applicationNameabove must match the one the key was registered for, andsystemNamemust be one the registration permits — a registration with no system names listed permits any. - Rotation is: issue a second key, deploy it, then revoke the first. Both work in the meantime.
- Treat it like a password: keep it in configuration or a secret store, not in source.
A key is required as of 2.2. The Dashboard version shipping alongside it sets
Authentication:RequireClientKey, so the older keyless ResilientApiConnection gets 401 on every call.
It still works against an installation that has not taken that version yet, or one that has deliberately
overridden the flag while keys are rolled out — and there each keyless call is logged as a warning on the
Dashboard naming the application that needs one. See "Upgrading to 2.2" below.
If you are not using the Monitor, you may set it to NoMonitorClient.
MonitorClient.Instance = NoMonitor.Client;
This way no errors will occur.
You also have the option to ignore configuration errors, like missing configuration
MonitorClient.IgnoreMissingConfiguration = true;
This will ignore configuration errors and allow the application to run without throwing exceptions related to the monitor configuration.
Please be aware that he method EnsureSystemExistsAsync will not work if the configuration is missing.
Sending a System Status Message
var message = "This is a message";
await MonitorClient.SetStatusSuccessAsync(CurrentStatus.Running, message);
For errors you can use:
await MonitorClient.SetStatusErrorAsync(CurrentStatus.Running, message);
Sending a Notification
var message = "This is a notification";
await MonitorClient.NotifyAsync(message);
Ensuring System Exists
await MonitorClient.EnsureSystemExistsAsync();
Upgrading to 2.2
Nothing in this library changed. What changed is what the Dashboard accepts. Recompiling against 2.2 alters no behaviour; the version exists so that this page reaches you before your calls start being refused.
Authentication:RequireClientKey ships true from the Dashboard version released with 2.2, ending the
grace period that let applications report with no credential at all. Two consequences:
| If your application | Then |
|---|---|
Constructs ResilientClientKeyApiConnection / ClientKeyApiConnection with a valid key |
Nothing to do |
Constructs ResilientApiConnection or BasicApiConnection |
Every report is refused with 401 once that installation upgrades. Get a key issued and change the connection — see "The client key" above |
Watch reports go with it, and that is easy to miss. IClientConnection.WatchReport — everything built
on WatcherBase — is authorized as "either producer credential", which the Dashboard only enforces once
both the agent and client flags are on. The agent flag has been on all along, so it is this change that
starts refusing keyless watch reports too.
Diagnosing a refusal takes a Serilog sink. Every method on IClientConnection catches, logs and returns
false, so a wrong key is indistinguishable from an unreachable server unless something is configured to
receive Log.Error. Configure one before you roll a key out, not after:
Log.Logger = new LoggerConfiguration().WriteTo.Console().CreateLogger();
A 401 there means no valid key was presented — missing, mistyped, or revoked; note that a key is
{keyId}_{secret} in full, and half of one authenticates as nothing. A 403 means the opposite: the key
is valid, but the registration does not cover the application or system name being reported.
Upgrading to 2.0
If you use MonitorClient / IClientConnection — the usage shown above — nothing changes. Recompile
and carry on. NotifyAsync, SetStatusAsync, EnsureSystemExistsAsync, HandleNotificationAsync and
WatchReport all keep their signatures and their behaviour.
The breaking changes are in ISystemStatusRepository, which only matters if you took a dependency on that
interface directly. They come from SystemStatus moving out of SQL Server in the Dashboard:
| Change | Why |
|---|---|
GetAsync, UpdateAsync and SetStatusAsync return SystemStatus? |
A system that is not registered is now a 404 answered as null, instead of a 500 that surfaced as an exception |
SystemStatus has a new Id property |
The ApplicationName + SystemName pair, serialized — assigned by the Dashboard, ignore it when reporting |
AddWatchReport is gone |
Watch reports have their own endpoint now. IClientConnection.WatchReport(...) is unchanged and uses it — and works, which it never did before: the old server side wrote to a table that did not exist |
New ImportAsync |
Migration only; this client throws NotSupportedException for it |
One behaviour worth knowing even if you change nothing: an application reporting a status for a system that nobody registered still gets that system created for it, as before.
No packages depend on Monitor.Client.
2.2.0 - no code change. The Dashboard now requires a client key: an application still using ResilientApiConnection or BasicApiConnection is refused with 401, and keyless watch reports stop with it. See "Upgrading to 2.2" in the readme.
.NET 10.0
- Microsoft.Extensions.Http.Polly (>= 10.0.10)
- Serilog (>= 4.4.0)