Click here to Skip to main content
15,887,952 members
Articles / Programming Languages / C#
Technical Blog

Retrieving a list of eBay categories in a .NET 4.5 Windows Store App

Rate me:
Please Sign up or sign in to vote.
4.00/5 (1 vote)
28 Jan 2013CPOL2 min read 12.4K   2  
Retrieving a list of eBay categories in a .NET 4.5 Windows Store app.

Previously I wrote a post on how to get the eBay category list using their .NET SDK. I wanted to try doing the same thing in a Windows Store App for Windows 8 using Visual Studio 2012, but quickly ran into compatibility problems since the DLLs are compiled for .NET 2.0. I could have either changed the targeted framework, or attempted to re-write the DLLs, but neither sounded particularly exciting, so I simply decided to fall back to using a simple URL request and parsing it via LINQ to XML.

As mentioned in the previous post, the first step is to join the eBay Developer Program. Once you've joined and gotten your app ID, you can try a simple request with this URL:

http://open.api.ebay.com/Shopping?callname=GetCategoryInfo&appid=yourappid8&version=679&siteid=0&CategoryID=-1&IncludeSelector=ChildCategories

Passing CategoryID=-1 returns the top-level categories, like this:

XML
<GetCategoryInfoResponse xmlns="urn:ebay:apis:eBLBaseComponents"> 
   <Timestamp>2012-12-19T16:03:33.893Z</Timestamp> 
   <Ack>Success</Ack> 
   <Build>E803_CORE_BUNDLED_15627359_R1</Build> 
   <Version>803</Version> 
   <CategoryArray> 
      <Category> 
         <CategoryID>-1</CategoryID> 
         <CategoryLevel>0</CategoryLevel> 
         <CategoryName>Root</CategoryName> 
         <CategoryParentID>0</CategoryParentID> 
         <LeafCategory>false</LeafCategory> 
      </Category> 
      <Category> 
         <CategoryID>20081</CategoryID> 
         <CategoryLevel>1</CategoryLevel> 
         <CategoryName>Antiques</CategoryName> 
         <CategoryParentID>-1</CategoryParentID> 
         <CategoryNamePath>Antiques</CategoryNamePath> 
         <CategoryIDPath>20081</CategoryIDPath> 
         <LeafCategory>false</LeafCategory> 
      </Category> 
(etc.)

You can continue to walk down the category tree by passing the sub-category IDs.

The first step will be to fire up an HttpClient and send an asynchronous GET request to the URL:

