HUSKY - Product Filter for WooCommerce

Фільтр WooCommerce за категорією не дає результатів: виправлення ієрархії

Якщо фільтр WooCommerce за категорією не дає результатів для батьківських категорій, навіть якщо продукти призначено дочірнім категоріям, цей посібник допоможе вам це виправити.

Проблема

Симптом:Коли ви фільтруєте за батьківською категорією, продукти не відображаються, навіть якщо продукти існують у дочірніх категоріях.

приклад:

  • Структура категорії:Federal Actions > SEC > Enforcement
  • Продукт призначений для:Enforcement(лише дочірня категорія)
  • Фільтрування заFederal ActionsабоSECповертає:Результатів немає
  • Фільтрування заEnforcementповертає:Показаний продукт

Чому це відбувається

WordPress/WooCommerceвимагаєпродукти, які мають бути явно позначенівсі категорії батьківв ієрархії, а не лише в дочірній категорії.

Коли ви призначаєте продукт дочірньої категорії через інтерфейс адміністратора WordPress, WooCommerce автоматично не позначає продукт усіма батьківськими категоріями в таблиці зв’язків термінів. Це вимога до структури даних, а не обмеження HUSKY.

Правильне призначення категорії має включати:

  • Дитяча категорія:Enforcement
  • Батьківська категорія:SEC
  • Категорія бабусі та дідуся:Federal Actions

Як перевірити, чи є у вас ця проблема

  1. Перейдіть на сторінку редагування продукту:wp-admin/post.php?post=YOUR_PRODUCT_ID&action=edit
  2. Подивіться на метабокс «Категорії» праворуч
  3. Перевірте, якщовсі категорії батьківв ієрархії перевіряються
  4. Якщо позначено лише дочірню категорію →У вас є ця проблема

Рішення: автоматична нормалізація ієрархії категорій

Це рішення складається з двох частин:

  1. Майбутнє виправлення: автоматично позначати батьківські категорії під час збереження продуктів
  2. Негайне виправлення: нормалізуйте всі існуючі продукти

Частина 1: Автоматичне позначення батьківських категорій (майбутні продукти)

Додайте цей код до дочірніх темfunctions.php:

/**
 * Automatically mark all parent categories when product is saved
 * This ensures hierarchy filtering works correctly
 */
add_action('save_post_product', 'auto_mark_parent_categories', 10, 1);

function auto_mark_parent_categories($product_id) {
    // Clear cache
    clean_object_term_cache($product_id, 'product_cat');

    // Get currently assigned categories
    $terms = wp_get_post_terms($product_id, 'product_cat', ['fields' => 'ids']);

    if (!is_wp_error($terms) AND !empty($terms)) {
        $all_terms = [];

        // For each assigned category, get all its parents
        foreach ($terms as $term_id) {
            $all_terms[] = $term_id;

            // Get all ancestor categories
            $ancestors = get_ancestors($term_id, 'product_cat', 'taxonomy');
            if (!empty($ancestors)) {
                $all_terms = array_merge($all_terms, $ancestors);
            }
        }

        // Assign product to all categories including parents
        wp_set_object_terms($product_id, array_unique($all_terms), 'product_cat');

        // Clear caches
        clean_post_cache($product_id);
        clean_object_term_cache($product_id, 'product_cat');

        if (function_exists('wc_delete_product_transients')) {
            wc_delete_product_transients($product_id);
        }
    }
}

Що це робить:

  • Спрацьовує кожного разу, коли продукт зберігається
  • Отримує всі призначені категорії
  • Знаходить усі батьківські категорії для кожної призначеної категорії
  • Позначає продукт повною ієрархією
  • Очищає всі відповідні кеші

Результат:Відтепер будь-який збережений продукт автоматично включатиме всі батьківські категорії.

Частина 2. Нормалізація наявних продуктів (одноразове виправлення)

Цей скрипт виправить усі існуючі продукти у вашій базі даних. Додайте цетимчасовийкод до вашогоfunctions.php:

/**
 * One-time script to normalize all existing products
 * Access: yourdomain.com/?normalize_cats=1 (must be logged in as admin)
 */
add_action('init', function () {
    if (isset($_GET['normalize_cats']) AND current_user_can('manage_options')) {
        $result = normalize_all_products_categories();
        echo '<h2>Category Normalization Results</h2>';
        echo '<pre>';
        print_r($result);
        echo '</pre>';
        die();
    }
});

