Class AiProviderHealthTracker
- Namespace
- MailFathom.Infrastructure.Observability
- Assembly
- MailFathom.Infrastructure.dll
Holds what the last call to each AI provider established, and publishes both states as one instrument.
public sealed class AiProviderHealthTracker : IAiProviderHealthRecorder, IAiProviderHealthReader
- Inheritance
-
AiProviderHealthTracker
- Implements
- Inherited Members
Remarks
One tracker for both roles, with the role as a key rather than as a second class. That is what makes the two states independently observable without being independently implemented: a reader asks for one role and receives that role's answer, and the gauge below carries one measurement per role so a dashboard can show either without the other hiding it.
The gauge reports a number rather than a name, because an instrument's value has to be one. It publishes the state's
own enumeration value, whose members are allocated once and never reordered, so a recording rule written against
2 keeps meaning "unavailable" for as long as the series exists.
A transition is logged as well as measured, because a metric answers what the state is now and an operator reading afterwards needs to know when it changed and to what. Only a change is logged: every provider call records, and a line per call would put the log's volume on the mailbox's size rather than on anything an operator would act on. The one change that is not logged is a first call that succeeded, which restores nothing.
Nothing here is mail or derived from it. The only tag is the role, one of two constants, and the only values are a state and the moment it was observed — which is also a cardinality rule, since anything per endpoint or per request would open a time series that grows with the deployment. The log lines carry the same two things and no credential, endpoint address, request, or provider response text.
Constructors
- AiProviderHealthTracker(TimeProvider, ILogger<AiProviderHealthTracker>)
Initializes a tracker that has observed nothing yet, and the instrument it publishes through.
Methods
- Read(AiProviderRole)
Reads the state of one provider.
- RecordMisconfigured(AiProviderRole)
Records that a call failed for a reason no later attempt changes until somebody acts.
- RecordServed(AiProviderRole)
Records that a call to the provider produced an answer.
- RecordUnavailable(AiProviderRole)
Records that a call failed for a reason a later attempt may not meet.