From fc4c3234a7fdc7db5cb40a72faa50b14ee5c07bb Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?P=C5=91cze=20Bence?= Date: Sat, 17 Jun 2023 11:53:46 +0200 Subject: [PATCH] implement multi relation loading --- .../PersistentData/IPersistentDataManager.php | 2 ++ src/PersistentData/Model/Model.php | 7 ++++ src/PersistentData/PersistentDataManager.php | 34 +++++++++++++++++++ 3 files changed, 43 insertions(+) diff --git a/src/Interfaces/PersistentData/IPersistentDataManager.php b/src/Interfaces/PersistentData/IPersistentDataManager.php index 6cdf496..09970ac 100644 --- a/src/Interfaces/PersistentData/IPersistentDataManager.php +++ b/src/Interfaces/PersistentData/IPersistentDataManager.php @@ -16,6 +16,8 @@ interface IPersistentDataManager public function loadRelationsFromDb(Model $model, bool $recursive = false, array $withRelations = []): void; + public function loadMultiRelationsFromDb(array $models, string $relation, bool $useRelations = false, array $withRelations = []): void; + public function saveToDb(Model $model): void; public function deleteFromDb(Model $model): void; diff --git a/src/PersistentData/Model/Model.php b/src/PersistentData/Model/Model.php index c5f566c..c74f36e 100644 --- a/src/PersistentData/Model/Model.php +++ b/src/PersistentData/Model/Model.php @@ -8,6 +8,8 @@ abstract class Model protected static array $relations = []; + protected static array $multiRelations = []; + protected $id = null; private array $snapshot = []; @@ -27,6 +29,11 @@ abstract class Model return static::$relations; } + public static function getMultiRelations(): array + { + return static::$multiRelations; + } + public function setId($id): void { $this->id = $id; diff --git a/src/PersistentData/PersistentDataManager.php b/src/PersistentData/PersistentDataManager.php index 6547782..41cb21d 100644 --- a/src/PersistentData/PersistentDataManager.php +++ b/src/PersistentData/PersistentDataManager.php @@ -92,6 +92,40 @@ class PersistentDataManager implements IPersistentDataManager } } + public function loadMultiRelationsFromDb(array $models, string $relation, bool $useRelations = false, array $withRelations = []): void + { + if (count($models) === 0) { + return; + } + + $parentModelType = get_class($models[0]); + $relationModelsSetter = 'set' . str_replace('_', '', ucwords($relation, '_')); + [$relationModelType, $reverseRelation] = call_user_func([$parentModelType, 'getMultiRelations'])[$relation]; + $reverseRelationIdGetter = 'get' . str_replace('_', '', ucwords($reverseRelation, '_')) . 'Id'; + + $parentModelsById = []; + foreach ($models as $model) { + $parentModelsById[$model->getId()] = $model; + } + + $select = new Select($this->dbConnection); + $select->where($reverseRelation . '_id', 'IN', array_keys($parentModelsById)); + + $relationsByParentModelId = []; + foreach ($this->selectMultipleFromDb($select, $relationModelType, $useRelations, $withRelations) as $relationModel) { + $reverseRelationId = $relationModel->$reverseRelationIdGetter(); + if (!isset($relationsByParentModelId[$reverseRelationId])) { + $relationsByParentModelId[$reverseRelationId] = []; + } + $relationsByParentModelId[$reverseRelationId][] = $relationModel; + } + + foreach ($parentModelsById as $parentModelId => $parentModel) { + $relationModels = $relationsByParentModelId[$parentModelId] ?? []; + $parentModel->$relationModelsSetter($relationModels); + } + } + public function saveToDb(Model $model): void { $this->syncRelations($model);