定制 beta/bx.model.ext 二次开发

按需修改功能、优化性能、对接业务系统,提供一站式技术支持

邮箱:yvsm@zunyunkeji.com | QQ:316430983 | 微信:yvsm316

beta/bx.model.ext

Composer 安装命令:

composer require beta/bx.model.ext

包简介

Extended model

README 文档

README

Данный модуль включает в себя ряд декораторов для сервисов моделей:

  • LazyModelService - реализует механизм загрузки данных по требованию.
  • StorageModelService - реализует механизм Indenty map, содержит хранилище с ранее запрошенными объектами.
  • TransactionModelService - содержит хранилище операций записи/удаления, для создания общей транзакции.

LazyModelService

Содержит декоратор сервиса моделей (LazyModelService), декоратор модели (LazyModel) и отдельную коллекцию (LazyModelCollection) для массовой загурзки данных по требованию.

Пример работы

use Bx\Model\Ext\DataHelper;
use Bx\Model\Ext\LazyModelService;
use Bx\Model\Ext\LazyModel;
use Bitrix\Main\Loader;

Loader::includeModule('bx.model.ext');
$someServiceModel = new SomeServiceModel();     // некий сервис для работы с моделями
$lazyServiceModel = new LazyModelService(
    $someServiceModel,
    SomeModel::class,       // класс модели данных
    'ID'                    // первичный ключ
);

$collection = $lazyServiceModel->getList([
    'select' => ['ID'],
]);                             // [['ID' => 1], ['ID' => 2], ['ID' => 3]]

$firstModel = $collection->first();
$firstModel->load();            // запрашиваем все данные по данной модели
DataHelper::load($firstModel);  // альтернативный способ запроса данных модели

print_r(iterator_to_array($firstModel));    // ['ID' => 1, 'NAME' => 'first'...]
print_r(iterator_to_array($collection));    // [['ID' => 1, 'NAME' => 'first'...], ['ID' => 2], ['ID' => 3]]

$collection->load();            // запрашиваем все данные по моделям коллекции
DataHelper::load($collection);  // альтернативный способ запроса данных коллекции

print_r(iterator_to_array($collection));    // [['ID' => 1, 'NAME' => 'first'...], ['ID' => 2, 'NAME' => 'second'...], ['ID' => 3, 'NAME' => 'third'...]]

var_dump($first instanceof SomeModel);  // false
var_dump($first instanceof LazyModel);  // true

// данный метод позволяет получить инкапсулированную модель
var_dump($first->getOriginalObject() instanceof SomeModel); // true
/** 
 * альтернативный метод для запроса инкапсулированной модели, 
 * в отличии от первого метода позволяет пройти по всей цепочки 
 * декоратов и извлечь исходную модель 
 * **/
var_dump(DataHelper::extractOriginalObject($first) instanceof SomeModel); // true

var_dump($lazyServiceModel->getOriginalObject() instanceof SomeServiceModel); // true
var_dump(DataHelper::extractOriginalObject($lazyServiceModel) instanceof SomeServiceModel); // true

StorageModelService

Содержит докоратор сервиса моделей (LazyModelService), который в свою очередь сохраняет список запрошенных моделей и при повторном запросе тех же моделей извлекает их из внутреннего хранилища. Таким образом можно избежать дублирования объектов и уменьшить количество обращений к источнику данных. Механизм хранилища по-умолчанию использует LRU кеш.

Пример работы

use Bx\Model\Ext\StorageModelService;
use Bx\Model\Ext\Common\ModelStorage;
use Bx\Model\Ext\Common\LruRemoveStrategy;
use Bitrix\Main\Loader;

Loader::includeModule('bx.model.ext');

$someServiceModel = new SomeServiceModel();     // некий сервис для работы с моделями
$modelSotrage = new ModelStorage(               // создаем хранилище для моделей
    new LruRemoveStrategy(),                    // стратегия чистки кеша
    'ID',                                       // первичный ключ
    [],                                         // элементы для добавления в хранилище
    1000                                        // максимальное количество элементов в хранилище
);
$storageServiceModel = new StorageModelService(
    $someServiceModel,
    SomeModel::class,
    'ID',
    $modelSotrage
);

$model1 = $storageServiceModel->getById(1);
$model2 = $storageServiceModel->getById(1);
$model3 = $storageServiceModel->getList(['filter' => ['=ID' => 1]])->first();

var_dump($model1 === $model2);      // true, один и тот же объект
var_dump($model1 === $model3);      // true, один и тот же объект

TransactionModelService

Содержит декоратор сервиса моделей (TransactionModelService) и декоратор моделей (StateModel), который позволяет отслеживать изменение данных в модели. Все опреции на запись и удаление собираются в отдельном хранилище операций, которые в последующем можно запустить как единую транзакцию и/или реализовать сценарий массового обновления данных или же реализовать паттерн Unit of Work.

