public interface IDraftService
{
///
/// Returns the full draft payload for a batch, including patient, encounter,
/// and all observation rows entered so far.
///
Task GetDraftAsync(Guid batchId);
///
/// Upserts draft patient demographics for a batch. Creates the DraftPatient
/// row on the first call; updates it on subsequent calls. Transitions batch
/// from Uploaded/Rejected to InEntry on first save.
///
Task UpsertPatientAsync(Guid batchId, UpsertDraftPatientRequest req, Guid actorUserId);
///
/// Upserts draft encounter fields for a batch. Creates the DraftEncounter
/// row on the first call; updates it on subsequent calls.
///
Task UpsertEncounterAsync(Guid batchId, UpsertDraftEncounterRequest req, Guid actorUserId);
///
/// Adds a new observation row to the batch draft. Validates plausibility
/// before saving — implausible values throw ValidationException.
///
Task AddObservationAsync(Guid batchId, CreateDraftObservationRequest req, Guid actorUserId);
///
/// Edits an existing observation row. Re-validates plausibility on the new value.
///
Task UpdateObservationAsync(Guid batchId, Guid observationId, UpdateDraftObservationRequest req, Guid actorUserId);
///
/// Removes an observation row from the batch draft.
///
Task DeleteObservationAsync(Guid batchId, Guid observationId, Guid actorUserId);
///
/// Validates completeness per batch type and transitions the batch to
/// PendingVerification. Throws ValidationException if required fields
/// are missing.
///
Task SubmitForVerificationAsync(Guid batchId, Guid actorUserId);
}