Позволяет создавать и валидировать структуры данных, без привязки к БД / ActiveRecord / ORM.
Можно использовать как замену DTO.
Можно использовать как замену валидатора Active Record или ORM в проектах, где нет желания использовать массивные ORM.
Конечную структуру можно экспортировать в массив, далее сохранить в БД.
Кроме стандартных типов данных и валидаторов, позволяет регистрировать свои.
- не нужно создавать обилие классов под каждый тип, заполнять их полями, геттерами и сеттерами
- экономит время на разработку, количество кода в рантайме
- стандартные проверки полей типа minVal, maxVal, maxLength, defaultValue, isNullable делаются одной настройкой в файле конфигурации
- есть возможность проверить всели ли required поля заполнены
- есть слежение за состоянием изменения (получить список полей которые изменились)
- можно создавать собственные (custom) типы данных (достаточно просто)
- использует ленивую загрузку, экономит оперативную память
- значительно меньшее потребление памяти относительно DTO
- автоматическая конвертация типов, например DateTime
$record->set('dateTimeField', '2021-01-01 00:00:00');
/**
* @var \DateTime $result
*/
$result = $record->get('dateTimeField');
composer require dvelum/dr
Файл настроек реестра Records registry.php
<?php
use Dvelum\DR\Type\StringType;
use Dvelum\DR\Type\DateTimeType;
use Dvelum\DR\Record\DefaultValue\CurrentDateTimeString;
$registry = [
'records'=> [
'ClientData' => [
'fields' => [
'firstName' => [
'type' => 'string', // можно StringType::class
'minLength' => 2,
'required' => true,
],
'age' => [
'type' => 'int',
'minValue' => 18,
'default' => 18,
],
'date' => [
'type' => DateTimeType::class,
'minValue' => '2021-01-01',
'defaultValueAdapter' => CurrentDateTimeString::class
]
]
]
]
];
Использование:
<?php
use Dvelum\DR\Factory;
// получаем данные POST из запроса
$params = $psr7Request->getParsedBody();
// получаем настройки реестра
$registry = include 'registry.php';
// создаем фабрику DR
$factory = new Factory($registry);
//=== Пример 1 ================================
$record = $factory->create('ClientData');
try{
$record->setData($params);
}catch(\InvalidArgumentException $e){
// переданы невалидные данные
}
// можно проверить все ли обязательные поля переданы
if(!$record->validateRequired()->isSuccess()){
// не все обязательные поля заданы
}
//=== Пример 2 ================================
// получаем id записи из параметров запроса
$id = $psr7Request->getQueryParams()['id'];
/**
* Загружаем данные из нашего хранилища
* @var array $clientData
*/
$clientData = $someStorage->load($id);
$record = $factory->create('ClientData');
// помещаем данные из хранилища в структуру
$record->setData($clientData);
// помечаем изменения как принятые
$record->commitChanges();
try{
// сетим данные из запроса
$record->setData($params);
}catch(\InvalidArgumentException $e){
// переданы невалидные данные
}
// Для удобства экспорта данных в хранилище, например в БД, есть подготовленный класс экспорта,
// который конвертирует поля в нужный вид (например json поле в строку, DateTime в строку формата 'Y-m-d H:i:s')
$export = new \Dvelum\DR\Export\Database();
// получить все данные
$data = $export->exportRecord($record);
// или получить только обновления
$data = $export->exportUpdates($record);
// Export можно получить и из объекта $factory->getExport('ExportAlias'), тогда его нужно будет зарегистрировать при создании $factory
// и получить командой:
/**
* @var ExportInterface $export
*/
$export = $factory->getExport('Database');
Отсутствие подсветки полей в IDE можно компенсировать UI пакетом dvelum\dr-ui
Экспериментальный пакет, позволяет просматривать ваши структуры данных.
Пока доступен только просмотр, возможно будет добавлено и редактирование.
Запускается одной командой на локальном хосте linux/macos
Сравнение DataRecord с DTO, тест на заполнение 50,000 объектов.
PHP 7.4, xdebug отключен, cli opcache включен.
php test/tests/performance/create.php
- создать рандомный датасет
php test/tests/performance/dto.php
- заполнение DTO
php test/tests/performance/record.php
- заполнение Record
php test/tests/performance/record.php -r 1
- заполнение Record при помощи setRawData
Время, c | RAM, mb | |
---|---|---|
DTO | 0.025 | 13.177 |
DR | 0.146 | 2.016 |
DR raw | 0.036 | 2.016 |
Data Record потребляет значительно меньше (6.5 раз) оперативной памяти за счет оптимизаций, но по времени выполнения естественно уступает нативным иструментам (5.5 раз), так как валидаций больше и выполняются они в коде.
Для повышения производительности заполнения Data Record есть метод setRawData, который заполняет Record без валидаций. Этим методом можно воспользоваться когда данные приходят из бд и мы им доверяем (уверенны, что они провалидированы перед записью). В этом случае разница в скорости выполнения минимальна.
Валидации "из коробки" больше, кода писать нужно значительно меньше, вполне конкурентное решение имеющее право на жизнь.