<?php

declare(strict_types=1);

namespace Drupal\flowdrop_stategraph\Checkpointer;

use Drupal\flowdrop_stategraph\DTO\Checkpoint;

/**
 * Interface for checkpoint persistence.
 *
 * Checkpointers are responsible for storing and retrieving graph state
 * snapshots. Two implementations are provided:
 * - MemoryCheckpointer: In-memory storage for development/testing.
 * - EntityCheckpointer: Drupal entity storage for production.
 *
 * The checkpointer type is configured at the workflow/pipeline level,
 * allowing different execution contexts to use appropriate storage.
 *
 * @see \Drupal\flowdrop_stategraph\Checkpointer\MemoryCheckpointer
 * @see \Drupal\flowdrop_stategraph\Checkpointer\EntityCheckpointer
 *
 * @api
 */
interface CheckpointerInterface {

  /**
   * Gets a checkpoint by ID.
   *
   * @param string $checkpointId
   *   The checkpoint ID.
   *
   * @return \Drupal\flowdrop_stategraph\DTO\Checkpoint|null
   *   The checkpoint or NULL if not found.
   *
   * @throws \Drupal\flowdrop_stategraph\Exception\CheckpointException
   *   When retrieval fails due to storage error.
   */
  public function get(string $checkpointId): ?Checkpoint;

  /**
   * Stores a checkpoint.
   *
   * @param \Drupal\flowdrop_stategraph\DTO\Checkpoint $checkpoint
   *   The checkpoint to store.
   *
   * @return string
   *   The checkpoint ID (same as $checkpoint->id).
   *
   * @throws \Drupal\flowdrop_stategraph\Exception\CheckpointException
   *   When storage fails.
   */
  public function put(Checkpoint $checkpoint): string;

  /**
   * Lists checkpoints for a thread.
   *
   * @param string $threadId
   *   The thread ID to list checkpoints for.
   * @param int $limit
   *   Maximum number of checkpoints to return.
   *
   * @return array<\Drupal\flowdrop_stategraph\DTO\Checkpoint>
   *   Array of checkpoints, ordered by creation time (newest first).
   *
   * @throws \Drupal\flowdrop_stategraph\Exception\CheckpointException
   *   When listing fails.
   */
  public function list(string $threadId, int $limit = 100): array;

  /**
   * Gets the latest checkpoint for a thread.
   *
   * @param string $threadId
   *   The thread ID.
   *
   * @return \Drupal\flowdrop_stategraph\DTO\Checkpoint|null
   *   The latest checkpoint or NULL if no checkpoints exist.
   *
   * @throws \Drupal\flowdrop_stategraph\Exception\CheckpointException
   *   When retrieval fails.
   */
  public function getLatest(string $threadId): ?Checkpoint;

  /**
   * Deletes a checkpoint.
   *
   * @param string $checkpointId
   *   The checkpoint ID to delete.
   *
   * @return bool
   *   TRUE if deleted, FALSE if not found.
   *
   * @throws \Drupal\flowdrop_stategraph\Exception\CheckpointException
   *   When deletion fails.
   */
  public function delete(string $checkpointId): bool;

  /**
   * Deletes all checkpoints for a thread.
   *
   * @param string $threadId
   *   The thread ID.
   *
   * @return int
   *   Number of checkpoints deleted.
   *
   * @throws \Drupal\flowdrop_stategraph\Exception\CheckpointException
   *   When deletion fails.
   */
  public function deleteThread(string $threadId): int;

  /**
   * Clears all checkpoints (for testing/cleanup).
   *
   * @return int
   *   Number of checkpoints deleted.
   */
  public function clear(): int;

}
