According to this article which shows how to create strictly typed arrays and collections in Php7, php-generic generator was born.
There is some discusion about generic in Php but who knows when it comes to us.
It is not exacly what you know from Java or C++ where generic looks like
Vector<int>(), Array<bool>() or Vector<\Namespace\Entity\User>().
Here generics looks like VectorInt, ArrayBool and VectorUser
so I hope when they come to nativ Php all what you need to do will be:
- Replace all
VectorType,ArrayTypetoVector<Type>,array<Type>, - Delete directory where you store all generated array/vector,
- Enjoy a nice day.
They are not collections like Doctrine or Laravel Collections. They are like normal php array
which can store values one type. array<int> can store only numeric values which will converted to int
so you can not push 'some string value' to it.
$ composer require d0niek/php-genericThere is a bin command that you should find in vendor/bin or somewhere else according to your composer.json settings.
To generate a generic array run:
$ bin/generic generate:array [-s|--save [SAVE]] [--] <type> <namespace>where:
- -s|--saveCollection - do you want to save generated array for future regenerate (default true),
- type - is a type of generic array. It can be simple type (bool, int, float, string, array) or complex type (\YourApp\Module\Repository\User),
- namespace - is a namespace where new generic array will be save. Remember that namespace's directory have to exists. To separate namespace parts use \\ or / to speed up typing if your namespace is 1:1 with your directory structure
For example you have project in /path/to/project and your composer.json contains this kind of entry:
"autoload": {
"psr-4": {
"VendorName\\AppName\\": "src/"
}
}Now, when you call command like this:
$ bin/generic generate:array int VendorName\\AppName\\Collectionsnew generic array ArrayInt will be save to /path/to/project/src/Collections/ directory.
If this directory does not exists, exceptions will be throw.
Tip! Store all php-generics in one diretory and add it to .gitignore. When php will start support generics, replace
ArrayInttoarray<int>and remove php-generic directory.
You can alse generate generic \Ds\Vector (it is new data structure since Php7, here you can and you should read about it!). To do this just run:
$ bin/generic generate:vector [-s|--save [SAVE]] [--] <type> <namespace>parameters means exacly the same whats means when you run generate:array.
By defaule generated array/vector are save in generated-colletions.json file in your root app path.
Keep this file in repository and ignore all generated php-generics. When you clone repository,
after composer install run:
$ bin/generic collections:regenerateand all your collections will be regenerate.
Now you can create in easy way specific generic when you are selecting data from DB
class UserRepository implements UserRepositoryInterface
{
...
/**
* @inheritDoc
*/
public function findAll(): VectorUser
{
$users = new VectorUser();
$mysqli = new \mysqli('localhost:3306', 'user', 'password', 'db');
$mysqliResult = $mysqli->query('SELECT id, name FROM users LIMIT 10');
if ($mysqliResult !== false) {
while (($user = $mysqliResult->fetch_object(User::class)) !== null) {
$users->push($user);
}
}
$mysqli->close();
return $users;
}
...
}Before you run tests remember to regenerate collections. Run:
$ bin/generic collections:regenerateand now you can run
$ phpunit