<?php

declare(strict_types=1);

namespace Drupal\flowdrop_interrupt\Message;

use Drupal\flowdrop_interrupt\Enum\InterruptType;

/**
 * Convenience base class for {@see InterruptMessageInterface} implementations.
 *
 * Concrete message classes call parent::__construct() with type/message/
 * context and add their own readonly fields. Plugins overwhelmingly want
 * this; if a shape doesn't fit, implement
 * {@see InterruptMessageInterface} directly.
 *
 * Example:
 * @code
 * final class MyInterruptMessage extends AbstractInterruptMessage {
 *   public function __construct(
 *     string $message,
 *     public readonly string $myExtraField,
 *     array $context = [],
 *   ) {
 *     parent::__construct(MyInterruptType::Whatever, $message, $context);
 *   }
 * }
 * @endcode
 *
 * @api
 */
abstract class AbstractInterruptMessage implements InterruptMessageInterface {

  /**
   * Constructs a new AbstractInterruptMessage.
   *
   * @param \Drupal\flowdrop_interrupt\Enum\InterruptType $type
   *   The interrupt type.
   * @param string $message
   *   Human-readable description of the interrupt.
   * @param array<string, mixed> $context
   *   Opaque payload — never used as a lookup key by the framework.
   */
  public function __construct(
    public readonly InterruptType $type,
    public readonly string $message,
    public readonly array $context = [],
  ) {}

  /**
   * {@inheritdoc}
   */
  public function getType(): InterruptType {
    return $this->type;
  }

  /**
   * {@inheritdoc}
   */
  public function getMessage(): string {
    return $this->message;
  }

  /**
   * {@inheritdoc}
   */
  public function getContext(): array {
    return $this->context;
  }

}
