Методы Entity

Обсуждаем, как правильно строить приложения
Ответить
paurlift
Сообщения: 26
Зарегистрирован: 2017.01.29, 20:16

Методы Entity

Сообщение paurlift »

В последнее время довольно часто встречаю мнение, что в Entity не должно быть никаких get и set методов.

Мне нравится вот такой подход наименования методов.

Код: Выделить всё


class Client
{
	private $id;
	private $name;
	private $surname ;
	
	public function __construct($id, $name, $surname )
	{
		$this->id = (int)$id;
		$this->name = $name;
		$this->surname  = $surname;
	}
	
	public function id()
	{
		return $this->id;
	}
	
	public function name()
	{
		return $this->name;
	}
	
	public function surname()
	{
		return $this->surname;
	}
	
	public function changeContactInfo($contactInfo)
	{
		$this->name = isset($contactInfo['name']) ? $contactInfo['name'] : null; 
		$this->surname = isset($contactInfo['surname ']) ? $contactInfo['surname '] : null; 
	}
}

Смысл написанного прост, не пишем get перед методами, которые просто возвращают свойства. Модель всегда валидна, а если что-то нужно установить, то это метод бизнеса и она не может называться, как setName.
Написание таких get методов видел в книге Carlos Buenosvinos PHP in DDD.

1) Кто что думает, на сколько это правильно? Возможно для вас вообще это не принципиально?
2) Где бы вы в этом примере кода (может где-то в другом месте), сделали проверку (бизнес правило) - имя пользователя и его фамилия должны иметь длину - максимум 255 символов.
3) Как вы относитесь к преобразованию типов данных из БД перед заполнением Entity в Repository ?

Код: Выделить всё

$client->id = (int)$dataSet['id'];
Проверка соблюдение инвариантов модели, её валидность и консистентность должна быть в одном месте (фабрика или конструктор), а тут получается валиндостью данных занимаешься в двух местах
zelenin
Сообщения: 10596
Зарегистрирован: 2013.04.20, 11:30

Re: Методы Entity

Сообщение zelenin »

paurlift писал(а): 2017.02.16, 22:541) Кто что думает, на сколько это правильно? Возможно для вас вообще это не принципиально?
в этой ветке много тем по ddd (почти все)
paurlift писал(а): 2017.02.16, 22:542) Где бы вы в этом примере кода (может где-то в другом месте), сделали проверку (бизнес правило) - имя пользователя и его фамилия должны иметь длину - максимум 255 символов.
где угодно, лишь бы сущность была валидна
paurlift писал(а): 2017.02.16, 22:54 3) Как вы относитесь к преобразованию типов данных из БД перед заполнением Entity в Repository ?

Код: Выделить всё

$client->id = (int)$dataSet['id'];
как к этому относиться, если это необходимо?
paurlift писал(а): 2017.02.16, 22:54 Проверка соблюдение инвариантов модели, её валидность и консистентность должна быть в одном месте (фабрика или конструктор), а тут получается валиндостью данных занимаешься в двух местах
вы все еще про репозиторий? это не проверка на валидность - это приведение типов из системы, где типы данных совсем другие.
Аватара пользователя
ElisDN
Сообщения: 5845
Зарегистрирован: 2012.10.07, 10:24
Контактная информация:

Re: Методы Entity

Сообщение ElisDN »

paurlift писал(а): 2017.02.16, 22:54 В последнее время довольно часто встречаю мнение, что в Entity не должно быть никаких get и set методов.
Не должно быть анемичных сеттеров. А геттеры вреда не приносят.
paurlift писал(а): 2017.02.16, 22:54 Мне нравится вот такой подход наименования методов... Смысл написанного прост, не пишем get перед методами, которые просто возвращают свойства.
То, что вы называете метод без get* ничего не меняет. Это так и остаётся геттером.
paurlift писал(а): 2017.02.16, 22:54 1) Кто что думает, насколько это правильно? Возможно для вас вообще это не принципиально?
В сущностях предпочитаю называть явно getName(), isDraft(), draft(). Иначе не понятно, что этот метод draft() из себя представляет (геттер это или переключатель). Только в DTO могу иногда назвать без get, так как там все методы являются геттерами. Хотя в DTO и публичных полей без геттеров хватает.
paurlift писал(а): 2017.02.16, 22:54 2) Где бы вы в этом примере кода (может где-то в другом месте), сделали проверку (бизнес правило) - имя пользователя и его фамилия должны иметь длину - максимум 255 символов.
В объекте имени:

Код: Выделить всё

class Name
{
	private $first;
	private $sur;
	
	public function __construct($first, $sur)
	{
	        Assertion::maxLength($first, 255);
	        Assertion::maxLength($sur, 255);	        
		$this->first = $first;
		$this->sur  = $sur;
	}
	
	public function getFirst()
	{
		return $this->first;
	}
	
	public function getSur()
	{
		return $this->sur;
	}
}

class Client
{
	private $id;
	private $name;
	
	public function __construct($id, Name $name)
	{
		$this->id = $id;
		$this->name = $name;
	}
	
	public function rename(Name $name)
	{
		$this->name = $name;
	}
	
	public function getId()
	{
		return $this->id;
	}
	
	public function getName()
	{
		return $this->name;
	}
}
Но Вы уверены, что длина имени это именно "бизнес-правило"?
paurlift писал(а): 2017.02.16, 22:54 3) Как вы относитесь к преобразованию типов данных из БД перед заполнением Entity в Repository? Проверка соблюдение инвариантов модели, её валидность и консистентность должна быть в одном месте (фабрика или конструктор), а тут получается валиндостью данных занимаешься в двух местах
При извлечении данных из БД валидации и прочих проверок быть не должно. Только простейшее преобразование типов (int)$row['id'].
paurlift
Сообщения: 26
Зарегистрирован: 2017.01.29, 20:16

Re: Методы Entity

Сообщение paurlift »

zelenin писал(а): 2017.02.16, 23:21 в этой ветке много тем по ddd (почти все)
Везде примеры с set и get, поэтому и спросил
zelenin писал(а): 2017.02.16, 23:21 где угодно, лишь бы сущность была валидна
Мне казалось, это должно быть где-то в одном месте (фабрике или конструкторе сущности), чтобы сущность была валидна и чтобы не делать проверку в нескольких местах.
paurlift
Сообщения: 26
Зарегистрирован: 2017.01.29, 20:16

Re: Методы Entity

Сообщение paurlift »

ElisDN писал(а): 2017.02.16, 23:30 Не должно быть анемичных сеттеров. А геттеры вреда не приносят.
Гетеры не приносят вреда, но использование приставки get, кажется, излишним. И это как-то не доменно что-ли. Но наверно действительно не принципиально.
ElisDN писал(а): 2017.02.16, 23:30 В сущностях предпочитаю называть явно getName(), isDraft(), draft(). Иначе не понятно, что этот метод draft() из себя представляет (геттер это или переключатель). Только в DTO могу иногда назвать без get, так как там все методы являются геттерами. Хотя в DTO и публичных полей без геттеров хватает.
Хороший довод. Вопрос соглашений в проекте.
ElisDN писал(а): 2017.02.16, 23:30 Но Вы уверены, что длина имени это именно "бизнес-правило"?
Не уверен, но можно так завернуть, у меня соц. сеть, фишка которой - "людям с длинными именами здесь не место" :)
А вообще интересно, даже если это не бизнес правило, а просто правило валидации, оно же тоже должно быть в модели?
Аватара пользователя
ElisDN
Сообщения: 5845
Зарегистрирован: 2012.10.07, 10:24
Контактная информация:

Re: Методы Entity

Сообщение ElisDN »

paurlift писал(а): 2017.02.17, 10:03 А вообще интересно, даже если это не бизнес правило, а просто правило валидации, оно же тоже должно быть в модели?
viewtopic.php?f=34&t=36725&p=188218#p188218
Ответить