<?php

declare(strict_types=1);

namespace Drupal\flowdrop_runtime\DTO;

/**
 * Enumeration of logging verbosity levels for node execution.
 *
 * Controls how much detail is logged during workflow execution.
 * Higher verbosity levels include all logging from lower levels.
 *
 * Configured via: /admin/flowdrop/settings → Logging → Verbosity
 *
 * Usage:
 * - Silent: No execution logging at all
 * - Minimal: Production with minimal logging overhead (errors only)
 * - Standard: Normal operation with key events logged
 * - Verbose: Debugging with input/output summaries
 * - Debug: Full tracing with complete data dumps
 *
 * @internal
 *   This class is not part of the public API and may change without notice.
 */
enum LogVerbosity: string {

  /* No execution logging.
   *
   * Use when logging is completely disabled.
   * Logs: Nothing at all.
   */
  case Silent = "silent";

  /* Only log errors and critical failures.
   *
   * Use for production environments where logging overhead matters.
   * Logs: Errors, exceptions, critical failures.
   */
  case Minimal = "minimal";

  /* Log start, complete, and failures (default).
   *
   * Standard operation logging for normal workflows.
   * Logs: Node start/complete, validation failures, errors.
   */
  case Standard = "standard";

  /* Include inputs/outputs summary.
   *
   * For debugging specific workflow issues.
   * Logs: All Standard + parameter counts, output sizes, timing.
   */
  case Verbose = "verbose";

  /* Full inputs/outputs with detailed timing.
   *
   * For development and deep debugging.
   * Logs: All Verbose + full parameter values, complete outputs.
   */
  case Debug = "debug";

  /**
   * Check if this verbosity level should log at the given level.
   *
   * @param \Drupal\flowdrop_runtime\DTO\LogVerbosity $requiredLevel
   *   The minimum verbosity level required for logging.
   *
   * @return bool
   *   TRUE if current verbosity should include this log level.
   */
  public function shouldLog(LogVerbosity $requiredLevel): bool {
    return $this->getNumericLevel() >= $requiredLevel->getNumericLevel();
  }

  /**
   * Get numeric level for comparison.
   *
   * @return int
   *   Numeric level (higher = more verbose).
   */
  public function getNumericLevel(): int {
    return match ($this) {
      self::Silent => 0,
      self::Minimal => 1,
      self::Standard => 2,
      self::Verbose => 3,
      self::Debug => 4,
    };
  }

  /**
   * Create from string value with fallback to Standard.
   *
   * @param string $value
   *   The verbosity value string.
   *
   * @return self
   *   The LogVerbosity enum case.
   */
  public static function fromString(string $value): self {
    return match (strtolower($value)) {
      "silent" => self::Silent,
      "minimal" => self::Minimal,
      "standard" => self::Standard,
      "verbose" => self::Verbose,
      "debug" => self::Debug,
      default => self::Standard,
    };
  }

  /**
   * Get human-readable description.
   *
   * @return string
   *   Description of what this level logs.
   */
  public function getDescription(): string {
    return match ($this) {
      self::Silent => "No execution logging",
      self::Minimal => "Only errors and critical failures",
      self::Standard => "Node start/complete and failures",
      self::Verbose => "Includes input/output summaries",
      self::Debug => "Full data dumps with detailed timing",
    };
  }

}
