Added placeholders filter to utilize the placeholders in twig mode

Fixes #546
This commit is contained in:
Jan Böhmer 2024-03-06 21:00:21 +01:00
parent 757201cafa
commit dff1ef04bf
5 changed files with 83 additions and 3 deletions

View file

@ -53,7 +53,14 @@ use Twig\Error\Error;
final class LabelHTMLGenerator
{
public function __construct(private readonly ElementTypeNameGenerator $elementTypeNameGenerator, private readonly LabelTextReplacer $replacer, private readonly Environment $twig, private readonly LabelBarcodeGenerator $barcodeGenerator, private readonly SandboxedTwigFactory $sandboxedTwigProvider, private readonly Security $security, private readonly string $partdb_title)
public function __construct(
private readonly ElementTypeNameGenerator $elementTypeNameGenerator,
private readonly LabelTextReplacer $replacer,
private readonly Environment $twig,
private readonly LabelBarcodeGenerator $barcodeGenerator,
private readonly SandboxedTwigFactory $sandboxedTwigProvider,
private readonly Security $security,
private readonly string $partdb_title)
{
}

View file

@ -64,6 +64,17 @@ final class LabelTextReplacer
* @return string If the placeholder was valid, the replaced info. Otherwise the passed string.
*/
public function handlePlaceholder(string $placeholder, object $target): string
{
return $this->handlePlaceholderOrReturnNull($placeholder, $target) ?? $placeholder;
}
/**
* Similar to handlePlaceholder, but returns null if the placeholder is not known (instead of the original string)
* @param string $placeholder
* @param object $target
* @return string|null
*/
public function handlePlaceholderOrReturnNull(string $placeholder, object $target): ?string
{
foreach ($this->providers as $provider) {
/** @var PlaceholderProviderInterface $provider */
@ -73,7 +84,7 @@ final class LabelTextReplacer
}
}
return $placeholder;
return null;
}
/**

View file

@ -64,6 +64,7 @@ use App\Twig\BarcodeExtension;
use App\Twig\EntityExtension;
use App\Twig\FormatExtension;
use App\Twig\Sandbox\InheritanceSecurityPolicy;
use App\Twig\Sandbox\SandboxedLabelExtension;
use App\Twig\TwigCoreExtension;
use InvalidArgumentException;
use Twig\Environment;
@ -92,6 +93,9 @@ final class SandboxedTwigFactory
//FormatExtension:
'format_money', 'format_si', 'format_amount', 'format_bytes',
//SandboxedLabelExtension
'placeholders',
];
private const ALLOWED_FUNCTIONS = ['country_names', 'country_timezones', 'currency_names', 'cycle',
@ -103,7 +107,8 @@ final class SandboxedTwigFactory
'entity_type', 'entity_url',
//BarcodeExtension:
'barcode_svg',
//SandboxedLabelExtension
'placeholder',
];
private const ALLOWED_METHODS = [
@ -143,6 +148,7 @@ final class SandboxedTwigFactory
private readonly BarcodeExtension $barcodeExtension,
private readonly EntityExtension $entityExtension,
private readonly TwigCoreExtension $twigCoreExtension,
private readonly SandboxedLabelExtension $sandboxedLabelExtension,
)
{
}
@ -172,6 +178,7 @@ final class SandboxedTwigFactory
$twig->addExtension($this->barcodeExtension);
$twig->addExtension($this->entityExtension);
$twig->addExtension($this->twigCoreExtension);
$twig->addExtension($this->sandboxedLabelExtension);
return $twig;
}

View file

@ -0,0 +1,51 @@
<?php
/*
* This file is part of Part-DB (https://github.com/Part-DB/Part-DB-symfony).
*
* Copyright (C) 2019 - 2024 Jan Böhmer (https://github.com/jbtronics)
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU Affero General Public License as published
* by the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Affero General Public License for more details.
*
* You should have received a copy of the GNU Affero General Public License
* along with this program. If not, see <https://www.gnu.org/licenses/>.
*/
declare(strict_types=1);
namespace App\Twig\Sandbox;
use App\Services\LabelSystem\LabelTextReplacer;
use Twig\Extension\AbstractExtension;
use Twig\TwigFilter;
use Twig\TwigFunction;
class SandboxedLabelExtension extends AbstractExtension
{
public function __construct(private readonly LabelTextReplacer $labelTextReplacer)
{
}
public function getFunctions()
{
return [
new TwigFunction('placeholder', fn(string $text, object $label_target) => $this->labelTextReplacer->handlePlaceholderOrReturnNull($text, $label_target)),
];
}
public function getFilters(): array
{
return [
new TwigFilter('placeholders', fn(string $text, object $label_target) => $this->labelTextReplacer->replace($text, $label_target)),
];
}
}

View file

@ -88,6 +88,10 @@ class SandboxedTwigFactoryTest extends WebTestCase
'],
['
{{ entity_type(part) is object }}
'],
['
{% apply placeholders(part) %}[[NAME]]{% endapply %}</br>
{{ placeholder("[[NAME]]", part) }}
']
];
}