feat(usage): hold the last good TokenTracker export fail-open
This commit is contained in:
@@ -0,0 +1,55 @@
|
||||
namespace ClaudeDo.Worker.Usage.TokenTracker;
|
||||
|
||||
/// <summary>
|
||||
/// Threadsafe holder for the last successful export. Mirrors <see cref="UsageState"/>: a failed
|
||||
/// fetch never overwrites a good export, it only records <see cref="LastError"/>.
|
||||
/// </summary>
|
||||
public sealed class TokenTrackerState
|
||||
{
|
||||
private readonly object _lock = new();
|
||||
private TokenTrackerExport? _export;
|
||||
private DateTime? _lastAttemptUtc;
|
||||
private string? _lastError;
|
||||
|
||||
public TokenTrackerExport? Export
|
||||
{
|
||||
get { lock (_lock) return _export; }
|
||||
}
|
||||
|
||||
public DateTime? LastAttemptUtc
|
||||
{
|
||||
get { lock (_lock) return _lastAttemptUtc; }
|
||||
}
|
||||
|
||||
public string? LastError
|
||||
{
|
||||
get { lock (_lock) return _lastError; }
|
||||
}
|
||||
|
||||
public void ReportSuccess(TokenTrackerExport export)
|
||||
{
|
||||
lock (_lock)
|
||||
{
|
||||
_export = export;
|
||||
_lastAttemptUtc = export.FetchedAtUtc;
|
||||
_lastError = null;
|
||||
}
|
||||
}
|
||||
|
||||
public void ReportFailure(string error, DateTime attemptedAtUtc)
|
||||
{
|
||||
lock (_lock)
|
||||
{
|
||||
_lastAttemptUtc = attemptedAtUtc;
|
||||
_lastError = error;
|
||||
}
|
||||
}
|
||||
|
||||
public bool IsOlderThan(TimeSpan maxAge, DateTime nowUtc)
|
||||
{
|
||||
lock (_lock)
|
||||
{
|
||||
return _export is null || nowUtc - _export.FetchedAtUtc > maxAge;
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user