using ErsatzTV.Core.Domain;
using ErsatzTV.Core.Errors;
namespace ErsatzTV.Core;
public static class VersionedAggregateExtensions
{
///
/// Optimistic-concurrency pre-check (issue #253). When the caller supplied one or more expected
/// versions (the strong If-Match entity-tags), fail with
/// (→ 412) unless the loaded aggregate's version is one of them (RFC 7232 §3.1: any strong match
/// proceeds). An empty set never matches → always 412 (a weak/non-canonical tag was sent).
/// An absent expectation is a force-write (Phase 1 back-compat). This returns a standalone
/// so the 412 is introduced AFTER the validation pipeline and never
/// flattened to 422 by (see api-conventions §7a).
///
public static Either CheckVersion(this T aggregate, Option> expectedVersions)
where T : IVersionedAggregate =>
expectedVersions.Match(
Some: versions => versions.Contains(aggregate.Version)
? Right(aggregate)
: Left(new PreconditionFailedError(
"The resource was modified by another request. Reload and try again.")),
None: () => Right(aggregate));
}