77 lines
2.7 KiB
PHP
77 lines
2.7 KiB
PHP
<?php
|
|
|
|
declare(strict_types=1);
|
|
|
|
/*
|
|
* This file is part of the TYPO3 CMS project.
|
|
*
|
|
* It is free software; you can redistribute it and/or modify it under
|
|
* the terms of the GNU General Public License, either version 2
|
|
* of the License, or any later version.
|
|
*
|
|
* For the full copyright and license information, please read the
|
|
* LICENSE.txt file that was distributed with this source code.
|
|
*
|
|
* The TYPO3 project - inspiring people to share!
|
|
*/
|
|
|
|
namespace TYPO3\CMS\Core\TypoScript\IncludeTree;
|
|
|
|
use Symfony\Component\DependencyInjection\Attribute\Autoconfigure;
|
|
use TYPO3\CMS\Core\Cache\Frontend\PhpFrontend;
|
|
use TYPO3\CMS\Core\TypoScript\IncludeTree\IncludeNode\RootInclude;
|
|
use TYPO3\CMS\Core\TypoScript\IncludeTree\IncludeNode\StringInclude;
|
|
use TYPO3\CMS\Core\TypoScript\Tokenizer\TokenizerInterface;
|
|
|
|
/**
|
|
* Parse a single TypoScript string, supporting imports and conditions.
|
|
*
|
|
* This is a relatively simple "tree" builder: It gets a single TypoScript string
|
|
* snippet, tokenizes it and creates a RootInclude "tree". The string is scanned
|
|
* for imports and conditions: Those create sub includes, just like the other
|
|
* TreeBuilder classes do.
|
|
*
|
|
* @internal
|
|
*/
|
|
#[Autoconfigure(public: true)]
|
|
final readonly class StringTreeBuilder
|
|
{
|
|
public function __construct(
|
|
private TreeFromLineStreamBuilder $treeFromTokenStreamBuilder,
|
|
) {}
|
|
|
|
/**
|
|
* Create tree, ready to be traversed. Will cache if $cache is not null.
|
|
*
|
|
* @param non-empty-string $name A name used as cache identifier, [a-z,A-Z,-] only
|
|
*/
|
|
public function getTreeFromString(
|
|
string $name,
|
|
string $typoScriptString,
|
|
TokenizerInterface $tokenizer,
|
|
?PhpFrontend $cache = null,
|
|
): RootInclude {
|
|
$lowerCaseName = mb_strtolower($name);
|
|
$identifier = 'string-' . $lowerCaseName . '-' . hash('xxh3', $typoScriptString);
|
|
if ($cache) {
|
|
$includeTree = $cache->require($identifier);
|
|
if ($includeTree instanceof RootInclude) {
|
|
return $includeTree;
|
|
}
|
|
}
|
|
$includeTree = new RootInclude();
|
|
$includeNode = new StringInclude();
|
|
$includeNode->setName('[string] ' . $name);
|
|
$includeNode->setLineStream($tokenizer->tokenize($typoScriptString));
|
|
$this->treeFromTokenStreamBuilder->buildTree($includeNode, 'other', $tokenizer);
|
|
$includeTree->addChild($includeNode);
|
|
$cache?->set($identifier, $this->prepareTreeForCache($includeTree));
|
|
return $includeTree;
|
|
}
|
|
|
|
private function prepareTreeForCache(RootInclude $node): string
|
|
{
|
|
return 'return unserialize(\'' . addcslashes(serialize($node), '\'\\') . '\');';
|
|
}
|
|
}
|