Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

BUGFIX: Remove import site from site creation module and fix delete sites (9.0) #5440

Open
wants to merge 11 commits into
base: 9.0
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -16,11 +16,11 @@

use Neos\ContentRepository\Core\Feature\NodeRenaming\Command\ChangeNodeAggregateName;
use Neos\ContentRepository\Core\Projection\ContentGraph\NodeAggregate;
use Neos\ContentRepository\Core\SharedModel\Workspace\Workspace;
use Neos\ContentRepository\Core\SharedModel\ContentRepository\ContentRepositoryId;
use Neos\ContentRepository\Core\SharedModel\Exception\NodeNameIsAlreadyCovered;
use Neos\ContentRepository\Core\SharedModel\Exception\NodeTypeNotFound;
use Neos\ContentRepository\Core\SharedModel\Node\NodeName;
use Neos\ContentRepository\Core\SharedModel\Workspace\Workspace;
use Neos\ContentRepository\Core\SharedModel\Workspace\WorkspaceName;
use Neos\ContentRepositoryRegistry\ContentRepositoryRegistry;
use Neos\ContentRepositoryRegistry\Exception\ContentRepositoryNotFoundException;
Expand All @@ -41,10 +41,6 @@
use Neos\Neos\Domain\Service\NodeTypeNameFactory;
use Neos\Neos\Domain\Service\SiteService;
use Neos\Neos\Domain\Service\UserService;
use Neos\Neos\FrontendRouting\SiteDetection\SiteDetectionResult;
use Neos\SiteKickstarter\Generator\SitePackageGeneratorInterface;
use Neos\SiteKickstarter\Service\SiteGeneratorCollectingService;
use Neos\SiteKickstarter\Service\SitePackageGeneratorNameService;

/**
* The Neos Sites Management module controller
Expand Down Expand Up @@ -89,6 +85,18 @@ class SitesController extends AbstractModuleController
*/
protected $session;

/**
* This is not 100% correct, but it is as good as we can get it to work right now
* It works when the created site's name will use the configuration "*" which by default uses the default preset.
*
* As proposed here https://github.com/neos/neos-development-collection/issues/4470#issuecomment-2432140074
* the site must have a field to define the contentRepositoryId to correctly create sites dynamically.
*
* @Flow\InjectConfiguration("sitePresets.default.contentRepository")
* @var string|null
*/
protected $defaultContentRepositoryForNewSites;

#[Flow\Inject]
protected UserService $domainUserService;

Expand Down Expand Up @@ -236,65 +244,29 @@ public function updateSiteAction(Site $site, $newSiteNodeName)
*/
public function newSiteAction(): void
{
// This is not 100% correct, but it is as good as we can get it to work right now
try {
$contentRepositoryId = SiteDetectionResult::fromRequest($this->request->getHttpRequest())
->contentRepositoryId;
} catch (\RuntimeException) {
$contentRepositoryId = ContentRepositoryId::fromString('default');
$contentRepositoryId = ContentRepositoryId::fromString($this->defaultContentRepositoryForNewSites ?? '');
} catch (\InvalidArgumentException $e) {
throw new \RuntimeException('The default content repository for new sites configured in "Neos.Neos.sitePresets.default.contentRepository" is not valid.', 1736946907, $e);
}

try {
$contentRepository = $this->contentRepositoryRegistry->get($contentRepositoryId);
$documentNodeTypes = $contentRepository->getNodeTypeManager()->getSubNodeTypes(NodeTypeNameFactory::forSite(), false);
} catch (ContentRepositoryNotFoundException) {
$documentNodeTypes = [];
} catch (ContentRepositoryNotFoundException $e) {
throw new \RuntimeException(sprintf('The default content repository for new sites "%s" could not be instantiated.', $contentRepositoryId->value), 1736946907);
}

$documentNodeTypes = $contentRepository->getNodeTypeManager()->getSubNodeTypes(NodeTypeNameFactory::forSite(), false);

$sitePackages = $this->packageManager->getFilteredPackages('available', 'neos-site');

$this->view->assignMultiple([
'defaultContentRepositoryForNewSites' => $contentRepositoryId->value,
'sitePackages' => $sitePackages,
'documentNodeTypes' => $documentNodeTypes
]);
}

/**
* Import a site from site package.
*
* @param string $packageKey Package from where the import will come
* @Flow\Validate(argumentName="$packageKey", type="\Neos\Neos\Validation\Validator\PackageKeyValidator")
* @return void
*/
/*public function importSiteAction($packageKey)
{
try {
$this->siteImportService->importFromPackage($packageKey);
$this->addFlashMessage(
$this->getModuleLabel('sites.theSiteHasBeenImported.body'),
'',
Message::SEVERITY_OK,
[],
1412372266
);
} catch (\Exception $exception) {
$logMessage = $this->throwableStorage->logThrowable($exception);
$this->logger->error($logMessage, LogEnvironment::fromMethodName(__METHOD__));
$this->addFlashMessage(
$this->getModuleLabel(
'sites.importError.body',
[htmlspecialchars($packageKey), htmlspecialchars($exception->getMessage())]
),
$this->getModuleLabel('sites.importError.title'),
Message::SEVERITY_ERROR,
[],
1412372375
);
}
$this->unsetLastVisitedNodeAndRedirect('index');
}*/