function normalize_all_products_categories() {
    global $wpdb;

    // Get all product IDs
    $args = [
        'post_type' => 'product',
        'post_status' => 'any',
        'posts_per_page' => -1,
        'fields' => 'ids'
    ];

    $product_ids = get_posts($args);
    $log = [];
    $normalized_count = 0;

    foreach ($product_ids as $product_id) {
        // Get current categories
        $terms = wp_get_post_terms($product_id, 'product_cat', ['fields' => 'ids']);

        if (!is_wp_error($terms) AND !empty($terms)) {
            $all_terms = [];

            // Collect all parent categories
            foreach ($terms as $term_id) {
                $all_terms[] = $term_id;

                // Get ancestors
                $ancestors = get_ancestors($term_id, 'product_cat', 'taxonomy');

                if (!empty($ancestors)) {
                    $all_terms = array_merge($all_terms, $ancestors);
                }
            }

            $all_terms = array_unique($all_terms);

            // Only update if we're adding new parent categories
            if (count($all_terms) > count($terms)) {
                wp_set_object_terms($product_id, $all_terms, 'product_cat');
                $normalized_count++;
                $log[] = "Product #{$product_id}: added " . (count($all_terms) - count($terms)) . " parent categories";
            }
        }
    }

    // Log to WordPress error log
    error_log("=== Category Normalization Complete ===");
    error_log(implode("\n", $log));
    error_log("Total normalized: {$normalized_count} products");

    return [
        'success' => true,
        'normalized' => $normalized_count,
        'total' => count($product_ids),
        'details' => $log
    ];
}

Як використовувати:

  1. Додайте код до свогоfunctions.php
  2. Перейти до:https://yoursite.com/?normalize_cats=1(потрібно увійти як адмін)
  3. Дочекайтеся завершення сценарію
  4. Ви побачите результати, які показують, скільки продуктів було оновлено
  5. Видаліть цей кодпісля одного запуску

Очікуваний результат:

Category Normalization Results
Array
(
    [success] => 1
    [normalized] => 156
    [total] => 919
)

Це означає, що для 156 продуктів із 919 відсутні батьківські категорії, і їх було виправлено.

Тестування виправлення

Після реалізації обох частин:

  1. Перейдіть на сторінку свого магазину з фільтрами HUSKY
  2. Спробуйте відфільтрувати за aбатьківська категорія
  3. Тепер мають з’явитися товари з дочірніх категорій
  4. Спробуйте детально переглянути ієрархію – усі рівні мають працювати

Чому б не зробити це типовим у HUSKY?

Це закономірне запитання. Ось чому:

  1. Зміна структури даних: це змінює основні зв’язки даних WooCommerce
  2. Не універсальний: Деякі сайти навмисно призначають лише дочірні категорії для певної бізнес-логіки
  3. Продуктивність: у дуже великих каталогах це додає накладні витрати на кожне збереження продукту
  4. Конфлікти: може заважати іншим плагінам, які керують зв’язками категорій

Майбутнє вдосконалення: ми можемо додати це якнеобов'язкове налаштуванняу HUSKY, який користувачі можуть увімкнути за потреби, але це не буде поведінкою за замовчуванням.

Альтернатива: призначення категорії вручну

Якщо ви віддаєте перевагу ручному управлінню, ви можете:

  1. Відредагуйте кожен товар
  2. У метавікні Категорії поставте прапорецьусі відповідні категорії батьківвручну
  3. Збережіть товар

Це дає вам детальний контроль, але займає багато часу для великих каталогів.

Усунення несправностей

Сценарій показує 0 нормалізованих продуктів

  • Можливо, вашим продуктам уже призначено правильні батьківські категорії
  • Перевірте кілька продуктів вручну, щоб перевірити

Після нормалізації фільтрація все ще не працює

  • Очистити всі кеші (WordPress, сервер, браузер)
  • Переконайтеся, що HUSKY використовує правильну таксономію (product_cat)
  • Перевірте наявність конфліктів з іншими плагінами фільтрів
  • Переконайтеся, що продукти опубліковані (не чернетки)

Продукти зникають із фільтра дочірніх категорій

Цього не повинно статися, але якщо це станеться:

  • Сценарій зберігає всі існуючі призначення категорій
  • Перевірте, чи не заважає інший плагін
  • Відновіть із резервної копії та зверніться до служби підтримки

Спеціальні таксономії

Це рішення також працює дляспеціальні таксономіїстворений за допомогою CPT UI або подібних плагінів. Просто змінити'product_cat'до вашої спеціальної таксономії:

// Example for custom taxonomy 'modality'
$terms = wp_get_post_terms($product_id, 'modality', ['fields' => 'ids']);
wp_set_object_terms($product_id, array_unique($all_terms), 'modality');

Важливі зауваження

  • Потрібна дочірня тема: Завжди використовуйте дочірню тему, щоб запобігти втраті коду під час оновлення теми
  • Спершу резервне копіювання: створіть резервну копію бази даних перед запуском сценарію нормалізації
  • Тест на постановку: Якщо це можливо, спершу перевірте на тестовому сайті
  • Одноразовий сценарій: видаліть сценарій нормалізації після його запуску
  • Зберігайте код частини 1: Thesave_post_productгачок повинен залишатися постійно

Резюме

Додайте до functions.php назавжди:

  • Автоматично позначати хук батьківських категорій (частина 1)

Запустіть один раз і видаліть:

  • Скрипт нормалізації (частина 2)

Очікувані результати:

  • Фільтрування батьківських категорій працює правильно
  • Фільтр дочірніх категорій продовжує працювати
  • Деталізація ієрархії працює належним чином
  • Майбутні продукти автоматично включають батьківські категорії