implement EmailAddress value object

immutable readonly. trims whitespace, splits on @, lowercases the
domain (local-part case preserved per RFC 5321), validates with
FILTER_VALIDATE_EMAIL after normalization. throws
InvalidArgumentException on empty / missing-@ / malformed input.
exposes value(), getDomain(), equals(), __toString(). all 7
EmailAddressTest cases green; 9 tests total pass.
This commit is contained in:
yisroel 2026-05-06 14:52:45 +03:00
parent f862348a31
commit 4f6ac876ce

View file

@ -0,0 +1,53 @@
<?php
namespace App\Shared\ValueObject;
use InvalidArgumentException;
final readonly class EmailAddress
{
private string $normalized;
private string $domain;
private const ERROR_MESSAGE = 'Invalid email address:';
public function __construct(string $email)
{
$trimmed = trim($email);
if ($trimmed === '' || ! str_contains($trimmed, '@')) {
throw new InvalidArgumentException(self::ERROR_MESSAGE." $email");
}
[$local, $domain] = explode('@', $trimmed, 2);
$this->domain = mb_strtolower($domain);
$normalized = $local.'@'.$this->domain;
if (filter_var($normalized, FILTER_VALIDATE_EMAIL) === false) {
throw new InvalidArgumentException(self::ERROR_MESSAGE." $email");
}
$this->normalized = $normalized;
}
public function value(): string
{
return $this->normalized;
}
public function equals(self $other): bool
{
return $this->normalized === $other->normalized;
}
public function getDomain(): string
{
return $this->domain;
}
public function __toString(): string
{
return $this->normalized;
}
}