-
Notifications
You must be signed in to change notification settings - Fork 38
Правки для старой версии битрикса + тегированный кеш для элементов #26
Changes from all commits
b13f197
d974cfc
dc503ca
eb12173
f65ced2
d173adb
ffcbec2
4021a22
2b1575c
d4fa12d
3be944a
cb66734
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -2,6 +2,9 @@ | |
|
|
||
| namespace Arrilot\BitrixModels; | ||
|
|
||
| use Arrilot\BitrixModels\Models\BaseBitrixModel; | ||
| use Illuminate\Support\Collection; | ||
|
|
||
| class Helpers | ||
| { | ||
| /** | ||
|
|
@@ -15,4 +18,83 @@ public static function startsWith($haystack, $needle) | |
| { | ||
| return strncmp($haystack, $needle, strlen($needle)) === 0; | ||
| } | ||
|
|
||
| /** | ||
| * @param Collection|BaseBitrixModel[] $primaryModels первичные модели | ||
| * @param Collection|BaseBitrixModel[] $relationModels подгруженные связанные модели | ||
| * @param string $primaryKey ключ связи в первичной модели | ||
| * @param string $relationKey ключ связи в связанной модели | ||
| * @param string $relationName название связи в первичной модели | ||
| * @param bool $multiple множественная ли это свзязь | ||
| */ | ||
| public static function assocModels($primaryModels, $relationModels, $primaryKey, $relationKey, $relationName, $multiple) | ||
| { | ||
| $buckets = static::buildBuckets($relationModels, $relationKey, $multiple); | ||
|
|
||
| foreach ($primaryModels as $i => $primaryModel) { | ||
| if ($multiple && is_array($keys = $primaryModel[$primaryKey])) { | ||
| $value = []; | ||
| foreach ($keys as $key) { | ||
| $key = static::normalizeModelKey($key); | ||
| if (isset($buckets[$key])) { | ||
| $value = array_merge($value, $buckets[$key]); | ||
| } | ||
| } | ||
| } else { | ||
| $key = static::normalizeModelKey($primaryModel[$primaryKey]); | ||
| $value = isset($buckets[$key]) ? $buckets[$key] : ($multiple ? [] : null); | ||
| } | ||
|
|
||
| $primaryModel->populateRelation($relationName, is_array($value) ? (new Collection($value))->keyBy(function ($item) {return $item->id;}) : $value); | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
|
||
| } | ||
| } | ||
|
|
||
| /** | ||
| * Сгруппировать найденные модели | ||
| * @param array $models | ||
| * @param string $linkKey | ||
| * @param bool $multiple | ||
| * @return array | ||
| */ | ||
| protected static function buildBuckets($models, $linkKey, $multiple) | ||
| { | ||
| $buckets = []; | ||
|
|
||
| foreach ($models as $model) { | ||
| $key = $model[$linkKey]; | ||
| if (is_scalar($key)) { | ||
| $buckets[$key][] = $model; | ||
| } elseif (is_array($key)){ | ||
| foreach ($key as $k) { | ||
| $k = static::normalizeModelKey($k); | ||
| $buckets[$k][] = $model; | ||
| } | ||
| } else { | ||
| $key = static::normalizeModelKey($key); | ||
| $buckets[$key][] = $model; | ||
| } | ||
| } | ||
|
|
||
| if (!$multiple) { | ||
| foreach ($buckets as $i => $bucket) { | ||
| $buckets[$i] = reset($bucket); | ||
| } | ||
| } | ||
|
|
||
| return $buckets; | ||
| } | ||
|
|
||
| /** | ||
| * @param mixed $value raw key value. | ||
| * @return string normalized key value. | ||
| */ | ||
| protected static function normalizeModelKey($value) | ||
| { | ||
| if (is_object($value) && method_exists($value, '__toString')) { | ||
| // ensure matching to special objects, which are convertable to string, for cross-DBMS relations, for example: `|MongoId` | ||
| $value = $value->__toString(); | ||
| } | ||
|
|
||
| return $value; | ||
| } | ||
| } | ||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -3,6 +3,7 @@ | |
| namespace Arrilot\BitrixModels\Queries; | ||
|
|
||
| use Arrilot\BitrixModels\Models\BaseBitrixModel; | ||
| use Arrilot\BitrixModels\ServiceProvider; | ||
| use BadMethodCallException; | ||
| use Bitrix\Main\Data\Cache; | ||
| use Closure; | ||
|
|
@@ -15,7 +16,9 @@ | |
| abstract class BaseQuery | ||
| { | ||
| use BaseRelationQuery; | ||
|
|
||
|
|
||
| public static $cacheDir = '/bitrix-models'; | ||
|
|
||
| /** | ||
| * Query select. | ||
| * | ||
|
|
@@ -518,7 +521,7 @@ protected function rememberInCache($key, $minutes, Closure $callback) | |
| } | ||
|
|
||
| $cache = Cache::createInstance(); | ||
| if ($cache->initCache($minutes * 60, $key, '/bitrix-models')) { | ||
| if ($cache->initCache($minutes * 60, $key, static::$cacheDir)) { | ||
| $vars = $cache->getVars(); | ||
| return !empty($vars['isCollection']) ? new Collection($vars['cache']) : $vars['cache']; | ||
| } | ||
|
|
@@ -577,4 +580,33 @@ protected function prepareMultiFilter(&$key, &$value) | |
| { | ||
|
|
||
| } | ||
|
|
||
| /** | ||
| * Проверка включен ли тегированный кеш | ||
| * @return bool | ||
| */ | ||
| protected function isManagedCacheOn() | ||
| { | ||
| $config = ServiceProvider::configProvider(); | ||
| return $config::GetOptionString('main', 'component_managed_cache_on', 'N') == 'Y'; | ||
| } | ||
|
|
||
| public function exec($query) | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Тоже не хочу это мержить. У моделей и так слишком много ответственностей, это уже явный перебор. |
||
| { | ||
| $queryType = 'BaseQuery::exec'; | ||
|
|
||
| $callback = function () use ($query) { | ||
| $rows = []; | ||
| $result = \Bitrix\Main\Application::getConnection()->query($query); | ||
| $modelName = $this->modelName; | ||
| $result->setSerializedFields($modelName::$serializedFields ?: []); | ||
| while ($row = $result->fetch()) { | ||
| $this->addItemToResultsUsingKeyBy($rows, new $this->modelName($row['ID'], $row)); | ||
| } | ||
|
|
||
| return new Collection($rows); | ||
| }; | ||
|
|
||
| return $this->handleCacheIfNeeded(compact('queryType', 'query'), $callback); | ||
| } | ||
| } | ||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Не хочу добавлять костыли для старых версий Битрикса.
Если кому-то это нужно - могут добавить это в базовую модель своего приложения