Attainly/backend/tests/Feature/Element/EloquentElementRepositoryTest.php

112 lines
3.5 KiB
PHP

<?php
namespace Tests\Feature\Element;
use App\Element\CreateElementDto;
use App\Element\ElementRepository;
use App\Set\CreateSetDto;
use App\Set\Set;
use App\Set\SetRepository;
use App\Shared\ValueObject\EmailAddress;
use App\User\CreateUserDto;
use App\User\UserRepository;
use DomainException;
use Illuminate\Foundation\Testing\RefreshDatabase;
use Tests\TestCase;
class EloquentElementRepositoryTest extends TestCase
{
use RefreshDatabase;
public function testItPersistsNestedElementsInSiblingOrder(): void
{
$set = $this->createSet('Bible');
$repository = app(ElementRepository::class);
$genesisBook = $repository->create(new CreateElementDto(
set: $set,
name: 'Genesis',
kind: 'book',
parentElement: null,
));
$exodusBook = $repository->create(new CreateElementDto(
set: $set,
name: 'Exodus',
kind: 'book',
parentElement: null,
));
$genesisPortion = $repository->create(new CreateElementDto(
set: $set,
name: 'Genesis',
kind: 'portion',
parentElement: $genesisBook,
));
$noahPortion = $repository->create(new CreateElementDto(
set: $set,
name: 'Noah',
kind: 'portion',
parentElement: $genesisBook,
));
$this->assertSame(1, $genesisBook->getPosition());
$this->assertSame(2, $exodusBook->getPosition());
$this->assertSame(1, $genesisPortion->getPosition());
$this->assertSame(2, $noahPortion->getPosition());
$this->assertDatabaseHas('elements', [
'id' => $genesisPortion->getId(),
'set_id' => $set->getId(),
'name' => 'Genesis',
'kind' => 'portion',
'parent_element_id' => $genesisBook->getId(),
'position' => 1,
]);
$foundElement = $repository->find($noahPortion->getId());
$this->assertNotNull($foundElement);
$this->assertSame('Noah', $foundElement->getName());
$this->assertSame('portion', $foundElement->getKind());
$this->assertSame($set->getId(), $foundElement->getSet()->getId());
$this->assertSame(
$genesisBook->getId(),
$foundElement->getParentElement()?->getId(),
);
}
public function testItRejectsAParentFromAnotherSet(): void
{
$bible = $this->createSet('Bible');
$course = $this->createSet('Course');
$repository = app(ElementRepository::class);
$book = $repository->create(new CreateElementDto(
set: $bible,
name: 'Genesis',
kind: 'book',
parentElement: null,
));
$this->expectException(DomainException::class);
$this->expectExceptionMessage(
'parent element must belong to the same set',
);
$repository->create(new CreateElementDto(
set: $course,
name: 'Invalid lesson',
kind: 'lesson',
parentElement: $book,
));
}
private function createSet(string $name): Set
{
$creator = app(UserRepository::class)->create(new CreateUserDto(
email: new EmailAddress(strtolower($name) . '@example.com'),
passwordHash: 'hashed-password',
));
return app(SetRepository::class)->create(new CreateSetDto(
name: $name,
creator: $creator,
));
}
}