WordPress vs WooCommerce categories with Rest API in C#

By , last updated August 15, 2019

Categories are an important part of WordPress and WooCommerce solutions. They give an opportunity to group similar items together. If you are using WordPress as a CMS for your online shop, chances are you will need the WooCommerce plugin to manage your products.

Using standard free plugins is time consuming. Working with WooCommerce inside WordPress is a lot of work: first you need to create all your products and then publish them inside posts or pages. The complexity rises if you target several countries with different varieties of the same products.

Automating the process is the answer. Both WordPress and WooCommerce offer their own REST APIs that you can use to automate product creation and publishing: WordPress Rest API, WooCommerce Rest API.

There is a difference between WordPress and WooCommerce categories. They are both Terms in the WP database, but have different taxonomies: “category” for WordPress and “product_cat” for WooCommerce.

WordPress categories

In order to fetch and save categories through WordPress Rest API in C# we have chosen the library WordPressPCL. No need to reinvent the wheel if there are libraries out there that you can adjust to your own needs and contribute in the process.

To begin with, we used the WordPressSharp library, which uses the XML-RPC WordPress interface. It didn’t want to work with categories, so we switched over to WordPressPCL. It is incomplete, but is open source. To get WordPressPCL to work with WordPress categories, we had to extend it. There we’ll publish the code after some polishing.

Fetching WordPress categories

The process of getting the categories in C# with WordPressPCL is as follows:

  1. Initialize the consumer of the API.
    WordPressClient _wprest = new WordPressClient($"{base_url}/wp-json/");
    _wprest.Username = user;
    _wprest.Password = pass;
    
  2. Get categories as a list of WordPressPCL categories.
    public List<WordPressPCL.Models.Category> GetCategories()
    {
    	List<WordPressPCL.Models.Category> cats = null;
    
    	if (_wprest != null)
    	{
    		Task.Run(() =>
    		{
    			var cat_task = _wprest.ListCategories();
    			cat_task.Wait();
    			cats = cat_task.Result.ToList();
    		}).Wait();
    	}
    
    	return cats;
    }
    
  3. Create a XAML UserControl to show categories inside a Grid as a TreeView with checkboxes.
    <UserControl x:Class="mywoo.WpCategories"
                 xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
                 xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
                 xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" 
                 xmlns:d="http://schemas.microsoft.com/expression/blend/2008" 
                 xmlns:local="clr-namespace:woo_pdf.PDF"
                 mc:Ignorable="d" 
                 d:DesignHeight="300" d:DesignWidth="120">
        <Grid >
            <TreeView x:Name="treeCategories" ItemsSource="{Binding}" >
            </TreeView>
    
        </Grid>
    </UserControl>
    
  4. Insert WordPress categories into MainWindow with C# XAML.
    <Window x:Class="MainWindow"
            xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
            xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
            xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
            xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
            xmlns:local_woo="clr-namespace:mywoo"
            mc:Ignorable="d"
            Name="MyWoo" Height="692.084" Width="715.226">
        <Grid>
            <local_woo:WpCategories MinHeight="200" x:Name="wpcats_post"/>
        </Grid>
    </Window>
    
  5. Show the categories that we have fetched from WordPress in the new XAML window with TreeView and checkboxes.
    var cats = GetCategories();
    wpcats_post.SetCategories(cats);
    
    
    
    public void SetCategories(List<WordPressPCL.Models.Category> cats)
    {
    	var parents = cats.Where(p => p.ParentId == 0);
    
    	foreach (var c in parents)
    	{
    		var children = find_children(c, cats);
    		var p = MakeTreeViewItem(c);
    
    		foreach (var child in children)
    		{
    			child.Items.Add(d);
    		}
    
    		treeCategories.Items.Add(p);
    	}
    }
    

Resulting categories look almost the same as in WordPress:

Saving chosen WordPress categories

