<?php

namespace EasyLinkAutomations\Actions;

if (!defined('ABSPATH')) {
    exit;
}

use EasyLinkAutomations\Actions\Contracts\ActionInterface;

/**
 * Registry for managing available actions.
 *
 * Actions register themselves here so they can be discovered by the UI
 * and instantiated when automations are executed.
 */
final class ActionRegistry
{
    /**
     * @var array<string, class-string<ActionInterface>>
     */
    private static array $actions = [];

    /**
     * Register an action class.
     *
     * @param class-string<ActionInterface> $actionClass
     */
    public static function register(string $actionClass): void
    {
        if (!is_subclass_of($actionClass, ActionInterface::class)) {
            return;
        }

        $slug = $actionClass::getSlug();
        self::$actions[$slug] = $actionClass;
    }

    /**
     * Get an action instance by slug.
     */
    public static function get(string $slug): ?ActionInterface
    {
        if (!isset(self::$actions[$slug])) {
            return null;
        }

        $class = self::$actions[$slug];

        return new $class();
    }

    /**
     * Get all registered actions.
     *
     * @return array<string, ActionInterface>
     */
    public static function all(): array
    {
        $instances = [];

        foreach (self::$actions as $slug => $class) {
            $instances[$slug] = new $class();
        }

        return $instances;
    }

    /**
     * Get all actions as array (for API response).
     *
     * @return array<int, array>
     */
    public static function toArray(): array
    {
        $result = [];

        foreach (self::$actions as $class) {
            $result[] = $class::toArray();
        }

        return $result;
    }

    /**
     * Get actions grouped by category.
     * Actions without a category are returned under '_uncategorized' key.
     *
     * @return array<string, array>
     */
    public static function groupedByCategory(): array
    {
        $grouped = [];

        foreach (self::$actions as $class) {
            $category = $class::getCategory();
            $key = $category ?: '_uncategorized';
            $grouped[$key][] = $class::toArray();
        }

        return $grouped;
    }

    /**
     * Check if an action exists.
     */
    public static function has(string $slug): bool
    {
        return isset(self::$actions[$slug]);
    }
}
