namespace ZB.MOM.WW.OtOpcUa.Core.Abstractions;

/// <summary>
///     Durable, crash-safe FIFO buffer the continuous-historization recorder appends sampled values
///     to <em>before</em> acking the writer, so nothing is lost if the process dies mid-drain. An
///     implementation guarantees: appended entries survive an unclean restart up to its commit
///     cadence; <see cref="PeekBatchAsync"/> returns entries in append (FIFO) order; and
///     <see cref="RemoveAsync"/> durably reclaims an acked entry. A capacity-bounded implementation
///     drops the oldest entry on overflow and reflects it in <see cref="DroppedCount"/>.
/// </summary>
public interface IHistorizationOutbox : IDisposable
{
    /// <summary>Lifetime count of entries dropped because an append would have exceeded capacity.</summary>
    long DroppedCount { get; }

    /// <summary>Appends <paramref name="entry"/> to the tail of the durable buffer.</summary>
    /// <param name="entry">The value record to buffer.</param>
    /// <param name="ct">Cancellation token.</param>
    /// <returns>A task that represents the asynchronous operation.</returns>
    ValueTask AppendAsync(HistorizationOutboxEntry entry, CancellationToken ct);

    /// <summary>
    ///     Returns up to <paramref name="max"/> oldest un-acked entries in FIFO order without removing
    ///     them. Removal happens via <see cref="RemoveAsync"/> once each entry is durably written.
    /// </summary>
    /// <param name="max">Maximum number of entries to return; must be positive.</param>
    /// <param name="ct">Cancellation token.</param>
    /// <returns>Up to <paramref name="max"/> oldest un-acked entries in FIFO order.</returns>
    ValueTask<IReadOnlyList<HistorizationOutboxEntry>> PeekBatchAsync(int max, CancellationToken ct);

    /// <summary>
    ///     Durably removes the entry identified by <paramref name="id"/> (and any older entries ahead
    ///     of it in FIFO order), advancing the buffer head. A no-op when the id is unknown.
    /// </summary>
    /// <param name="id">The <see cref="HistorizationOutboxEntry.Id"/> to ack.</param>
    /// <param name="ct">Cancellation token.</param>
    /// <returns>A task that represents the asynchronous operation.</returns>
    ValueTask RemoveAsync(Guid id, CancellationToken ct);

    /// <summary>Current number of un-acked entries held in the buffer.</summary>
    /// <param name="ct">Cancellation token.</param>
    /// <returns>The current number of un-acked entries in the buffer.</returns>
    ValueTask<int> CountAsync(CancellationToken ct);
}