Пример работы

use Bx\Model\Ext\DataHelper;
use Bx\Model\Ext\TransactionModelService;
use Bx\Model\Ext\Common\OperationHolder;
use Bitrix\Main\Loader;

Loader::includeModule('bx.model.ext');
$someServiceModel = new SomeServiceModel();     // некий сервис для работы с моделями
$operationHolder = new OperationHolder();       // хранилище операций
$transactionServiceModel = new TransactionModelService(
    $operationHolder,
    $someServiceModel,
    SomeModel::class
);

$model = $transactionServiceModel->getById(1); // ['ID' => 1, 'NAME' => 'Original name']
$model->setName('Name 1');
$model['NAME'] = 'Name 2';

var_dump($model->isChanged());              //true

$state = $model->offsetGetState('NAME');    // хранище состояний указанного поля
print_r(iterator_to_array($state));         // ['Name 2', 'Name 1', 'Original name']

var_dump($model->getName());                // 'Name 2'
var_dump($model['NAME']);                   // 'Name 2'

$model->loadPrevState('NAME');              // загружаем предыдущее состояние поля

var_dump($model->getName());                // 'Name 1'
var_dump($model['NAME']);                   // 'Name 1'

$model->loadPrevState('NAME');              // загружаем предыдущее состояние поля

var_dump($model->getName());                // 'Original name'
var_dump($model['NAME']);                   // 'Original name'

$model->loadNexState('NAME');               // загружаем следующее состояние поля

var_dump($model->getName());                // 'Name 1'
var_dump($model['NAME']);                   // 'Name 1'

$model->loadOriginalState();                // загружаем исходное состояние всех полей модели

var_dump($model->getName());                // 'Original name'
var_dump($model['NAME']);                   // 'Original name'

$model->loadLastState();                    // загружаем последнее состояние всех полей модели

var_dump($model->getName());                // 'Name 2'
var_dump($model['NAME']);                   // 'Name 2'

// запрашиваем измененные данные
var_dump($model->getChangesData());         // ['NAME' => 'NAME 2']

$result = $transactionServiceModel->save($model);     // получаем экземпляр TransactionResult, данная операция добавлена в хранилище операций, но не была применена
$result->commit();              // мы можем применить данную операцию на месте
DataHelper::commit($result);    // или применить ее таким способом

// запрос всех опреаций для указанного сервиса
$operationHolder->getOperationList(SomeServiceModel::class);
// запрос опреаций создания для указанного сервиса
$operationHolder->getCreateOperationList(SomeServiceModel::class); 
// запрос опреаций обновления для указанного сервиса
$operationHolder->getUpdateOperationList(SomeServiceModel::class); 
// запрос опреаций создания для указанного сервиса
$operationHolder->getRemoveOperationList(SomeServiceModel::class);

$operationHolder->actualizeOperations();    // данный метод позволяет отчистить хранилище от ранее выполненных операции и устанить конфликтующие операции

$operationHolder->commit();             // выполнить все опреции из хранилища и отчистить хранилище
DataHelper::commit($operationHolder);   // альтернативный метод выполнения операций из хранилища

beta/bx.model.ext 适用场景与选型建议

beta/bx.model.ext 是一款 基于 PHP 开发的 Composer 扩展包,目前已累计 5 次下载、GitHub Stars 达 1, 最近一次更新时间为 2022 年 02 月 17 日, 在 PHP 生态内属于活跃度较高的组件。

我们在过去多个企业项目中使用过 beta/bx.model.ext 或与其功能相近的方案,如果你在选型或落地过程中遇到问题,例如 版本兼容、二次改造、私有化封装、与内部系统对接、生产 BUG 排查,欢迎联系我们协助评估。

围绕 beta/bx.model.ext 我们能提供哪些服务?
定制开发 / 二次开发

基于 beta/bx.model.ext 在你已有业务上做功能扩展、字段裁剪、UI 适配、与内部账号 / 权限 / 日志系统的深度对接。

BUG 修复 & 性能优化

线上偶发问题、内存泄漏、慢查询、并发异常等排查修复;针对高流量场景做缓存、队列、索引层面的调优。

项目外包 & 长期维护

承接完整的项目从需求 → 设计 → 开发 → 上线 → 长期运维;也可按月提供技术保姆服务。

yvsm@zunyunkeji.com QQ:316430983 微信:yvsm316 西安尊云信息科技 · 专注 PHP / Go / 分布式系统研发

统计信息

  • 总下载量: 5
  • 月度下载量: 0
  • 日度下载量: 0
  • 收藏数: 1
  • 点击次数: 3
  • 依赖项目数: 0
  • 推荐数: 0

GitHub 信息

  • Stars: 1
  • Watchers: 2
  • Forks: 0
  • 开发语言: PHP

其他信息

  • 授权协议: MIT
  • 更新时间: 2022-02-17