| Current Path : /var/www/surf/TYPO3/vendor/typo3/cms-install/Classes/FolderStructure/ |
| Current File : /var/www/surf/TYPO3/vendor/typo3/cms-install/Classes/FolderStructure/LinkNode.php |
<?php
/*
* 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\Install\FolderStructure;
use TYPO3\CMS\Core\Messaging\FlashMessage;
use TYPO3\CMS\Core\Type\ContextualFeedbackSeverity;
use TYPO3\CMS\Install\FolderStructure\Exception\InvalidArgumentException;
/**
* A link
* @internal This class is only meant to be used within EXT:install and is not part of the TYPO3 Core API.
*/
class LinkNode extends AbstractNode implements NodeInterface
{
/**
* @var string Optional link target
*/
protected $target = '';
/**
* Implement constructor
*
* @param array $structure Structure array
* @param NodeInterface $parent Parent object
* @throws Exception\InvalidArgumentException
*/
public function __construct(array $structure, NodeInterface $parent = null)
{
if ($parent === null) {
throw new InvalidArgumentException(
'Link node must have parent',
1380485700
);
}
$this->parent = $parent;
// Ensure name is a single segment, but not a path like foo/bar or an absolute path /foo
if (str_contains($structure['name'], '/')) {
throw new InvalidArgumentException(
'File name must not contain forward slash',
1380546061
);
}
$this->name = $structure['name'];
if (isset($structure['target']) && $structure['target'] !== '') {
$this->target = $structure['target'];
}
}
/**
* Get own status
* Returns information status if running on Windows
* Returns OK status if is link and possible target is correct
* Else returns error (not fixable)
*
* @return FlashMessage[]
*/
public function getStatus(): array
{
if ($this->isWindowsOs()) {
return [
new FlashMessage(
'This node is not handled for Windows OS and should be checked manually.',
$this->getRelativePathBelowSiteRoot() . ' should be a link, but this support is incomplete for Windows.',
ContextualFeedbackSeverity::INFO
),
];
}
if (!$this->exists()) {
return [
new FlashMessage(
'Links cannot be fixed by this system',
$this->getRelativePathBelowSiteRoot() . ' should be a link, but it does not exist',
ContextualFeedbackSeverity::ERROR
),
];
}
if (!$this->isLink()) {
$type = @filetype($this->getAbsolutePath());
if ($type) {
$messageBody =
'The target ' . $this->getRelativePathBelowSiteRoot() . ' should be a link,' .
' but is of type ' . $type . '. This cannot be fixed automatically. Please investigate.'
;
} else {
$messageBody =
'The target ' . $this->getRelativePathBelowSiteRoot() . ' should be a file,' .
' but is of unknown type, probably because an upper level directory does not exist. Please investigate.'
;
}
return [
new FlashMessage(
$messageBody,
'Path ' . $this->getRelativePathBelowSiteRoot() . ' is not a link',
ContextualFeedbackSeverity::WARNING
),
];
}
if (!$this->isTargetCorrect()) {
return [
new FlashMessage(
'Link target should be ' . $this->getTarget() . ' but is ' . $this->getCurrentTarget(),
$this->getRelativePathBelowSiteRoot() . ' is a link, but link target is not as specified',
ContextualFeedbackSeverity::ERROR
),
];
}
$message = 'Is a link';
if ($this->getTarget() !== '') {
$message .= ' and correctly points to target ' . $this->getTarget();
}
return [
new FlashMessage(
$message,
$this->getRelativePathBelowSiteRoot()
),
];
}
/**
* Fix structure
*
* If there is nothing to fix, returns an empty array
*
* @return FlashMessage[]
*/
public function fix(): array
{
return [];
}
/**
* Get link target
*
* @return string Link target
*/
protected function getTarget()
{
return $this->target;
}
/**
* Find out if node is a link
*
* @throws Exception\InvalidArgumentException
* @return bool TRUE if node is a link
*/
protected function isLink()
{
if (!$this->exists()) {
throw new InvalidArgumentException(
'Link does not exist',
1380556246
);
}
return @is_link($this->getAbsolutePath());
}
/**
* Checks if the real link target is identical to given target
*
* @throws Exception\InvalidArgumentException
* @return bool TRUE if target is correct
*/
protected function isTargetCorrect()
{
if (!$this->exists()) {
throw new InvalidArgumentException(
'Link does not exist',
1380556245
);
}
if (!$this->isLink()) {
throw new InvalidArgumentException(
'Node is not a link',
1380556247
);
}
$result = false;
$expectedTarget = $this->getTarget();
if (empty($expectedTarget)) {
$result = true;
} else {
$actualTarget = $this->getCurrentTarget();
if ($expectedTarget === rtrim((string)$actualTarget, '/')) {
$result = true;
}
}
return $result;
}
/**
* Return current target of link
*
* @return false|string target
*/
protected function getCurrentTarget()
{
return readlink($this->getAbsolutePath());
}
}