import { Result, ok, err } from '@shared/kernel/fp';
import { problemDetail } from '@shared/infrastructure/api-error';
import { withIdempotencyKey } from '@shared/infrastructure/api-client.provider';

/**
 * Run a mutating API call and fold it into a `Result` — the one place the
 * try/catch + ProblemDetails-mapping lives, so every `submit-*` command is just
 * its own payload mapping. The backend re-validates and returns a 422
 * ProblemDetails on rejection, surfaced here as the error string.
 *
 * Also the one place a logical submit's Idempotency-Key is minted — once per
 * `runSubmit` call, not per HTTP attempt — so a retry of this same submit
 * dedupes on the backend (see `withIdempotencyKey`).
 */
export async function runSubmit<T>(
  fn: () => Promise<T>,
  fallback: string,
): Promise<Result<string, T>> {
  try {
    return ok(await withIdempotencyKey(crypto.randomUUID(), fn));
  } catch (e) {
    return err(problemDetail(e, fallback));
  }
}

// Single shared default for a failed submit; the @@id dedupes it at the
// translation layer.
export const SUBMIT_FAILED = $localize`:@@submit.failed:Het indienen is niet gelukt. Probeer het later opnieuw.`;
