feat: add migrations, mantenance tasks, database cache, blocks cache

This commit is contained in:
2025-11-13 02:24:00 +03:00
parent ab5c2f42b9
commit c0a6cb17b3
32 changed files with 948 additions and 213 deletions

View File

@@ -2,6 +2,7 @@
use Bastion\ApplicationFactory;
use Cart\User;
use Openguru\OpenCartFramework\Application;
use Openguru\OpenCartFramework\Http\Response as HttpResponse;
use Openguru\OpenCartFramework\Logger\LoggerInterface;
use Openguru\OpenCartFramework\Logger\OpenCartLogAdapter;
@@ -94,14 +95,12 @@ class ControllerExtensionModuleTgshop extends Controller
public function index(): void
{
$this->cleanUpOldAssets();
$this->migrateFromOldSettings();
$this->removeLegacyFiles();
$this->runMaintenanceTasks();
$this->injectVueJs();
$this->config();
$this->showConfigPage();
}
private function config(): void
private function showConfigPage(): void
{
$data = [];
$this->document->setTitle($this->language->get('heading_title'));
@@ -124,51 +123,8 @@ class ControllerExtensionModuleTgshop extends Controller
public function handle(): void
{
try {
$json = $this->model_setting_setting->getSetting('module_telecart');
if (! isset($json['module_telecart_settings'])) {
$json['module_telecart_settings'] = [];
}
$items = Arr::mergeArraysRecursively($json['module_telecart_settings'], [
'app' => [
'shop_base_url' => HTTPS_CATALOG, // for catalog: HTTPS_SERVER, for admin: HTTPS_CATALOG
'language_id' => (int) $this->config->get('config_language_id'),
],
'logs' => [
'path' => DIR_LOGS,
],
'database' => [
'host' => DB_HOSTNAME,
'database' => DB_DATABASE,
'username' => DB_USERNAME,
'password' => DB_PASSWORD,
'prefix' => DB_PREFIX,
'port' => (int) DB_PORT,
],
'store' => [
'oc_store_id' => 0,
'oc_default_currency' => $this->config->get('config_currency'),
'oc_config_tax' => filter_var($this->config->get('config_tax'), FILTER_VALIDATE_BOOLEAN),
],
'orders' => [
'oc_customer_group_id' => (int) $this->config->get('config_customer_group_id'),
],
'telegram' => [
'mini_app_url' => rtrim(HTTPS_CATALOG, '/') . '/image/catalog/tgshopspa/#/',
],
]);
$app = ApplicationFactory::create($items);
$app->bind(OcRegistryDecorator::class, fn() => new OcRegistryDecorator($this->registry));
$app
->withLogger(fn() => new OpenCartLogAdapter(
$this->log,
'TeleCartAdmin',
$app->getConfigValue('app.app_debug')
? LoggerInterface::LEVEL_DEBUG
: LoggerInterface::LEVEL_WARNING,
))
$this
->createApplication()
->bootAndHandleRequest();
} catch (Exception $e) {
$this->log->write('[TELECART] Error: ' . $e->getMessage());
@@ -264,68 +220,6 @@ class ControllerExtensionModuleTgshop extends Controller
return $map;
}
private function cleanUpOldAssets(): void
{
$spaPath = rtrim(DIR_IMAGE, '/') . '/catalog/tgshopspa';
$assetsPath = $spaPath . '/assets';
$manifestPath = $spaPath . '/manifest.json';
if (! file_exists($manifestPath)) {
$this->log->write('[TELECART] Файл manifest.json не найден — очистка пропущена.');
return;
}
try {
$contents = json_decode(file_get_contents($manifestPath), true, 512, JSON_THROW_ON_ERROR);
$entry = $contents['index.html'] ?? null;
if (! $entry) {
throw new RuntimeException('[TELECART] Некорректный manifest.json — отсутствует ключ index.html.');
}
$keep = [$entry['file']];
if (! empty($entry['css'])) {
foreach ($entry['css'] as $css) {
$keep[] = $css;
}
}
$deletedFiles = 0;
$keptFiles = 0;
foreach (glob($assetsPath . '/*') as $file) {
$ext = pathinfo($file, PATHINFO_EXTENSION);
if (! in_array($ext, ['js', 'css', 'map'])) {
continue;
}
$relative = 'assets/' . basename($file);
if (in_array($relative, $keep, true)) {
$keptFiles++;
continue;
}
if (is_file($file)) {
unlink($file);
$deletedFiles++;
}
}
if ($deletedFiles > 0) {
$this->log->write(
sprintf(
'[TELECART] Очистка assets завершена. Удалено: %d, оставлено: %d',
$deletedFiles,
$keptFiles
)
);
}
} catch (JsonException $e) {
$this->log->write('[TELECART] Ошибка декодирования файла manifest.json: ' . $e->getMessage());
} catch (Exception $e) {
$this->log->write('[TELECART] Ошибка удаления старых assets: ' . $e->getMessage());
}
}
private function injectVueJs(): void
{
$appDir = rtrim(DIR_APPLICATION, '/');
@@ -340,92 +234,59 @@ class ControllerExtensionModuleTgshop extends Controller
}
}
private function migrateFromOldSettings(): void
private function createApplication(): Application
{
$legacySettings = $this->model_setting_setting->getSetting('module_tgshop');
if (! $legacySettings) {
return;
$json = $this->model_setting_setting->getSetting('module_telecart');
if (! isset($json['module_telecart_settings'])) {
$json['module_telecart_settings'] = [];
}
$newSettings = $this->model_setting_setting->getSetting('module_telecart');
$items = Arr::mergeArraysRecursively($json['module_telecart_settings'], [
'app' => [
'shop_base_url' => HTTPS_CATALOG, // for catalog: HTTPS_SERVER, for admin: HTTPS_CATALOG
'language_id' => (int) $this->config->get('config_language_id'),
],
'logs' => [
'path' => DIR_LOGS,
],
'database' => [
'host' => DB_HOSTNAME,
'database' => DB_DATABASE,
'username' => DB_USERNAME,
'password' => DB_PASSWORD,
'prefix' => DB_PREFIX,
'port' => (int) DB_PORT,
],
'store' => [
'oc_store_id' => 0,
'oc_default_currency' => $this->config->get('config_currency'),
'oc_config_tax' => filter_var($this->config->get('config_tax'), FILTER_VALIDATE_BOOLEAN),
],
'orders' => [
'oc_customer_group_id' => (int) $this->config->get('config_customer_group_id'),
],
'telegram' => [
'mini_app_url' => rtrim(HTTPS_CATALOG, '/') . '/image/catalog/tgshopspa/#/',
],
]);
static $mapLegacyToNewSettings = [
'module_tgshop_app_icon' => 'app.app_icon',
'module_tgshop_theme_light' => 'app.theme_light',
'module_tgshop_bot_token' => 'telegram.bot_token',
'module_tgshop_status' => 'app.app_enabled',
'module_tgshop_app_name' => 'app.app_name',
'module_tgshop_theme_dark' => 'app.theme_dark',
'module_tgshop_debug' => 'app.app_debug',
'module_tgshop_chat_id' => 'telegram.chat_id',
'module_tgshop_owner_notification_template' => 'telegram.owner_notification_template',
'module_tgshop_text_order_created_success' => 'texts.text_order_created_success',
'module_tgshop_enable_store' => 'store.enable_store',
'module_tgshop_yandex_metrika' => 'metrics.yandex_metrika_counter',
'module_tgshop_customer_notification_template' => 'telegram.customer_notification_template',
'module_tgshop_feature_vouchers' => 'store.feature_vouchers',
'module_tgshop_order_default_status_id' => 'orders.order_default_status_id',
'module_tgshop_feature_coupons' => 'store.feature_coupons',
'module_tgshop_text_no_more_products' => 'texts.text_no_more_products',
'module_tgshop_text_empty_cart' => 'texts.text_empty_cart',
];
$app = ApplicationFactory::create($items);
$app->bind(OcRegistryDecorator::class, fn() => new OcRegistryDecorator($this->registry));
if (! $newSettings) {
$data = [];
Arr::set($data, 'app.app_icon', $legacySettings['module_tgshop_app_icon']);
$app
->withLogger(fn() => new OpenCartLogAdapter(
$this->log,
'TeleCartAdmin',
$app->getConfigValue('app.app_debug')
? LoggerInterface::LEVEL_DEBUG
: LoggerInterface::LEVEL_INFO,
));
foreach ($mapLegacyToNewSettings as $key => $value) {
if (array_key_exists($key, $legacySettings)) {
if ($key === 'module_tgshop_status') {
$newValue = filter_var($legacySettings[$key], FILTER_VALIDATE_BOOLEAN);
} elseif ($key === 'module_tgshop_debug') {
$newValue = filter_var($legacySettings[$key], FILTER_VALIDATE_BOOLEAN);
} elseif ($key === 'module_tgshop_chat_id') {
$newValue = (int) $legacySettings[$key];
} elseif ($key === 'module_tgshop_enable_store') {
$newValue = filter_var($legacySettings[$key], FILTER_VALIDATE_BOOLEAN);
} elseif ($key === 'module_tgshop_order_default_status_id') {
$newValue = (int) $legacySettings[$key];
} elseif ($key === 'module_tgshop_feature_vouchers') {
$newValue = filter_var($legacySettings[$key], FILTER_VALIDATE_BOOLEAN);
} elseif ($key === 'module_tgshop_feature_coupons') {
$newValue = filter_var($legacySettings[$key], FILTER_VALIDATE_BOOLEAN);
} else {
$newValue = $legacySettings[$key];
}
Arr::set($data, $value, $newValue);
}
}
Arr::set(
$data,
'metrics.yandex_metrika_enabled',
! empty(trim($legacySettings['module_tgshop_yandex_metrika']))
);
$this->model_setting_setting->editSetting('module_telecart', [
'module_telecart_settings' => $data,
]);
$this->log->write('[TELECART] Выполнено обновление настроек с 1й версии модуля.');
$this->session->data['success'] = 'Выполнено обновление настроек с прошлой версии модуля.';
}
$this->model_setting_setting->deleteSetting('module_tgshop');
return $app;
}
private function removeLegacyFiles(): void
private function runMaintenanceTasks(): void
{
$legacyFilesToRemove = [
DIR_TEMPLATE . '/extension/module/tgshop_init.twig',
];
foreach ($legacyFilesToRemove as $file) {
if (file_exists($file)) {
unlink($file);
$this->log->write('[TELECART] Удалён старый файл: ' . $file);
}
}
$this->createApplication()->runMaintenanceTasks();
}
}