/**
* Create a new empty site.
*
Expand Down
13 changes: 11 additions & 2 deletions Neos.Neos/Classes/Domain/Service/SiteService.php
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@
use Neos\ContentRepositoryRegistry\ContentRepositoryRegistry;
use Neos\Flow\Annotations as Flow;
use Neos\Flow\Persistence\PersistenceManagerInterface;
use Neos\Flow\Security\Context as SecurityContext;
use Neos\Media\Domain\Model\Asset;
use Neos\Media\Domain\Repository\AssetCollectionRepository;
use Neos\Neos\Domain\Exception\SiteNodeNameIsAlreadyInUseByAnotherSite;
Expand Down Expand Up @@ -70,14 +71,21 @@ class SiteService
*/
protected $workspaceService;

/**
* @Flow\Inject
* @var SecurityContext
*/
protected $securityContext;

/**
* Remove given site all nodes for that site and all domains associated.
*/
public function pruneSite(Site $site): void
{
$siteServiceInternals = new SiteServiceInternals(
$this->contentRepositoryRegistry->get($site->getConfiguration()->contentRepositoryId),
$this->workspaceService
$this->workspaceService,
$this->securityContext
);

try {
Expand Down Expand Up @@ -181,7 +189,8 @@ public function createSite(

$siteServiceInternals = new SiteServiceInternals(
$this->contentRepositoryRegistry->get($site->getConfiguration()->contentRepositoryId),
$this->workspaceService
$this->workspaceService,
$this->securityContext
);
$siteServiceInternals->createSiteNodeIfNotExists($site, $nodeTypeName);

Expand Down
39 changes: 25 additions & 14 deletions Neos.Neos/Classes/Domain/Service/SiteServiceInternals.php
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@
use Neos\ContentRepository\Core\SharedModel\Node\NodeAggregateId;
use Neos\ContentRepository\Core\SharedModel\Node\NodeVariantSelectionStrategy;
use Neos\ContentRepository\Core\SharedModel\Workspace\WorkspaceName;
use Neos\Flow\Security\Context as SecurityContext;
use Neos\Neos\Domain\Exception\SiteNodeTypeIsInvalid;
use Neos\Neos\Domain\Model\Site;
use Neos\Neos\Domain\Model\SiteNodeName;
Expand All @@ -49,6 +50,7 @@
public function __construct(
private ContentRepository $contentRepository,
private WorkspaceService $workspaceService,
private SecurityContext $securityContext
) {
$this->nodeTypeManager = $this->contentRepository->getNodeTypeManager();
$this->interDimensionalVariationGraph = $this->contentRepository->getVariationGraph();
Expand All @@ -66,9 +68,13 @@ public function removeSiteNode(SiteNodeName $siteNodeName): void
);
}

// todo only remove site node in base workspace and rebase dependant workspaces to avoid also the security hacks here.
foreach ($this->contentRepository->findWorkspaces() as $workspace) {
$contentGraph = $this->contentRepository->getContentGraph($workspace->workspaceName);
$sitesNodeAggregate = $contentGraph->findRootNodeAggregateByType(
$contentGraph = null;
$this->securityContext->withoutAuthorizationChecks(function () use (&$contentGraph, $workspace) {
$contentGraph = $this->contentRepository->getContentGraph($workspace->workspaceName);
});
$sitesNodeAggregate = $contentGraph?->findRootNodeAggregateByType(
NodeTypeNameFactory::forSites()
);
if (!$sitesNodeAggregate) {
Expand All @@ -80,12 +86,14 @@ public function removeSiteNode(SiteNodeName $siteNodeName): void
$siteNodeName->toNodeName()
);
if ($siteNodeAggregate instanceof NodeAggregate) {
$this->contentRepository->handle(RemoveNodeAggregate::create(
$workspace->workspaceName,
$siteNodeAggregate->nodeAggregateId,
$arbitraryDimensionSpacePoint,
NodeVariantSelectionStrategy::STRATEGY_ALL_VARIANTS,
));
$this->securityContext->withoutAuthorizationChecks(
fn () => $this->contentRepository->handle(RemoveNodeAggregate::create(
$workspace->workspaceName,
$siteNodeAggregate->nodeAggregateId,
$arbitraryDimensionSpacePoint,
NodeVariantSelectionStrategy::STRATEGY_ALL_VARIANTS,
))
);
}
}
}
Expand All @@ -94,12 +102,15 @@ public function createSiteNodeIfNotExists(Site $site, string $nodeTypeName): voi
{
$liveWorkspace = $this->contentRepository->findWorkspaceByName(WorkspaceName::forLive());
if ($liveWorkspace === null) {
$this->workspaceService->createRootWorkspace(
$this->contentRepository->id,
WorkspaceName::forLive(),
WorkspaceTitle::fromString('Public live workspace'),
WorkspaceDescription::empty(),
WorkspaceRoleAssignments::createForLiveWorkspace()
// CreateRootWorkspace was denied: Creation of root workspaces is currently only allowed with disabled authorization checks
$this->securityContext->withoutAuthorizationChecks(
fn () => $this->workspaceService->createRootWorkspace(
$this->contentRepository->id,
WorkspaceName::forLive(),
WorkspaceTitle::fromString('Public live workspace'),
WorkspaceDescription::empty(),
WorkspaceRoleAssignments::createForLiveWorkspace()
)
);
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,30 +5,11 @@
<h2>{neos:backend.translate(id: 'sites.new', value: 'New site', source: 'Modules')}</h2>

<div class="neos-row-fluid">
<f:form action="importSite">
<fieldset class="neos-span3">
<legend>{neos:backend.translate(id: 'sites.import', value: 'Import a site', source: 'Modules')}</legend>
<f:if condition="{sitePackages -> f:count()} > 0">
<f:then>
<div class="neos-control-group">
<label class="neos-control-label" for="site">{neos:backend.translate(id: 'sites.select', value: 'Select a site package', source: 'Modules')}</label>
<div class="neos-controls neos-select">
<f:form.select name="packageKey" options="{sitePackages}" optionLabelField="packageKey" optionValueField="packageKey" id="site" class="neos-span12" />
</div>
</div>
<f:form.submit value="{neos:backend.translate(id: 'sites.import', value: 'Import Site', source: 'Modules')}" class="neos-button neos-button-primary" />
</f:then>
<f:else>
<p>{neos:backend.translate(id: 'sites.noPackackeInfo', value: 'No site packages are available. Make sure you have an active site package.', source: 'Modules')}
</p>
</f:else>
</f:if>
</fieldset>
</f:form>

<f:form action="createSiteNode">
<fieldset class="neos-span3 neos-offset1">
<fieldset class="neos-span3">
<legend>{neos:backend.translate(id: 'sites.createBlank', value: 'Create a blank site', source: 'Modules')}</legend>
{neos:backend.translate(id: 'sites.creationContentRepository', value: 'In the content repository: "{defaultContentRepositoryForNewSites}"', source: 'Modules', arguments: {0: defaultContentRepositoryForNewSites})}

<f:if condition="{sitePackages -> f:count()} > 0">
<f:then>
<div class="neos-control-group">
Expand Down Expand Up @@ -59,6 +40,7 @@ <h2>{neos:backend.translate(id: 'sites.new', value: 'New site', source: 'Modules
</f:if>
</fieldset>
</f:form>

</div>
<div class="neos-footer">
<f:link.action action="index" class="neos-button">{neos:backend.translate(id: 'cancel', value: 'Cancel')}</f:link.action>
Expand Down
15 changes: 3 additions & 12 deletions Neos.Neos/Resources/Private/Translations/en/Modules.xlf
Original file line number Diff line number Diff line change
Expand Up @@ -359,9 +359,6 @@
<trans-unit id="sites.confirmDelete" xml:space="preserve">
<source>Yes, delete the site</source>
</trans-unit>
<trans-unit id="sites.import" xml:space="preserve">
<source>Import a site</source>
</trans-unit>
<trans-unit id="sites.select" xml:space="preserve">
<source>Select a site package</source>
</trans-unit>
Expand All @@ -371,6 +368,9 @@
<trans-unit id="sites.createBlank" xml:space="preserve">
<source>Create a blank site</source>
</trans-unit>
<trans-unit id="sites.creationContentRepository" xml:space="preserve">
<source>In the content repository: "{0}"</source>
</trans-unit>
<trans-unit id="sites.documentType" xml:space="preserve">
<source>Select a document nodeType</source>
</trans-unit>
Expand Down Expand Up @@ -545,15 +545,6 @@ Click on one of the nodes to only see its fallbacks and variants. Click again to
<trans-unit id="sites.update.body" xml:space="preserve">
<source>The site "{0}" has been updated.</source>
</trans-unit>
<trans-unit id="sites.theSiteHasBeenImported.body" xml:space="preserve">
<source>The site has been imported.</source>
</trans-unit>
<trans-unit id="sites.importError.title" xml:space="preserve">
<source>Import error</source>
</trans-unit>
<trans-unit id="sites.importError.body" xml:space="preserve">
<source>Error: During the import of the "Sites.xml" from the package "{0}" an exception occurred: {1}</source>
</trans-unit>
<trans-unit id="sites.siteCreationError.siteWithSiteNodeNameAlreadyExists.title" xml:space="preserve">
<source>Site creation error</source>
</trans-unit>
Expand Down
Loading