generated from yiisoft/package-template
-
-
Notifications
You must be signed in to change notification settings - Fork 3
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
Showing
6 changed files
with
247 additions
and
46 deletions.
There are no files selected for viewing
This file contains 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
This file contains 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
This file contains 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
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,57 @@ | ||
# General usage | ||
|
||
To hydrate existing object: | ||
|
||
```php | ||
use Yiisoft\Hydrator\Hydrator; | ||
|
||
$hydrator = new Hydrator(); | ||
$hydrator->hydrate($object, $data); | ||
``` | ||
|
||
To create a new object and fill it with the data: | ||
|
||
```php | ||
use Yiisoft\Hydrator\Hydrator; | ||
|
||
$hydrator = new Hydrator(); | ||
$object = $hydrator->create(MyClass::class, $data); | ||
``` | ||
|
||
To pass arguments to the constructor of a nested object, use nested array or dot-notation: | ||
|
||
```php | ||
final class Engine | ||
{ | ||
public function __construct( | ||
private string $name, | ||
) {} | ||
} | ||
|
||
final class Car | ||
{ | ||
public function __construct( | ||
private string $name, | ||
private Engine $engine, | ||
) {} | ||
} | ||
|
||
// nested array | ||
$object = $hydrator->create(Car::class, [ | ||
'name' => 'Ferrari', | ||
'engine' => [ | ||
'name' => 'V8', | ||
] | ||
]); | ||
|
||
// or dot-notation | ||
$object = $hydrator->create(Car::class, [ | ||
'name' => 'Ferrari', | ||
'engine.name' => 'V8', | ||
]); | ||
``` | ||
|
||
That would pass the `name` constructor argument of the `Car` object and create a new `Engine` object for `engine` | ||
argument passing `V8` as the `name` argument to its constructor. | ||
|
||
// TODO: strict mode |
This file contains 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
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,67 @@ | ||
# Mapping | ||
|
||
In many cases, class attribute names differ from data keys you fill or create objects of the class with. For example, | ||
we have a blog post class: | ||
|
||
```php | ||
final class Post | ||
{ | ||
public function __construct( | ||
private string $title, | ||
private string $body, | ||
) { | ||
} | ||
|
||
public function getTitle(): string | ||
{ | ||
return $this->title; | ||
} | ||
|
||
public function getBody(): string | ||
{ | ||
return $this->body; | ||
} | ||
} | ||
``` | ||
|
||
But the data you have has differently named keys: | ||
|
||
```php | ||
$data = ['header' => 'First post', 'text' => 'Hello, world!']; | ||
``` | ||
|
||
Hydrator allows you to map data: | ||
|
||
```php | ||
$hydrator = new Hydrator(); | ||
|
||
$object = new SimpleClass(); | ||
|
||
$map = ['title' => 'header', 'body' => 'text'],; | ||
$hydrator->hydrate($object, new ArrayData($data, $map)); | ||
``` | ||
|
||
This way we take `header` key for `title` and `text` key for `body`. | ||
|
||
## Using attributes | ||
|
||
Alternatively to specifying mapping as an array, you can use `Data` attribute to define mapping inline: | ||
|
||
```php | ||
use \Yiisoft\Hydrator\Attribute\Parameter\Data; | ||
|
||
final class Person | ||
{ | ||
public function __construct( | ||
#[Data('first_name')] | ||
private string $firstName, | ||
#[Data('last_name')] | ||
private string $lastName, | ||
) {} | ||
} | ||
|
||
$person = $hydrator->create(Person::class, [ | ||
'first_name' => 'John', | ||
'last_name' => 'Doe', | ||
]); | ||
``` |
This file contains 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
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,117 @@ | ||
# Typecasting | ||
|
||
When PHP types are defined in the class, type-casting automatically happens on object creation or hydration: | ||
|
||
```php | ||
final class Lock | ||
{ | ||
public function __construct( | ||
private string $name, | ||
private bool $isLocked | ||
) | ||
{ | ||
} | ||
} | ||
|
||
$hydrator = new Hydrator(); | ||
$lock = $hydrator->create(Lock::class, ['name' => 'The lock', 'isLocked' => 1]); | ||
``` | ||
|
||
## Custom type-casting | ||
|
||
You can define custom type-casters if needed: | ||
|
||
```php | ||
use Yiisoft\Hydrator\TypeCaster\TypeCastContext; | ||
use Yiisoft\Hydrator\TypeCaster\TypeCasterInterface; | ||
use Yiisoft\Hydrator\Result; | ||
use Yiisoft\Hydrator\Hydrator; | ||
use Yiisoft\Hydrator\TypeCaster\CompositeTypeCaster; | ||
|
||
final class User | ||
{ | ||
public function __construct( | ||
private string $nickname | ||
) | ||
{ | ||
} | ||
|
||
public function getNickName(): string | ||
{ | ||
return $this->nickname; | ||
} | ||
} | ||
|
||
final class NickNameTypeCaster implements TypeCasterInterface | ||
{ | ||
public function cast(mixed $value, TypeCastContext $context): Result | ||
{ | ||
$type = $context->getReflectionType(); | ||
|
||
if ( | ||
$context->getReflection()->getName() === 'author' | ||
&& $type instanceof ReflectionNamedType | ||
&& $type->isBuiltin() | ||
&& $type->getName() === 'string' | ||
&& preg_match('~^@(.*)$~', $value, $matches) | ||
) { | ||
$user = new User($matches[1]); | ||
return Result::success($user); | ||
} | ||
|
||
return Result::fail(); | ||
} | ||
} | ||
|
||
final class Post | ||
{ | ||
public function __construct( | ||
private string $title, | ||
private User $author | ||
) | ||
{ | ||
} | ||
|
||
public function getTitle(): string | ||
{ | ||
return $this->title; | ||
} | ||
|
||
public function getAuthor(): User | ||
{ | ||
return $this->author; | ||
} | ||
} | ||
|
||
$typeCaster = new CompositeTypeCaster( | ||
new NickNameTypeCaster(), | ||
); | ||
$hydrator = new Hydrator($typeCaster); | ||
|
||
$post = $hydrator->create(Post::class, ['title' => 'Example post', 'author' => '@samdark']); | ||
echo $post->getAuthor()->getNickName(); | ||
``` | ||
|
||
## Using attributes | ||
|
||
To cast a value to string explicitly, you can use `ToString` attribute: | ||
|
||
```php | ||
use \Yiisoft\Hydrator\Attribute\Parameter\ToString; | ||
|
||
class Money | ||
{ | ||
public function __construct( | ||
#[ToString] | ||
private string $value, | ||
private string $currency, | ||
) {} | ||
} | ||
|
||
$money = $hydrator->create(Money::class, [ | ||
'value' => 4200, | ||
'currency' => 'AMD', | ||
]); | ||
``` | ||
|
||
|
This file contains 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