C#
private async Task<string> CallGetCategoryInfo(int CategoryID) 
{ 
    httpClient = new HttpClient(); 
    string searchUrl = "http://open.api.ebay.com/Shopping?callname=GetCategoryInfo";
    string requestUrl = searchUrl + "&appid=" + api_key + "&version=679&siteid=0&CategoryID=" + 
      CategoryID.ToString() + "&IncludeSelector=ChildCategories";
    HttpResponseMessage response = await httpClient.GetAsync(requestUrl);

Next we'll load the response stream into an XDocument and create a LINQ query:

C#
System.Xml.Linq.XDocument doc = System.Xml.Linq.XDocument.Load(await response.Content.ReadAsStreamAsync());
XNamespace ns = "urn:ebay:apis:eBLBaseComponents";
var query = from categories in doc.Descendants(ns + "Category") 
    select new 
    { 
        CategoryID = categories.Element(ns + "CategoryID").Value, 
        CategoryParentID = categories.Element(ns + "CategoryParentID").Value, 
        CategoryName = categories.Element(ns + "CategoryName").Value, 
        LeafCategory = categories.Element(ns + "LeafCategory").Value, 
    };

We'll add the results of the query to a List of objects. I only needed the category name and ID, so that's all my object has:

C#
public class ComboBoxPairs 
{ 
    public string categoryName { get; set; } 
    public int categoryId { get; set; }
    public ComboBoxPairs(string CategoryName, int CategoryId) 
    { 
        categoryName = CategoryName; 
        categoryId = CategoryId; 
    } 
}

And here I add the objects to the List:

C#
List<ComboBoxPairs> cbp = new List<ComboBoxPairs>();
foreach (var element in query) 
{ 
    //The first category returned in the xml will always be either root, or the parent level category. 
    // I don't want it in the list 
    if (element.CategoryID != "-1" && element.CategoryID != _categoryID.ToString()) 
    { 
        cbp.Add(new ComboBoxPairs(element.CategoryName, Convert.ToInt32(element.CategoryID))); 
    } 
}

Finally I assign the List to a global variable and exit:

C#
_cbp = cbp; 
return "Finished";

The big difference between this method and using the SDK is that you can only return one level at a time. This is probably a good thing; the web service is responsive enough that there's no noticeable wait to the call, versus a distinct wait (and massive size) for retrieving the entire list. If you did want the entire list for some reason, you can simply drill down - use a category ID of -1 (the root category ID) on the first call to get all the level 1 categories, then use a level 1 category ID on the second call to get all the level 2 children of the specified category ID, and so forth. When you get to LeafCategory = true, you can stop.

If you omit the &IncludeSelector=ChildCategories flag then you'll just get info for the selected category, but you'll also get the version and last update time, like this:

<GetCategoryInfoResponse xmlns="urn:ebay:apis:eBLBaseComponents"> 
   <Timestamp>2012-12-19T16:37:46.516Z</Timestamp> 
   <Ack>Success</Ack> 
   <Build>E803_CORE_BUNDLED_15627359_R1</Build> 
   <Version>803</Version> 
   <CategoryArray> 
      <Category> 
         <CategoryID>-1</CategoryID> 
         <CategoryLevel>0</CategoryLevel> 
         <CategoryName>Root</CategoryName> 
         <CategoryParentID>0</CategoryParentID> 
         <LeafCategory>false</LeafCategory> 
      </Category> 
   </CategoryArray> 
   <CategoryCount>1</CategoryCount> 
   <UpdateTime>2012-09-11T02:42:04.000Z</UpdateTime> 
   <CategoryVersion>102</CategoryVersion> 
</GetCategoryInfoResponse>

If you're storing the information locally you can then compare to determine whether the category has changed; if it hasn't, skip the full query and move on to the next.

Here's the full code:

C#
private async Task<string> CallGetCategoryInfo(int CategoryID) 
{ 
    // http://open.api.ebay.com/Shopping?callname=GetCategoryInfo&appid=appID&version=679&siteid=0&CategoryID=-1&IncludeSelector=ChildCategories
    httpClient = new HttpClient(); 
    string searchUrl = "http://open.api.ebay.com/Shopping?callname=GetCategoryInfo";
    string requestUrl = searchUrl + "&appid=" + api_key + "&version=679&siteid=0&CategoryID=" + CategoryID.ToString() + "&IncludeSelector=ChildCategories";
    HttpResponseMessage response = await httpClient.GetAsync(requestUrl); 
    System.Xml.Linq.XDocument doc = System.Xml.Linq.XDocument.Load(await response.Content.ReadAsStreamAsync());
    XNamespace ns = "urn:ebay:apis:eBLBaseComponents";
    var query = from categories in doc.Descendants(ns + "Category") 
        select new 
        { 
            CategoryID = categories.Element(ns + "CategoryID").Value, 
            CategoryParentID = categories.Element(ns + "CategoryParentID").Value, 
            CategoryName = categories.Element(ns + "CategoryName").Value, 
            LeafCategory = categories.Element(ns + "LeafCategory").Value, 
        };
    List<ComboBoxPairs> cbp = new List<ComboBoxPairs>();
    foreach (var element in query) 
    { 
        //The first category returned in the xml will always be either root, or the parent level category 
        //I don't want it in the list 
        if (element.CategoryID != "-1" && element.CategoryID != _categoryID.ToString()) 
        { 
            cbp.Add(new ComboBoxPairs(element.CategoryName, Convert.ToInt32(element.CategoryID))); 
        } 
    }
    _cbp = cbp; 
    return "Finished"; 
}
public class ComboBoxPairs 
{ 
    public string categoryName { get; set; } 
    public int categoryId { get; set; }
    public ComboBoxPairs(string CategoryName, int CategoryId) 
    { 
        categoryName = CategoryName; 
        categoryId = CategoryId; 
    } 
}

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)


Written By
United States United States
This member has not yet provided a Biography. Assume it's interesting and varied, and probably something to do with programming.

Comments and Discussions

 
-- There are no messages in this forum --