2015-01-21 2 views
7

То, что я пытаюсь сделать, - это поиск по позиции заказа SKU или ID на странице администрирования заказов Woocommerce. То, что я нашел/сделал до сих пор, но без успеха, выглядит следующим образом в файле functions.php.Поиск по заказу SKU или ID в Woocommerce Orders Административная страница

add_filter('woocommerce_shop_order_search_fields', 'woocommerce_shop_order_search_sku'); 

function woocommerce_shop_order_search_sku($search_fields) { 

$args = array(
    'post_type' => 'shop_order' 
    ); 

$orders = new WP_Query($args); 

if($orders->have_posts()) { 
     while($orders->have_posts()) { 
     $post = $orders->the_post(); 
     $order_id = get_the_ID(); 
     $order = new WC_Order($order_id); 
     $items = $order->get_items(); 
     foreach($items as $item) { 
      $search_order_item_sku = wp_get_post_terms($item['product_id'], 'search_sku'); 
      foreach($search_order_item_sku as $search_sku) { 
       add_post_meta($order_id, "_search_sku", $search_sku->sku); 
      } 
     } 
    } 
}; 

$search_fields[] = '_search_sku'; 

return $search_fields; 

} 

Я полагаю, что вопрос является значение $ search_sku в соответствии с «add_post_meta». Я также попробовал его с get_sku(), $ item ['sku'] без везения.

Любые предложения?

+0

Я не понимаю. Похоже, вы не уверены, что $ search_sku-> sku или другие варианты даже имеют значение. Почему бы вам просто не запустить print_r ($ search_sku); умереть(); в вашем цикле foreach и посмотреть на него, чтобы определить, какое свойство объекта или массив необходимо использовать для ссылки? –

+1

Посмотрите на функцию _shop_order_search_custom_fields() _ в /woocommerce/includes/admin/class-wc-admin-post-types.php (строка ~ 1284).Из того, что я могу сказать, инструкция SELECT там только ищет таблицы wp_posts и wp_postmeta. SKU являются специфичными для продукта. Таким образом, вам нужно каким-то образом создать свой собственный запрос для UNION в (и поиске) данных о продуктах. – Jibran

+1

Уточнение: ... ищет только таблицы wp_posts и wp_postmeta для типов post _shop_order_. – Jibran

ответ

1

@blacksquare, @jibby, @helgatheviking, вы - мужчины! Это код, который работает, из-за вашей помощи.

//Search by product SKU in Admin Woocommerce Orders 
add_filter('woocommerce_shop_order_search_fields', function ($search_fields) { 
    $posts = get_posts(array('post_type' => 'shop_order')); 

    foreach ($posts as $post) { 
     $order_id = $post->ID; 
     $order = new WC_Order($order_id); 
     $items = $order->get_items(); 

     foreach($items as $item) { 
      $product_id = $item['product_id']; 
      $search_sku = get_post_meta($product_id, "_sku", true); 
      add_post_meta($order_id, "_product_sku", $search_sku); 
     } 
    } 

    return array_merge($search_fields, array('_product_sku')); 
}); 
2

У вас есть правильная идея об экономии дополнительных метаданных в заказе. Как показывают предложения jbby и helgatheviking, встроенная postmeta для product_id или sku доступна по умолчанию в заказах woocommerce api. Однако ваша методология для доступа и сохранения метаданных была не совсем правильной. wp_get_post_terms получит доступ к информации о таксономии, а не метаданным (используйте для этого get_post_meta). Вы будете в состоянии сделать то, что вы пытаетесь сделать с этим фильтром:

add_filter('woocommerce_shop_order_search_fields', function ($search_fields) { 
    $posts = get_posts(array('post_type' => 'shop_order')); 

    foreach ($posts as $post) { 
     $order_id = $post->ID; 
     $order = new WC_Order($order_id); 
     $items = $order->get_items(); 

     foreach($items as $item) { 
      $product_id = $item['product_id']; 
      $search_sku = get_post_meta($product_id, "_sku", true); 
      add_post_meta($order_id, "_product_sku", $search_sku); 
      add_post_meta($order_id, "_product_id", $product_id); 
     } 
    } 

    return array_merge($search_fields, array('_product_sku', '_product_id')); 
}); 

Строго говоря, вы, вероятно, следует переместить вызовы add_post_meta в крюк, который работает, когда заказ был сохранен в базе данных - это предотвратит ненужную работу с ногами, когда вы будете выполнять поиск по заказу.

+1

Ошибка кода (мало): вам нужно заменить в коде неопределенный '$ sku' на' $ search_sku'. – LoicTheAztec

1

В то время как ответы @Nikos и @blacksquare работают, каждый почтовый метам добавляется к каждому заказу при каждом поиске. Если у вас есть 100 заказов и выполните 10 поисков, в таблице wp_postmeta будет не менее 100 * 10 = 1000 _product_sku записей. Если в некоторых заказах содержится несколько продуктов, их будет еще больше.

Как предложено @blacksquare, следует вызвать add_post_meta, когда заказ сохранен. Тем не менее, если сайт небольшой, а производительность бэкэнд-поиска не слишком важна, следующий код будет работать без создания избыточных записей _product_sku.

add_filter('woocommerce_shop_order_search_fields', 'my_shop_order_search_fields')); 

public function my_shop_order_search_fields($search_fields) { 
    $orders = get_posts(array(
     'post_type' => 'shop_order', 
     'post_status' => wc_get_order_statuses(), //get all available order statuses in an array 
     'posts_per_page' => 999999, // query all orders 
     'meta_query' => array(
      array(
       'key' => '_product_sku', 
       'compare' => 'NOT EXISTS' 
      ) 
     ) // only query orders without '_product_sku' postmeta 
    )); 

    foreach ($orders as $order) { 
     $order_id = $order->ID; 
     $wc_order = new WC_Order($order_id); 
     $items = $wc_order->get_items(); 
     foreach($items as $item) { 
      $product_id = $item['product_id']; 
      $search_sku = get_post_meta($product_id, '_sku', true); 
      add_post_meta($order_id, '_product_sku', $search_sku); 
     } 
    } 

    return array_merge($search_fields, array('_product_sku')); // make '_product_sku' one of the meta keys we are going to search for. 
} 

Хотя лучшее решение может быть вызовом add_post_meta при создании заказа, дополнительные усилия, необходимые для создания _product_sku для существующих заказов, и вы должны создать _product_sku для заказов, сделанных в то время как код не активирован. Для простоты я бы просто использовал предложенное выше решение.

p.s. Решение @Nikos «ы есть один (спорно) преимущество - если изменить SKU продукта, после того, как заказы сделаны, решение Никоса найдет те заказы, используя новый SKU, в то время как выше решение не будет. Тем не менее, SKU или иной продукт не должен быть изменен в любом случае, и это спорно ли поиск новых артикулов должны показывать старые заказы.

Смежные вопросы