save progress
This commit is contained in:
@@ -9,6 +9,7 @@ using Microsoft.Extensions.Logging;
|
||||
using NATS.Client.Core;
|
||||
using NATS.Client.JetStream;
|
||||
using NATS.Client.JetStream.Models;
|
||||
using StellaOps.HybridLogicalClock;
|
||||
|
||||
namespace StellaOps.Scheduler.Queue.Nats;
|
||||
|
||||
@@ -24,6 +25,7 @@ internal abstract class NatsSchedulerQueueBase<TMessage> : ISchedulerQueue<TMess
|
||||
private readonly INatsSchedulerQueuePayload<TMessage> _payload;
|
||||
private readonly ILogger _logger;
|
||||
private readonly TimeProvider _timeProvider;
|
||||
private readonly IHybridLogicalClock? _hlc;
|
||||
private readonly SemaphoreSlim _connectionGate = new(1, 1);
|
||||
private readonly Func<NatsOpts, CancellationToken, ValueTask<NatsConnection>> _connectionFactory;
|
||||
|
||||
@@ -40,6 +42,7 @@ internal abstract class NatsSchedulerQueueBase<TMessage> : ISchedulerQueue<TMess
|
||||
INatsSchedulerQueuePayload<TMessage> payload,
|
||||
ILogger logger,
|
||||
TimeProvider timeProvider,
|
||||
IHybridLogicalClock? hlc = null,
|
||||
Func<NatsOpts, CancellationToken, ValueTask<NatsConnection>>? connectionFactory = null)
|
||||
{
|
||||
_queueOptions = queueOptions ?? throw new ArgumentNullException(nameof(queueOptions));
|
||||
@@ -48,6 +51,7 @@ internal abstract class NatsSchedulerQueueBase<TMessage> : ISchedulerQueue<TMess
|
||||
_payload = payload ?? throw new ArgumentNullException(nameof(payload));
|
||||
_logger = logger ?? throw new ArgumentNullException(nameof(logger));
|
||||
_timeProvider = timeProvider ?? TimeProvider.System;
|
||||
_hlc = hlc;
|
||||
_connectionFactory = connectionFactory ?? ((opts, cancellationToken) => new ValueTask<NatsConnection>(new NatsConnection(opts)));
|
||||
|
||||
if (string.IsNullOrWhiteSpace(_natsOptions.Url))
|
||||
@@ -67,7 +71,11 @@ internal abstract class NatsSchedulerQueueBase<TMessage> : ISchedulerQueue<TMess
|
||||
|
||||
var payloadBytes = _payload.Serialize(message);
|
||||
var idempotencyKey = _payload.GetIdempotencyKey(message);
|
||||
var headers = BuildHeaders(message, idempotencyKey);
|
||||
|
||||
// Generate HLC timestamp if clock is available
|
||||
var hlcTimestamp = _hlc?.Tick();
|
||||
|
||||
var headers = BuildHeaders(message, idempotencyKey, hlcTimestamp);
|
||||
|
||||
var publishOptions = new NatsJSPubOpts
|
||||
{
|
||||
@@ -531,6 +539,14 @@ internal abstract class NatsSchedulerQueueBase<TMessage> : ISchedulerQueue<TMess
|
||||
? DateTimeOffset.FromUnixTimeMilliseconds(unix)
|
||||
: now;
|
||||
|
||||
// Parse HLC timestamp if present
|
||||
HlcTimestamp? hlcTimestamp = null;
|
||||
if (headers.TryGetValue(SchedulerQueueFields.HlcTimestamp, out var hlcValues) && hlcValues.Count > 0
|
||||
&& HlcTimestamp.TryParse(hlcValues[0], out var parsedHlc))
|
||||
{
|
||||
hlcTimestamp = parsedHlc;
|
||||
}
|
||||
|
||||
var leaseExpires = now.Add(leaseDuration);
|
||||
var runId = _payload.GetRunId(deserialized);
|
||||
var tenantId = _payload.GetTenantId(deserialized);
|
||||
@@ -558,10 +574,11 @@ internal abstract class NatsSchedulerQueueBase<TMessage> : ISchedulerQueue<TMess
|
||||
attempt,
|
||||
enqueuedAt,
|
||||
leaseExpires,
|
||||
consumer);
|
||||
consumer,
|
||||
hlcTimestamp);
|
||||
}
|
||||
|
||||
private NatsHeaders BuildHeaders(TMessage message, string idempotencyKey)
|
||||
private NatsHeaders BuildHeaders(TMessage message, string idempotencyKey, HlcTimestamp? hlcTimestamp = null)
|
||||
{
|
||||
var headers = new NatsHeaders
|
||||
{
|
||||
@@ -572,6 +589,12 @@ internal abstract class NatsSchedulerQueueBase<TMessage> : ISchedulerQueue<TMess
|
||||
{ SchedulerQueueFields.EnqueuedAt, _timeProvider.GetUtcNow().ToUnixTimeMilliseconds().ToString() }
|
||||
};
|
||||
|
||||
// Include HLC timestamp if available
|
||||
if (hlcTimestamp.HasValue)
|
||||
{
|
||||
headers.Add(SchedulerQueueFields.HlcTimestamp, hlcTimestamp.Value.ToSortableString());
|
||||
}
|
||||
|
||||
var scheduleId = _payload.GetScheduleId(message);
|
||||
if (!string.IsNullOrWhiteSpace(scheduleId))
|
||||
{
|
||||
|
||||
Reference in New Issue
Block a user