Last active
August 29, 2015 14:05
-
-
Save tomphp/6ab886465a0626a352a3 to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
/* | |
* Say you have an entity class which has no need to expose its internal data | |
* fields in the business layer like so: | |
*/ | |
class LibraryBook | |
{ | |
/** @var string */ | |
private $title; | |
/** @var bool */ | |
private $isOnLoan; | |
/** @var int */ | |
private $numberOfPages; | |
/** | |
* @param string $title | |
* @param bool $isOnLoan | |
* @param int $numberOfPages | |
*/ | |
public function __construct($title, $isOnLoan, $numberOfPages) | |
{ | |
$this->title = $title; | |
$this->isOnLoan = $isOnLoan; | |
$this->numberOfPages = $numberOfPages; | |
} | |
public function checkOut() | |
{ | |
$this->isOnLoan = true; | |
} | |
public function checkIn() | |
{ | |
$this->isOnLoan = false; | |
} | |
/** @param int $numberOfPages */ | |
public function ripOutPages($numberOfPages) | |
{ | |
$this->numberOfPages -= $numberOfPages; | |
} | |
} | |
/* | |
* How do you prefer to expose the internal fields for display & for your | |
* storage layer to access them? | |
*/ | |
// Option 1: Add getters | |
class LibraryBook | |
{ | |
// ... | |
public function getTitle() | |
{ | |
return $this->title; | |
} | |
public function isOnLoan() | |
{ | |
return $this->isOnLoan; | |
} | |
public function getNumberOfPages() | |
{ | |
return $this->numberOfPages; | |
} | |
} | |
// Option 2: Return an array | |
class LibraryBook | |
{ | |
// ... | |
public function asArray() | |
{ | |
return [ | |
'title' => $this->title, | |
'onLoan' => $this->isOnLoan, | |
'numberOfPages' => $this->numberOfPages | |
]; | |
} | |
} | |
// Option 3: Return a DTO | |
// As Option 2 but return a BookDetails DTO object instead of a PHP array | |
class BookDetails | |
{ | |
/** @var string */ | |
private $title; | |
/** @var bool */ | |
private $isOnLoan; | |
/** @var int */ | |
private $numberOfPages; | |
/** | |
* @param string $title | |
* @param bool $isOnLoan | |
* @param int $numberOfPages | |
*/ | |
public function __construct($title, $isOnLoan, $numberOfPages) | |
{ | |
$this->title = $title; | |
$this->isOnLoan = $isOnLoan; | |
$this->numberOfPages = $numberOfPages; | |
} | |
public function getTitle() | |
{ | |
return $this->title; | |
} | |
public function isOnLoan() | |
{ | |
return $this->isOnLoan; | |
} | |
public function getNumberOfPages() | |
{ | |
return $this->numberOfPages; | |
} | |
} | |
class LibraryBook | |
{ | |
// ... | |
public function getDetails() | |
{ | |
return new BookDetails( | |
$this->title, | |
$this->isOnLoan, | |
$this->numberOfPages | |
); | |
} | |
} | |
// Option 4: Ask the entity to present it's data via an interface | |
interface BookDetailsReceiver | |
{ | |
/** @param $title string */ | |
public function setTitle($title); | |
/** @param $isOnLoan bool */ | |
public function setOnLoanStatus($isOnLoan); | |
/** @param $numPages int */ | |
public function setNumberOfPages($numPages); | |
} | |
class LibraryBook | |
{ | |
// ... | |
public function presentDetails(BookDetailsReceiver $receiver) | |
{ | |
$receiver->setTitle($this->title); | |
$receiver->setOnLoanStatus($this->isOnLoan); | |
$receiver->setNumberOfPages($this->numberOfPages); | |
} | |
} | |
// Option 5: Some other way, please describe |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment