=')) { return; // Already up to date } $log = $this->get_log(); $schema_provider = AKSRT_Admin_Schema_Provider::get_instance(); // Run migrations in order $this->migrate_v1_0_0($schema_provider, $log); $this->migrate_v1_2_0($log); $this->migrate_v1_3_0($log); // Update version update_option(self::VERSION_KEY, self::MIGRATION_VERSION); $log[] = [ 'version' => self::MIGRATION_VERSION, 'timestamp' => gmdate('Y-m-d H:i:s'), 'action' => 'migration_complete', ]; update_option(self::LOG_KEY, $log); } /** * Get the migration log. * * @return array */ public function get_log(): array { $log = get_option(self::LOG_KEY, []); return is_array($log) ? $log : []; } /** * Get current migration version. * * @return string */ public function get_version(): string { return get_option(self::VERSION_KEY, '0.0.0'); } /* ------------------------------------------------------------------ */ /* Migration: v1.0.0 */ /* Maps old option keys to new schema-managed domains. */ /* ------------------------------------------------------------------ */ private function migrate_v1_0_0(AKSRT_Admin_Schema_Provider $schema_provider, array &$log): void { // 1. Migrate aksrt_basic_settings fields into the new global domain $this->migrate_basic_to_global($schema_provider, $log); // 2. Migrate aksrt_seo_settings to the new seo domain (already a standalone key) // No action needed — it's already stored under aksrt_seo_settings. // 3. Ensure all domain options exist with defaults foreach ($schema_provider->get_domain_keys() as $domain) { $option_key = $schema_provider->get_option_key($domain); $existing = get_option($option_key); if ($existing === false) { $defaults = $schema_provider->get_defaults($domain); if (!empty($defaults)) { add_option($option_key, $defaults); $log[] = [ 'version' => '1.0.0', 'action' => 'created_domain_defaults', 'domain' => $domain, ]; } } } } /** * Migrate fields from aksrt_basic_settings to the new global domain. * * The old aksrt_basic_settings contains many fields from different domains * (auth, comment, avatar, etc.). We selectively map them to the new structure * without deleting the original option. */ private function migrate_basic_to_global(AKSRT_Admin_Schema_Provider $schema_provider, array &$log): void { $old = get_option('aksrt_basic_settings', []); if (!is_array($old) || empty($old)) return; // Map old keys to new global domain keys $field_map = [ 'comment_enabled' => 'comment_enabled', 'comments_per_page' => 'comments_per_page', 'comment_requires_registration' => 'comment_requires_registration', 'lazy_load' => 'lazy_load', 'avatar_source' => 'avatar_source', 'icp_filing' => 'icp_filing', 'footer_text' => 'footer_text', 'copyright_year' => 'copyright_year', 'registration_enabled' => 'registration_enabled', 'email_verification' => 'email_verification', ]; $new_data = []; foreach ($field_map as $old_key => $new_key) { if (isset($old[$old_key])) { $new_data[$new_key] = $old[$old_key]; } } if (!empty($new_data)) { $existing = get_option('aksrt_basic_settings', []); if (!is_array($existing)) $existing = []; // Merge: new mapped values take precedence only if not already set $merged = wp_parse_args($existing, $new_data); update_option('aksrt_basic_settings', $merged); $log[] = [ 'version' => '1.0.0', 'action' => 'migrated_basic_to_global', 'fields' => array_keys($new_data), 'migrated' => count($new_data), ]; } } private function migrate_v1_2_0(array &$log): void { $settings = get_option('aksrt_settings', []); if (!is_array($settings) || empty($settings)) { return; } $map = [ 'header_slider_search' => 'header_components_search_enabled', 'header_slider_cards' => 'header_components_cards_enabled', 'header_slider_nav_color' => 'header_components_nav_color', 'header_slider_show' => 'header_components_show_on', 'header_slider_show_type' => 'header_components_device_visibility', 'header_slider_filter_blur' => 'header_components_filter_blur_devices', 'header_slider_card_show' => 'header_components_card_show_devices', 'header_card_shared_bg' => 'header_components_card_shared_bg', 'header_card_blur' => 'header_components_card_blur', 'header_card_icon_shape' => 'header_components_card_icon_shape', 'header_icon_cards' => 'header_components_icon_cards', 'header_slider_search_pc' => 'header_components_search_pc', 'header_slider_search_mobile' => 'header_components_search_mobile', 'header_slider_search_show_keywords' => 'header_components_search_show_keywords', 'header_slider_search_popular_limit' => 'header_components_search_popular_limit', 'header_slider_search_show_input_cat' => 'header_components_search_show_input_cat', 'header_slider_search_show_type' => 'header_components_search_show_type', ]; $migrated = []; foreach ($map as $old_key => $new_key) { if (array_key_exists($old_key, $settings) && !array_key_exists($new_key, $settings)) { $settings[$new_key] = $settings[$old_key]; $migrated[] = $old_key; } if (array_key_exists($old_key, $settings)) { unset($settings[$old_key]); } } if (!empty($migrated)) { update_option('aksrt_settings', $settings); $log[] = [ 'version' => '1.2.0', 'action' => 'renamed_header_components_keys', 'migrated' => $migrated, ]; } } private function migrate_v1_3_0(array &$log): void { $settings = get_option('aksrt_settings', []); if (!is_array($settings) || empty($settings)) { return; } $map = [ 'homepage_hero_enabled' => 'homepage_module_hero_enabled', 'homepage_banner_enabled' => 'homepage_module_banner_enabled', ]; $migrated = []; foreach ($map as $old_key => $new_key) { if (array_key_exists($old_key, $settings) && !array_key_exists($new_key, $settings)) { $settings[$new_key] = $settings[$old_key]; $migrated[] = $old_key; } if (array_key_exists($old_key, $settings)) { unset($settings[$old_key]); } } if (!empty($migrated)) { update_option('aksrt_settings', $settings); $log[] = [ 'version' => '1.3.0', 'action' => 'renamed_homepage_module_toggle_keys', 'migrated' => $migrated, ]; } } public function map_legacy_key(string $option_key): ?array { $map = [ 'aksrt_basic_settings' => ['domain' => 'global', 'key' => 'aksrt_basic_settings'], 'aksrt_seo_settings' => ['domain' => 'seo', 'key' => 'aksrt_seo_settings'], 'aksrt_mail_smtp' => ['domain' => 'global', 'key' => 'aksrt_mail_smtp'], 'aksrt_oauth' => ['domain' => 'users', 'key' => 'aksrt_oauth'], 'aksrt_moderation_config' => ['domain' => 'permissions', 'key' => 'aksrt_moderation_config'], 'aksrt_captcha_config' => ['domain' => 'permissions', 'key' => 'aksrt_captcha_config'], 'aksrt_credit_settings' => ['domain' => 'users', 'key' => 'aksrt_credit_settings'], 'aksrt_notification_settings' => ['domain' => 'users', 'key' => 'aksrt_notification_settings'], 'aksrt_footer_settings' => ['domain' => 'page_display', 'key' => 'aksrt_footer_settings'], 'aksrt_footer_tabbar' => ['domain' => 'page_display', 'key' => 'aksrt_footer_tabbar'], 'aksrt_floating_buttons' => ['domain' => 'global', 'key' => 'aksrt_floating_buttons'], 'aksrt_friend_links' => ['domain' => 'page_display', 'key' => 'aksrt_friend_links'], 'aksrt_banners' => ['domain' => 'page_display', 'key' => 'aksrt_banners'], 'aksrt_category_recommend' => ['domain' => 'page_display', 'key' => 'aksrt_category_recommend'], ]; return $map[$option_key] ?? null; } }