add set deletion

This commit is contained in:
Yisroel Baum 2026-07-02 17:13:11 +03:00
parent ae48bdf93b
commit fb88bbfaa9
Signed by: yisroelbaum
GPG key ID: 0FA60884F75520A9
4 changed files with 147 additions and 0 deletions

View file

@ -0,0 +1,115 @@
<?php
namespace App\Set\UseCases\DeleteSet;
use App\Element\Element;
use App\Element\ElementRepository;
use App\Exceptions\BadRequestException;
use App\Exceptions\NotFoundException;
use App\Set\SetRepository;
use App\Shared\Files\Filesystem;
class DeleteSet
{
/**
* @var array<string, true>
*/
private array $managedFilePaths = [];
public function __construct(
private SetRepository $setRepository,
private ElementRepository $elementRepository,
private Filesystem $filesystem,
) {
}
/**
* @throws BadRequestException
* @throws NotFoundException
*/
public function execute(DeleteSetRequest $request): void
{
if ($request->id === null) {
throw new BadRequestException('setId is required');
}
$set = $this->setRepository->find($request->id);
if ($set === null) {
throw new NotFoundException('Set not found');
}
$this->managedFilePaths = [];
$this->rememberManagedFile($set->getIconImageUrl());
$elements = $this->elementRepository->findBySet($set);
foreach ($elements as $element) {
$this->rememberManagedFile($element->getIconImageUrl());
$this->rememberManagedFile($element->getShortPdfPath());
$this->rememberManagedFile($element->getLongPdfPath());
}
foreach ($this->deepestElementsFirst($elements) as $element) {
$this->elementRepository->delete($element);
}
$this->setRepository->delete($set);
foreach (array_keys($this->managedFilePaths) as $path) {
$this->filesystem->delete($path);
}
}
/**
* @param Element[] $elements
* @return Element[]
*/
private function deepestElementsFirst(array $elements): array
{
usort($elements, function (
Element $firstElement,
Element $secondElement,
): int {
$firstDepth = $this->elementDepth($firstElement);
$secondDepth = $this->elementDepth($secondElement);
if ($firstDepth === $secondDepth) {
return $secondElement->getId() <=> $firstElement->getId();
}
return $secondDepth <=> $firstDepth;
});
return $elements;
}
private function elementDepth(Element $element): int
{
$depth = 0;
$parentElement = $element->getParentElement();
while ($parentElement !== null) {
$depth++;
$parentElement = $parentElement->getParentElement();
}
return $depth;
}
private function rememberManagedFile(?string $path): void
{
if ($path === null) {
return;
}
if (! $this->isManagedFilePath($path)) {
return;
}
$this->managedFilePaths[$path] = true;
}
private function isManagedFilePath(string $path): bool
{
return str_starts_with($path, 'set-icons/')
|| str_starts_with($path, 'element-icons/')
|| str_starts_with($path, 'element-pdfs/short/')
|| str_starts_with($path, 'element-pdfs/long/');
}
}

View file

@ -0,0 +1,10 @@
<?php
namespace App\Set\UseCases\DeleteSet;
class DeleteSetRequest
{
public function __construct(public ?int $id)
{
}
}