Where is this function hooked?
widgets_init
is hooked into init
at priority 1
, but WooCommerce registers its taxonomies in init
at priority 5
. So if you use widgets_init
as the hook you won’t be able to use get_terms()
because it returns a WP_Error
if the taxonomy isn’t registered.
You’ll need to register the widget on init
at a priority greater than 5
for this to work, and you should still check that the result of get_terms()
isn’t a WP_Error
, in case WooCommerce isn’t activated:
function wpse_295558_category_sidebars() {
$product_cats = get_terms( array(
'taxonomy' => 'product_cat',
'hide_empty' => false,
'parent' => 0,
);
if ( ! is_wp_error( $product_cats ) ) {
foreach ( $product_cats as $product_cat ) {
register_sidebar( array(
'name' => 'Filter sidebar -' . $product_cat->name,
'id' => 'filter_sidebar_' . $product_cat->name,
'before_widget' => '<div class="filter-sidebar-' . $product_cat->name . '">',
'after_widget' => '</div>',
'before_title' => '<h2 class="filter-title">',
'after_title' => '</h2>',
) );
}
}
}
add_action( 'init', 'wpse_295558_category_sidebars', 10 );
This seems like an unwieldy method to achieve whatever you’re after though. Wouldn’t it be better to have one sidebar for categories and then have the widgets dynamically respond to which category you’re viewing? This is already how the bundled filter widgets work in WooCommerce.