mirror of
https://github.com/DesignPatternsPHP/DesignPatternsPHP.git
synced 2025-07-18 05:41:14 +02:00
introduced PostId and PostStatus and changed naming from Storage to Persistence
This commit is contained in:
More/Repository
locale
@@ -5,10 +5,15 @@ namespace DesignPatterns\More\Repository\Domain;
|
||||
class Post
|
||||
{
|
||||
/**
|
||||
* @var int
|
||||
* @var PostId
|
||||
*/
|
||||
private $id;
|
||||
|
||||
/**
|
||||
* @var PostStatus
|
||||
*/
|
||||
private $status;
|
||||
|
||||
/**
|
||||
* @var string
|
||||
*/
|
||||
@@ -19,10 +24,11 @@ class Post
|
||||
*/
|
||||
private $text;
|
||||
|
||||
public static function draft(int $id, string $title, string $text): Post
|
||||
public static function draft(PostId $id, string $title, string $text): Post
|
||||
{
|
||||
return new self(
|
||||
$id,
|
||||
PostStatus::fromString(PostStatus::STATE_DRAFT),
|
||||
$title,
|
||||
$text
|
||||
);
|
||||
@@ -31,29 +37,37 @@ class Post
|
||||
public static function fromState(array $state): Post
|
||||
{
|
||||
return new self(
|
||||
$state['id'],
|
||||
PostId::fromInt($state['id']),
|
||||
PostStatus::fromInt($state['statusId']),
|
||||
$state['title'],
|
||||
$state['text']
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param int $id
|
||||
* @param string $text
|
||||
* @param PostId $id
|
||||
* @param PostStatus $status
|
||||
* @param string $title
|
||||
* @param string $text
|
||||
*/
|
||||
private function __construct(int $id, string $title, string $text)
|
||||
private function __construct(PostId $id, PostStatus $status, string $title, string $text)
|
||||
{
|
||||
$this->id = $id;
|
||||
$this->status = $status;
|
||||
$this->text = $text;
|
||||
$this->title = $title;
|
||||
}
|
||||
|
||||
public function getId(): int
|
||||
public function getId(): PostId
|
||||
{
|
||||
return $this->id;
|
||||
}
|
||||
|
||||
public function getStatus(): PostStatus
|
||||
{
|
||||
return $this->status;
|
||||
}
|
||||
|
||||
public function getText(): string
|
||||
{
|
||||
return $this->text;
|
||||
|
42
More/Repository/Domain/PostId.php
Normal file
42
More/Repository/Domain/PostId.php
Normal file
@@ -0,0 +1,42 @@
|
||||
<?php
|
||||
|
||||
namespace DesignPatterns\More\Repository\Domain;
|
||||
|
||||
/**
|
||||
* This is a perfect example of a value object that is identifiable by it's value alone and
|
||||
* is guaranteed to be valid each time an instance is created. Another important property of value objects
|
||||
* is immutability.
|
||||
*
|
||||
* Notice also the use of a named constructor (fromInt) which adds a little context when creating an instance.
|
||||
*/
|
||||
class PostId
|
||||
{
|
||||
/**
|
||||
* @var int
|
||||
*/
|
||||
private $id;
|
||||
|
||||
public static function fromInt(int $id)
|
||||
{
|
||||
self::ensureIsValid($id);
|
||||
|
||||
return new self($id);
|
||||
}
|
||||
|
||||
private function __construct(int $id)
|
||||
{
|
||||
$this->id = $id;
|
||||
}
|
||||
|
||||
public function toInt(): int
|
||||
{
|
||||
return $this->id;
|
||||
}
|
||||
|
||||
private static function ensureIsValid(int $id)
|
||||
{
|
||||
if ($id <= 0) {
|
||||
throw new \InvalidArgumentException('Invalid PostId given');
|
||||
}
|
||||
}
|
||||
}
|
80
More/Repository/Domain/PostStatus.php
Normal file
80
More/Repository/Domain/PostStatus.php
Normal file
@@ -0,0 +1,80 @@
|
||||
<?php
|
||||
|
||||
namespace DesignPatterns\More\Repository\Domain;
|
||||
|
||||
/**
|
||||
* Like PostId, this is a value object which holds the value of the current status of a Post. It can be constructed
|
||||
* either from a string or int and is able to validate itself. An instance can then be converted back to int or string.
|
||||
*/
|
||||
class PostStatus
|
||||
{
|
||||
const STATE_DRAFT_ID = 1;
|
||||
const STATE_PUBLISHED_ID = 2;
|
||||
|
||||
const STATE_DRAFT = 'draft';
|
||||
const STATE_PUBLISHED = 'published';
|
||||
|
||||
private static $validStates = [
|
||||
self::STATE_DRAFT_ID => self::STATE_DRAFT,
|
||||
self::STATE_PUBLISHED_ID => self::STATE_PUBLISHED,
|
||||
];
|
||||
|
||||
/**
|
||||
* @var int
|
||||
*/
|
||||
private $id;
|
||||
|
||||
/**
|
||||
* @var string
|
||||
*/
|
||||
private $name;
|
||||
|
||||
public static function fromInt(int $statusId)
|
||||
{
|
||||
self::ensureIsValidId($statusId);
|
||||
|
||||
return new self($statusId, self::$validStates[$statusId]);
|
||||
}
|
||||
|
||||
public static function fromString(string $status)
|
||||
{
|
||||
self::ensureIsValidName($status);
|
||||
|
||||
return new self(array_search($status, self::$validStates), $status);
|
||||
}
|
||||
|
||||
private function __construct(int $id, string $name)
|
||||
{
|
||||
$this->id = $id;
|
||||
$this->name = $name;
|
||||
}
|
||||
|
||||
public function toInt(): int
|
||||
{
|
||||
return $this->id;
|
||||
}
|
||||
|
||||
/**
|
||||
* there is a reason that I avoid using __toString() as it operates outside of the stack in PHP
|
||||
* and is therefor not able to operate well with exceptions
|
||||
*/
|
||||
public function toString(): string
|
||||
{
|
||||
return $this->name;
|
||||
}
|
||||
|
||||
private static function ensureIsValidId(int $status)
|
||||
{
|
||||
if (!in_array($status, array_keys(self::$validStates), true)) {
|
||||
throw new \InvalidArgumentException('Invalid status id given');
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
private static function ensureIsValidName(string $status)
|
||||
{
|
||||
if (!in_array($status, self::$validStates, true)) {
|
||||
throw new \InvalidArgumentException('Invalid status name given');
|
||||
}
|
||||
}
|
||||
}
|
@@ -2,7 +2,7 @@
|
||||
|
||||
namespace DesignPatterns\More\Repository;
|
||||
|
||||
class MemoryStorage implements Storage
|
||||
class InMemoryPersistence implements Persistence
|
||||
{
|
||||
/**
|
||||
* @var array
|
@@ -2,7 +2,7 @@
|
||||
|
||||
namespace DesignPatterns\More\Repository;
|
||||
|
||||
interface Storage
|
||||
interface Persistence
|
||||
{
|
||||
public function generateId(): int;
|
||||
|
@@ -3,9 +3,10 @@
|
||||
namespace DesignPatterns\More\Repository;
|
||||
|
||||
use DesignPatterns\More\Repository\Domain\Post;
|
||||
use DesignPatterns\More\Repository\Domain\PostId;
|
||||
|
||||
/**
|
||||
* This class is situated between Entity layer (class Post) and access object layer (MemoryStorage).
|
||||
* This class is situated between Entity layer (class Post) and access object layer (Persistence).
|
||||
*
|
||||
* Repository encapsulates the set of objects persisted in a data store and the operations performed over them
|
||||
* providing a more object-oriented view of the persistence layer
|
||||
@@ -16,26 +17,26 @@ use DesignPatterns\More\Repository\Domain\Post;
|
||||
class PostRepository
|
||||
{
|
||||
/**
|
||||
* @var Storage
|
||||
* @var Persistence
|
||||
*/
|
||||
private $persistence;
|
||||
|
||||
public function __construct(Storage $persistence)
|
||||
public function __construct(Persistence $persistence)
|
||||
{
|
||||
$this->persistence = $persistence;
|
||||
}
|
||||
|
||||
public function generateId(): int
|
||||
public function generateId(): PostId
|
||||
{
|
||||
return $this->persistence->generateId();
|
||||
return PostId::fromInt($this->persistence->generateId());
|
||||
}
|
||||
|
||||
public function findById(int $id): Post
|
||||
public function findById(PostId $id): Post
|
||||
{
|
||||
try {
|
||||
$arrayData = $this->persistence->retrieve($id);
|
||||
$arrayData = $this->persistence->retrieve($id->toInt());
|
||||
} catch (\OutOfBoundsException $e) {
|
||||
throw new \OutOfBoundsException(sprintf('Post with id %d does not exist', $id), 0, $e);
|
||||
throw new \OutOfBoundsException(sprintf('Post with id %d does not exist', $id->toInt()), 0, $e);
|
||||
}
|
||||
|
||||
return Post::fromState($arrayData);
|
||||
@@ -44,7 +45,8 @@ class PostRepository
|
||||
public function save(Post $post)
|
||||
{
|
||||
$this->persistence->persist([
|
||||
'id' => $post->getId(),
|
||||
'id' => $post->getId()->toInt(),
|
||||
'statusId' => $post->getStatus()->toInt(),
|
||||
'text' => $post->getText(),
|
||||
'title' => $post->getTitle(),
|
||||
]);
|
||||
|
@@ -33,7 +33,19 @@ You can also find this code on `GitHub`_
|
||||
|
||||
Post.php
|
||||
|
||||
.. literalinclude:: Post.php
|
||||
.. literalinclude:: Domain/Post.php
|
||||
:language: php
|
||||
:linenos:
|
||||
|
||||
PostId.php
|
||||
|
||||
.. literalinclude:: Domain/PostId.php
|
||||
:language: php
|
||||
:linenos:
|
||||
|
||||
PostStatus.php
|
||||
|
||||
.. literalinclude:: Domain/PostStatus.php
|
||||
:language: php
|
||||
:linenos:
|
||||
|
||||
@@ -43,18 +55,24 @@ PostRepository.php
|
||||
:language: php
|
||||
:linenos:
|
||||
|
||||
MemoryStorage.php
|
||||
Persistence.php
|
||||
|
||||
.. literalinclude:: MemoryStorage.php
|
||||
.. literalinclude:: InMemoryPersistence.php
|
||||
:language: php
|
||||
:linenos:
|
||||
|
||||
InMemoryPersistence.php
|
||||
|
||||
.. literalinclude:: InMemoryPersistence.php
|
||||
:language: php
|
||||
:linenos:
|
||||
|
||||
Test
|
||||
----
|
||||
|
||||
Tests/RepositoryTest.php
|
||||
Tests/PostRepositoryTest.php
|
||||
|
||||
.. literalinclude:: Tests/RepositoryTest.php
|
||||
.. literalinclude:: Tests/PostRepositoryTest.php
|
||||
:language: php
|
||||
:linenos:
|
||||
|
||||
|
@@ -2,7 +2,9 @@
|
||||
|
||||
namespace DesignPatterns\More\Repository\Tests;
|
||||
|
||||
use DesignPatterns\More\Repository\MemoryStorage;
|
||||
use DesignPatterns\More\Repository\Domain\PostId;
|
||||
use DesignPatterns\More\Repository\Domain\PostStatus;
|
||||
use DesignPatterns\More\Repository\InMemoryPersistence;
|
||||
use DesignPatterns\More\Repository\Domain\Post;
|
||||
use DesignPatterns\More\Repository\PostRepository;
|
||||
use PHPUnit\Framework\TestCase;
|
||||
@@ -16,12 +18,12 @@ class PostRepositoryTest extends TestCase
|
||||
|
||||
protected function setUp()
|
||||
{
|
||||
$this->repository = new PostRepository(new MemoryStorage());
|
||||
$this->repository = new PostRepository(new InMemoryPersistence());
|
||||
}
|
||||
|
||||
public function testCanGenerateId()
|
||||
{
|
||||
$this->assertEquals(1, $this->repository->generateId());
|
||||
$this->assertEquals(1, $this->repository->generateId()->toInt());
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -30,7 +32,7 @@ class PostRepositoryTest extends TestCase
|
||||
*/
|
||||
public function testThrowsExceptionWhenTryingToFindPostWhichDoesNotExist()
|
||||
{
|
||||
$this->repository->findById(42);
|
||||
$this->repository->findById(PostId::fromInt(42));
|
||||
}
|
||||
|
||||
public function testCanPersistPostDraft()
|
||||
@@ -39,6 +41,9 @@ class PostRepositoryTest extends TestCase
|
||||
$post = Post::draft($postId, 'Repository Pattern', 'Design Patterns PHP');
|
||||
$this->repository->save($post);
|
||||
|
||||
$this->repository->findById($postId);
|
||||
|
||||
$this->assertEquals($postId, $this->repository->findById($postId)->getId());
|
||||
$this->assertEquals(PostStatus::STATE_DRAFT, $post->getStatus()->toString());
|
||||
}
|
||||
}
|
||||
|
@@ -3,20 +3,24 @@
|
||||
<ID>PHP</ID>
|
||||
<OriginalElement>\DesignPatterns\More\Repository\PostRepository</OriginalElement>
|
||||
<nodes>
|
||||
<node x="415.0" y="0.0">\DesignPatterns\More\Repository\Storage</node>
|
||||
<node x="405.0" y="137.0">\DesignPatterns\More\Repository\MemoryStorage</node>
|
||||
<node x="0.0" y="0.0">\DesignPatterns\More\Repository\Post</node>
|
||||
<node x="0.0" y="373.0">\DesignPatterns\More\Repository\PostRepository</node>
|
||||
<node x="283.0" y="167.0">\DesignPatterns\More\Repository\InMemoryPersistence</node>
|
||||
<node x="0.0" y="0.0">\DesignPatterns\More\Repository\Domain\PostStatus</node>
|
||||
<node x="590.0" y="385.0">\DesignPatterns\More\Repository\Domain\PostId</node>
|
||||
<node x="0.0" y="385.0">\DesignPatterns\More\Repository\Domain\Post</node>
|
||||
<node x="289.0" y="0.0">\DesignPatterns\More\Repository\Persistence</node>
|
||||
<node x="320.0" y="385.0">\DesignPatterns\More\Repository\PostRepository</node>
|
||||
</nodes>
|
||||
<notes />
|
||||
<edges>
|
||||
<edge source="\DesignPatterns\More\Repository\MemoryStorage" target="\DesignPatterns\More\Repository\Storage">
|
||||
<point x="0.0" y="-74.5" />
|
||||
<point x="0.0" y="43.5" />
|
||||
<edge source="\DesignPatterns\More\Repository\InMemoryPersistence" target="\DesignPatterns\More\Repository\Persistence">
|
||||
<point x="0.0" y="-81.0" />
|
||||
<point x="0.0" y="58.5" />
|
||||
</edge>
|
||||
</edges>
|
||||
<settings layout="Hierarchic Group" zoom="0.7394636015325671" x="299.5" y="251.0" />
|
||||
<SelectedNodes />
|
||||
<settings layout="Hierarchic Group" zoom="1.0" x="666.5" y="488.0" />
|
||||
<SelectedNodes>
|
||||
<node>\DesignPatterns\More\Repository\PostRepository</node>
|
||||
</SelectedNodes>
|
||||
<Categories>
|
||||
<Category>Fields</Category>
|
||||
<Category>Constants</Category>
|
||||
|
Binary file not shown.
Before ![]() (image error) Size: 26 KiB After ![]() (image error) Size: 128 KiB ![]() ![]() |
File diff suppressed because one or more lines are too long
Before (image error) Size: 89 KiB After (image error) Size: 184 KiB |
@@ -64,11 +64,11 @@ msgid "PostRepository.php"
|
||||
msgstr ""
|
||||
|
||||
#: ../../More/Repository/README.rst:46
|
||||
msgid "Storage.php"
|
||||
msgid "Persistence.php"
|
||||
msgstr ""
|
||||
|
||||
#: ../../More/Repository/README.rst:52
|
||||
msgid "MemoryStorage.php"
|
||||
msgid "InMemoryPersistence.php"
|
||||
msgstr ""
|
||||
|
||||
#: ../../More/Repository/README.rst:59
|
||||
|
@@ -75,12 +75,12 @@ msgid "PostRepository.php"
|
||||
msgstr "PostRepository.php"
|
||||
|
||||
#: ../../More/Repository/README.rst:46
|
||||
msgid "Storage.php"
|
||||
msgstr "Storage.php"
|
||||
msgid "Persistence.php"
|
||||
msgstr "Persistence.php"
|
||||
|
||||
#: ../../More/Repository/README.rst:52
|
||||
msgid "MemoryStorage.php"
|
||||
msgstr "MemoryStorage.php"
|
||||
msgid "InMemoryPersistence.php"
|
||||
msgstr "InMemoryPersistence.php"
|
||||
|
||||
#: ../../More/Repository/README.rst:59
|
||||
msgid "Test"
|
||||
|
@@ -64,11 +64,11 @@ msgid "PostRepository.php"
|
||||
msgstr ""
|
||||
|
||||
#: ../../More/Repository/README.rst:46
|
||||
msgid "Storage.php"
|
||||
msgid "Persistence.php"
|
||||
msgstr ""
|
||||
|
||||
#: ../../More/Repository/README.rst:52
|
||||
msgid "MemoryStorage.php"
|
||||
msgid "InMemoryPersistence.php"
|
||||
msgstr ""
|
||||
|
||||
#: ../../More/Repository/README.rst:59
|
||||
|
@@ -72,12 +72,12 @@ msgid "PostRepository.php"
|
||||
msgstr "PostRepository.php"
|
||||
|
||||
#: ../../More/Repository/README.rst:46
|
||||
msgid "Storage.php"
|
||||
msgstr "Storage.php"
|
||||
msgid "Persistence.php"
|
||||
msgstr "Persistence.php"
|
||||
|
||||
#: ../../More/Repository/README.rst:52
|
||||
msgid "MemoryStorage.php"
|
||||
msgstr "MemoryStorage.php"
|
||||
msgid "InMemoryPersistence.php"
|
||||
msgstr "InMemoryPersistence.php"
|
||||
|
||||
#: ../../More/Repository/README.rst:59
|
||||
msgid "Test"
|
||||
|
@@ -72,11 +72,11 @@ msgid "PostRepository.php"
|
||||
msgstr ""
|
||||
|
||||
#: ../../More/Repository/README.rst:46
|
||||
msgid "Storage.php"
|
||||
msgid "Persistence.php"
|
||||
msgstr ""
|
||||
|
||||
#: ../../More/Repository/README.rst:52
|
||||
msgid "MemoryStorage.php"
|
||||
msgid "InMemoryPersistence.php"
|
||||
msgstr ""
|
||||
|
||||
#: ../../More/Repository/README.rst:59
|
||||
|
@@ -73,12 +73,12 @@ msgid "PostRepository.php"
|
||||
msgstr "PostRepository.php"
|
||||
|
||||
#: ../../More/Repository/README.rst:46
|
||||
msgid "Storage.php"
|
||||
msgstr "Storage.php"
|
||||
msgid "Persistence.php"
|
||||
msgstr "Persistence.php"
|
||||
|
||||
#: ../../More/Repository/README.rst:52
|
||||
msgid "MemoryStorage.php"
|
||||
msgstr "MemoryStorage.php"
|
||||
msgid "InMemoryPersistence.php"
|
||||
msgstr "InMemoryPersistence.php"
|
||||
|
||||
#: ../../More/Repository/README.rst:59
|
||||
msgid "Test"
|
||||
|
@@ -64,11 +64,11 @@ msgid "PostRepository.php"
|
||||
msgstr ""
|
||||
|
||||
#: ../../More/Repository/README.rst:46
|
||||
msgid "Storage.php"
|
||||
msgid "Persistence.php"
|
||||
msgstr ""
|
||||
|
||||
#: ../../More/Repository/README.rst:52
|
||||
msgid "MemoryStorage.php"
|
||||
msgid "InMemoryPersistence.php"
|
||||
msgstr ""
|
||||
|
||||
#: ../../More/Repository/README.rst:59
|
||||
|
Reference in New Issue
Block a user