The process of saving chosen categories for the post with WordPressPCL is as follows:

  1. Get selected categories from XAML.
    var selectedCategories = wpcats_post.SelectedCategories();
    
    public List<int> SelectedCategories()
    {
    	return _selected;
    }
    

    Variable _selected is a list holding all our checked categories. In order to populate the list you will need to implement the Click-event for C# CheckBox.

  2. Get existing WordPress terms for each selected category by id.
    List<Term> categoriesList = new List<Term>();
    foreach (int id in selectedCategories)
    {
    	Term term = _wp.GetTerm("category", id);
    	categoriesList.Add(term);
    }
    
  3. Create new WP Post with categories.
    var post = new Post
    {
    	PostType = "post",
    	Status = "draft",
    	Title = title,
    	Content = contents,
    	PublishDateTime = DateTime.Now,
    	ModifiedDateTime = DateTime.Now,
    	Terms = categoriesList.ToArray(),
    };
    
    _wprest.NewPost(post);
    

WooCommerce categories

As mentioned earlier WooCommerce operates with it’s own categories. Taxonomy name is “product_cat” in the WordPress “wp_term_taxonomy” database table.

Working with product categories will require use of the Woocommerce Rest API. It is a well documented API with consumer libraries like WooCommerceNET that are being actively developed and maintained.

Fetching Woocommerce categories

Using WooCommerceNET in C# .NET project is straightforward. Here is a simple tutorial on how to use WooCommerceNET API consumer.

  1. Initialize WooCommerceNET API consumer.
    RestAPI rest = new RestAPI(url, key, secret);
    WCObject wc = new WCObject(rest);
    
  2. Get all product categories as a list of ProductCategory.
    public async Task<List<ProductCategory>> GetWooCommerceCategories()
    {
    	try
    	{
    		var prod_cats = await wc.GetProductCategories();
    
    		return prod_cats;
    	}
    	catch
    	{ }
    
    	return new List<ProductCategory>();
    }
    
  3. Use the same UserControl as we did for WordPress categories. Insert product categories into MainWindow with XAML.
    <Window x:Class="MainWindow"
            xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
            xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
            xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
            xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
            xmlns:local="clr-namespace:mywoo"
            mc:Ignorable="d"
            Name="MyWoo" Height="692.084" Width="715.226">
        <Grid>
            <local:WpCategories x:Name="wpcats" />
        </Grid>
    </Window>
    
  4. Show the categories that we have fetched from Woocommerce.
    var prod_cats = ProductCategories();
    SetCategories(prod_cats);
    
    public List<ProductCategory> ProductCategories()
    {
    	List<ProductCategory> prod_cats = new List<ProductCategory>();
    
    	var t = Task.Run(async () =>
    	{
    		prod_cats = await GetWooCommerceCategories();
    	});
    
    	t.Wait();
    
    	return prod_cats;
    }
    
    public void SetCategories(List<WooCommerceNET.WooCommerce.ProductCategory> prod_cats)
    {
    	var parents = prod_cats.Where(p => p.parent == 0);
    
    	foreach (var c in parents)
    	{
    		var children = find_children(c, prod_cats);
    		var p = MakeTreeViewItem(c);
    
    		foreach (var d in children)
    		{
    			p.Items.Add(d);
    		}
    
    		treeCategories.Items.Add(p);
    	}
    }
    

Saving selected Woocommerce categories per product

The process of saving selected categories for the product is almost the same as for post categories with WordPress.

  1. Get selected product categories from XAML.
    List<int> selectedProductCategories = wpcats.SelectedCategories();
    
    public List<int> SelectedCategories()
    {
    	return _selected;
    }
    
  2. Create new category for each Woocommerce ProductCategory selected. This is needed as the Woocommerce REST API returns ProductCategory only which is an extension of WordPress category.
    List<WooCommerce.Category> categoriesList = new ListWooCommerce.Category>();
    
    foreach (int id in selectedCategories)
    {
    	var cat = GetProductCategory(id);
    
    	var simple_cat = new WooCommerce.Category
    	{
    		id = cat.id,
    		name = cat.name,
    		slug = cat.slug
    	};
    
    	categoriesList.Add(simple_cat);
    }
    
  3. Create and insert new Product into Woocommerce. In this example we have created a new external product that is also free.
    Product p = new Product()
    {
    	name = name,
    	regular_price = 0,
    	type = "external",
    	button_text = "Free download",
    	external_url = link,
    	categories = categoriesList,
    	
    };
    
    int external_id = 0;
    
    var task = Task.Run(async() => 
    {
    	external_id = await _woo.InsertProduct(p);
    });
    
    task.Wait();
    

Conclusion

It is a lot of work to fetch and save categories for both posts and products. It may save you some time to use existing libraries.