eca-1.0.x-dev/modules/base/src/Plugin/Action/TokenReplace.php
modules/base/src/Plugin/Action/TokenReplace.php
<?php
namespace Drupal\eca_base\Plugin\Action;
use Drupal\Component\Render\MarkupInterface;
use Drupal\Core\Action\Attribute\Action;
use Drupal\Core\Field\FieldItemInterface;
use Drupal\Core\Field\FieldItemListInterface;
use Drupal\Core\StringTranslation\TranslatableMarkup;
use Drupal\Core\TypedData\TypedDataInterface;
use Drupal\eca\Attribute\EcaAction;
use Drupal\eca\Plugin\DataType\DataTransferObject;
/**
* Action to recursively replace tokens.
*/
#[Action(
id: 'eca_token_replace',
label: new TranslatableMarkup('Token: replace'),
)]
#[EcaAction(
description: new TranslatableMarkup('Replace all tokens, using a recursive strategy.'),
version_introduced: '2.0.0',
)]
class TokenReplace extends TokenSetValue {
/**
* {@inheritdoc}
*/
protected function setToken(string $name, mixed $value): void {
if ($value instanceof DataTransferObject) {
$value = $value->count() ? $value->toArray() : $value->getString();
}
elseif (($value instanceof TypedDataInterface) && !($value instanceof FieldItemListInterface) && !($value instanceof FieldItemInterface)) {
$value = $value->getValue();
}
if ($value instanceof MarkupInterface) {
$value = (string) $value;
}
$replace_recursive = function (mixed &$value) {
if (!is_scalar($value) && !is_null($value) && !($value instanceof MarkupInterface)) {
throw new \InvalidArgumentException(sprintf("Cannot replace tokens using a value of type %s.", is_object($value) ? get_class($value) : gettype($value)));
}
if (is_object($value)) {
$value = (string) $value;
}
if (is_string($value)) {
$limit = 5;
for ($i = 0; $i < $limit; $i++) {
$new_value = (string) $this->tokenService->replaceClear($value);
if ($new_value === $value) {
break;
}
$value = $new_value;
}
}
};
if (is_scalar($value)) {
$replace_recursive($value);
}
elseif (is_array($value)) {
array_walk_recursive($value, $replace_recursive);
}
elseif ($value instanceof FieldItemListInterface) {
$item_list = $value;
$item_values = $item_list->getValue();
array_walk_recursive($item_values, $replace_recursive);
$item_list->setValue($item_values);
}
elseif ($value instanceof FieldItemInterface) {
$item = $value;
$item_value = $item->getValue();
array_walk_recursive($item_value, $replace_recursive);
$item->setValue($item_value);
}
else {
throw new \InvalidArgumentException(sprintf("Cannot replace tokens using a value of type %s.", is_object($value) ? get_class($value) : gettype($value)));
}
parent::setToken($name, $value);
}
}
