using ZB.MOM.WW.Audit;
using ZB.MOM.WW.ScadaBridge.Commons.Types;
namespace ZB.MOM.WW.ScadaBridge.Commons.Interfaces.Services;
///
/// Site-local audit-log queue surface consumed by the site
/// SiteAuditTelemetryActor drain loop and the M6
/// SiteStreamGrpcServer.PullAuditEvents reconciliation handler.
/// Extracted from SqliteAuditWriter so both consumers can be
/// unit-tested against a stub without touching SQLite; the
/// SqliteAuditWriter production type implements this interface
/// and DI wires the same singleton instance to every consumer.
///
///
/// Lives in Commons (rather than alongside SqliteAuditWriter in
/// ZB.MOM.WW.ScadaBridge.AuditLog) because ZB.MOM.WW.ScadaBridge.Communication — which
/// hosts the M6 gRPC pull handler — must depend on this interface and
/// ZB.MOM.WW.ScadaBridge.AuditLog already depends on ZB.MOM.WW.ScadaBridge.Communication.
/// Pulling the interface up to Commons breaks the would-be cycle while
/// keeping the implementation in the AuditLog component.
///
/// Only the methods the drain and pull paths need are exposed — the
/// hot-path WriteAsync stays on
/// (script-thread surface), separated by concern so each side can be
/// mocked independently.
///
public interface ISiteAuditQueue
{
///
/// Returns up to rows currently in
/// ,
/// oldest first. Idempotent — repeated calls before
/// will yield the same rows again.
///
///
/// AuditLog-001: cached-lifecycle audit kinds
/// (,
/// ,
/// ,
/// ) are
/// EXCLUDED from this result — they ride the combined-telemetry drain via
/// + the central
/// OnCachedTelemetryAsync dual-write transaction. The audit-only
/// drain handled by this method covers everything else (sync ApiCall /
/// DbWrite, NotifySend, InboundRequest, etc.).
///
/// Maximum number of rows to return.
/// Cancellation token.
Task> ReadPendingAsync(int limit, CancellationToken ct = default);
///
/// AuditLog-001: returns up to rows in
///
/// whose audit kind belongs to the cached-call lifecycle
/// vocabulary (,
/// ,
/// ,
/// ),
/// oldest first. The site-side SiteAuditTelemetryActor drains these
/// rows separately, joining each with the matching operational tracking row
/// (IOperationTrackingStore.GetStatusAsync) before pushing the
/// combined CachedTelemetryBatch via
/// ISiteStreamAuditClient.IngestCachedTelemetryAsync. Idempotent —
/// repeated calls before yield the same
/// rows again.
///
///
/// The two-drain partition is the production wiring of the combined-telemetry
/// transport specified in Component-AuditLog.md §"Cached Operations —
/// Combined Telemetry": cached rows MUST flow with their matching
/// SiteCalls upsert through one MS SQL transaction at central. The
/// pre-AuditLog-001 implementation drained cached rows through the
/// audit-only path, leaving the operational half unsent and the central
/// dual-write handler unreachable. Returning them via this dedicated read
/// surface lets the new drain join with the tracking store before push.
///
/// Maximum number of rows to return.
/// Cancellation token.
Task> ReadPendingCachedTelemetryAsync(int limit, CancellationToken ct = default);
///
/// Flips the supplied EventIds from
/// to
/// .
/// Non-existent or already-forwarded ids are silent no-ops.
///
/// Event IDs to mark as forwarded.
/// Cancellation token.
Task MarkForwardedAsync(IReadOnlyList eventIds, CancellationToken ct = default);
///
/// M6 reconciliation-pull read surface: returns up to
/// rows whose >=
/// and whose is still
/// or
/// .
///
///
/// Rows in the brief race window between site-Forwarded and central-ingest are
/// intentionally included: the central reconciliation puller dedups on
/// , so re-shipping is safe and avoids losing rows
/// whose telemetry ack was acted on locally but never landed centrally. Ordering
/// is oldest first with
/// as the deterministic tiebreaker.
///
/// Lower bound timestamp (UTC).
/// Maximum number of rows to return.
/// Cancellation token.
Task> ReadPendingSinceAsync(
DateTime sinceUtc, int batchSize, CancellationToken ct = default);
///
/// M6 reconciliation-pull commit surface: flips the supplied EventIds to
/// ,
/// but ONLY for rows currently in
/// or
/// .
/// Rows already in
/// are left untouched (idempotent re-call). Non-existent ids are silent no-ops.
///
/// Event IDs to mark as reconciled.
/// Cancellation token.
Task MarkReconciledAsync(IReadOnlyList eventIds, CancellationToken ct = default);
///
/// M6 Bundle E (T6) health-metric surface: returns a point-in-time snapshot
/// of the site queue's pending count + oldest pending timestamp + on-disk
/// SQLite file size. Surfaced on
/// as
/// SiteAuditBacklog by the periodic SiteAuditBacklogReporter
/// hosted service so a stuck site→central drain is visible on the central
/// health dashboard. Safe to call concurrently with hot-path writes —
/// implementations are expected to take the same connection lock used by
/// the hot-path INSERT batch and the drain queries.
///
/// Cancellation token.
Task GetBacklogStatsAsync(CancellationToken ct = default);
}