28 if (!self::hasAccess())
32 Loc::getMessage(
'STORE_ENABLE_WIZARD_NO_PERMISSION_ENABLE'),
35 'analyticsCode' =>
'no_access',
41 if (!self::canBeEnabled())
45 Loc::getMessage(
'STORE_ENABLE_WIZARD_ENABLE_ERROR'),
48 'analyticsCode' =>
'conditions_not_met',
54 self::enableOptions();
55 self::resetQuantities();
56 self::installRealizationDocumentTradingPlatform();
57 self::registerEventsHandlers();
58 self::showEntityProductGridColumns();
67 if (!self::hasAccess())
71 Loc::getMessage(
'STORE_ENABLE_WIZARD_NO_PERMISSION_DISABLE'),
74 'analyticsCode' =>
'no_access',
80 if (!self::canBeDisabled())
84 Loc::getMessage(
'STORE_ENABLE_WIZARD_DISABLE_ERROR'),
87 'analyticsCode' =>
'conditions_not_met',
93 self::disableOptions();
94 self::resetQuantities();
95 self::deleteDocuments();
96 self::uninstallRealizationDocumentTradingPlatform();
97 self::unRegisterEventsHandlers();
102 private static function canBeEnabled(): bool
105 self::isCrmIncluded()
106 && !\CCrmSaleHelper::isWithOrdersMode()
110 private static function canBeDisabled(): bool
112 return self::isCrmIncluded();
115 private static function enableOptions(): void
117 Option::set(
'catalog',
'default_quantity_trace',
'Y');
118 Option::set(
'catalog',
'default_can_buy_zero',
'Y');
119 Option::set(
'catalog',
'allow_negative_amount',
'Y');
120 Option::set(
'catalog',
'default_use_store_control',
'Y');
121 Option::set(
'catalog',
'enable_reservation',
'Y');
124 private static function disableOptions(): void
126 Option::set(
'catalog',
'default_use_store_control',
'N');
127 Option::set(
'catalog',
'default_quantity_trace',
'N');
130 private static function resetQuantities(): void
137 self::resetQuantity();
138 self::resetQuantityTrace();
139 self::resetSaleReserve();
140 self::resetCrmReserve();
143 private static function deleteDocuments(): void
150 self::resetStoreBatch();
151 self::deleteStoreDocuments();
152 self::deleteRealizations();
155 private static function resetQuantity(): void
157 $conn = Application::getConnection();
158 $conn->queryExecute(
'truncate table b_catalog_store_product');
159 $conn->queryExecute(
'delete from b_catalog_store_barcode where ORDER_ID is null and STORE_ID > 0');
163 private static function resetQuantityTrace(): void
165 self::resetQuantityTraceMainTypes();
166 self::resetQuantityTraceSku();
167 self::resetQuantityTraceEmptySku();
168 self::resetQuantityTraceSets();
171 private static function resetQuantityTraceMainTypes(): void
173 $mainTypes = implode(
182 Application::getConnection()->queryExecute(
"
183 update b_catalog_product
186 QUANTITY_RESERVED = 0,
192 TYPE in (" . $mainTypes .
")
196 private static function resetQuantityTraceSku(): void
200 && Option::get(
'catalog',
'show_catalog_tab_with_offers') ===
'Y'
203 Application::getConnection()->queryExecute(
"
204 update b_catalog_product
207 QUANTITY_RESERVED = 0,
218 Application::getConnection()->queryExecute(
"
219 update b_catalog_product
222 QUANTITY_RESERVED = 0,
233 private static function resetQuantityTraceEmptySku(): void
235 if (!self::isCloud())
239 Application::getConnection()->queryExecute(
"
240 update b_catalog_product
253 private static function resetQuantityTraceSets(): void
255 Application::getConnection()->queryExecute(
"
256 update b_catalog_product
268 private static function resetStoreBatch(): void
270 Application::getConnection()->queryExecute(
'truncate table b_catalog_store_batch');
271 Application::getConnection()->queryExecute(
'truncate table b_catalog_store_batch_docs_element');
274 private static function resetSaleReserve(): void
276 if (Loader::includeModule(
'sale'))
278 $conn = Application::getConnection();
280 $conn->queryExecute(
"update b_sale_order_dlv_basket set RESERVED_QUANTITY = 0 where 1 = 1");
281 $conn->queryExecute(
"update b_sale_order_delivery set RESERVED='N' where 1 = 1");
283 $conn->queryExecute(
"truncate table b_sale_basket_reservation_history");
284 $conn->queryExecute(
"truncate table b_sale_basket_reservation");
288 private static function resetCrmReserve(): void
290 if (!self::isCrmIncluded())
295 Application::getConnection()->queryExecute(
"truncate table b_crm_product_row_reservation");
296 Application::getConnection()->queryExecute(
"truncate table b_crm_product_reservation_map");
299 private static function deleteStoreDocuments(): void
303 $fileIds = Catalog\StoreDocumentFileTable::getList([
'select' => [
'FILE_ID']])->fetchAll();
304 $fileIds = array_column($fileIds,
'FILE_ID');
306 foreach ($fileIds as $fileId)
308 \CFile::Delete($fileId);
311 $documents = Catalog\StoreDocumentTable::getList([
'select' => [
'ID',
'DOC_TYPE']])->fetchAll();
312 foreach ($documents as $document)
314 $typeTableClass = Catalog\Document\StoreDocumentTableManager::getTableClassByType($document[
'DOC_TYPE']);
321 $conn = Application::getConnection();
323 $conn->queryExecute(
'truncate table b_catalog_store_docs');
324 $conn->queryExecute(
'truncate table b_catalog_docs_element');
325 $conn->queryExecute(
'truncate table b_catalog_docs_barcode');
326 $conn->queryExecute(
'truncate table b_catalog_store_document_file');
328 if (self::isCrmIncluded())
330 TimelineEntry::deleteByAssociatedEntityType(\CCrmOwnerType::StoreDocument);
332 $conn->queryExecute(
"truncate table b_crm_store_document_contractor");
336 private static function deleteRealizations(): void
338 if (!self::isCrmIncluded())
343 $realizations = ShipmentRealizationTable::getList([
345 '=IS_REALIZATION' =>
'Y',
348 foreach ($realizations as $realization)
350 ShipmentRealizationTable::delete($realization[
'ID']);
351 ShipmentTable::deleteWithItems($realization[
'SHIPMENT_ID']);
355 private static function installRealizationDocumentTradingPlatform(): void
357 if (!self::isCrmIncluded())
362 $platformCode = TradingPlatform\RealizationDocument::TRADING_PLATFORM_CODE;
363 $platform = TradingPlatform\RealizationDocument::getInstanceByCode($platformCode);
370 private static function uninstallRealizationDocumentTradingPlatform(): void
372 if (!self::isCrmIncluded())
377 $platformCode = TradingPlatform\RealizationDocument::TRADING_PLATFORM_CODE;
378 $platform = TradingPlatform\RealizationDocument::getInstanceByCode($platformCode);
385 private static function registerEventsHandlers()
389 $eventManager->registerEventHandler(
'sale',
'onBeforeSaleShipmentSetField',
'crm',
'\Bitrix\Crm\Order\EventsHandler\Shipment',
'onBeforeSetField');
392 private static function unRegisterEventsHandlers()
396 $eventManager->unRegisterEventHandler(
'sale',
'onBeforeSaleShipmentSetField',
'crm',
'\Bitrix\Crm\Order\EventsHandler\Shipment',
'onBeforeSetField');
399 private static function showEntityProductGridColumns(): void
401 if (!self::isCrmIncluded())
414 $allHeaderMap = ProductList::getHeaderDefaultMap();
415 $allHeaders = array_keys($allHeaderMap);
417 $gridId = ProductList::DEFAULT_GRID_ID;
421 "SELECT ID, VALUE FROM b_user_option WHERE CATEGORY = 'main.interface.grid' AND NAME = '{$sqlHelper->forSql($gridId)}'"
425 while ($gridSettings = $queryResult->fetch())
427 $optionID = (int)$gridSettings[
'ID'];
428 $value = $gridSettings[
'VALUE'];
434 $options = unserialize($value, [
'allowed_classes' =>
false]);
446 foreach (
$options[
'views'] as &$view)
448 if (!isset($view[
'columns']) || $view[
'columns'] ===
'')
453 $allUsedColumns = explode(
',', $view[
'columns']);
454 $currentHeadersInDefaultPosition = array_values(
455 array_intersect($allHeaders, array_merge($allUsedColumns, $headers))
457 $headers = array_values(array_intersect($allHeaders, $headers));
459 foreach ($headers as $header)
461 if (in_array($header, $allUsedColumns,
true))
466 $insertPosition = array_search($header, $currentHeadersInDefaultPosition,
true);
467 array_splice($allUsedColumns, $insertPosition, 0, $header);
473 $view[
'columns'] = implode(
',', $allUsedColumns);
480 $sqlValue = $sqlHelper->forSql(serialize(
$options));
482 "UPDATE b_user_option SET VALUE = '{$sqlValue}' WHERE ID ='{$optionID}'"
490 Application::getInstance()->getManagedCache()->cleanDir(
'user_option');
494 private static function isCloud(): bool
496 return Loader::includeModule(
'bitrix24');
499 private static function isCrmIncluded(): bool
501 return Loader::includeModule(
'crm');
504 private static function hasAccess(): bool