Parse/Read XML Having Nested Nodes To Display As A List In ASP.NET MVC

Overview

In this article, we will learn how to parse XML having nested nodes in C#. This will help in a situation where the Server is returning XML as its response.

In this application, I am using an XML file that is saved on a local machine. This application reads the XML file and then associates the XML node values to the model which will display as a list. In real time, if the Server returns XML string as a response, we can directly parse the XML string instead of saving it in a file to read.

Below is the XML that is used in this application.

(userlist.xml) 
  1. <?xml version="1.0"?>  
  2. <Users>  
  3.     <user>  
  4.         <id>1</id>  
  5.         <name>Emma watson</name>  
  6.         <gender>Male</gender>  
  7.         <mobile>4557841155</mobile>  
  8.         <address>  
  9.             <streetname>Street1</streetname>  
  10.             <city>Pune</city>  
  11.             <pin>400043</pin>  
  12.         </address>  
  13.     </user>  
  14.     <user>  
  15.         <id>2</id>  
  16.         <name>Fred ordan</name>  
  17.         <gender>Female</gender>  
  18.         <mobile>4557841155</mobile>  
  19.         <address>  
  20.             <streetname>Street2</streetname>  
  21.             <city>Mumbai</city>  
  22.             <pin>400041</pin>  
  23.         </address>  
  24.     </user>  
  25.     <user>  
  26.         <id>3</id>  
  27.         <name>John Cena</name>  
  28.         <gender>Male</gender>  
  29.         <mobile>4557841155</mobile>  
  30.         <address>  
  31.             <streetname>Street3</streetname>  
  32.             <city>Pune</city>  
  33.             <pin>400045</pin>  
  34.         </address>  
  35.     </user>  
  36.     <user>  
  37.         <id>4</id>  
  38.         <name>Wilson ordan</name>  
  39.         <gender>Male</gender>  
  40.         <mobile>4557841155</mobile>  
  41.         <address>  
  42.             <streetname>Street4</streetname>  
  43.             <city>Pune</city>  
  44.             <pin>400043</pin>  
  45.         </address>  
  46.     </user>  
  47.     <user>  
  48.         <id>5</id>  
  49.         <name>Robort John</name>  
  50.         <gender>Male</gender>  
  51.         <mobile>4557841155</mobile>  
  52.         <address>  
  53.             <streetname>Street5</streetname>  
  54.             <city>Pune</city>  
  55.             <pin>400042</pin>  
  56.         </address>  
  57.     </user>  
  58. </Users>   

Step 1

Create an MVC web application.


Step 2

Create UsersModel and UsersController in "Models" and "Controllers" folders respectively.


Step 3

Define properties for “UsersModel” as shown below.

  1. namespace Xml_MVC.Models  
  2. {  
  3.     public class UsersModel  
  4.     {  
  5.         public int Id { get; set; }  
  6.         public string Name { get; set; }  
  7.         public string Gender { get; set; }  
  8.         public string Mobile { get; set; }  
  9.         public string StreetName { get; set; }  
  10.         public string City { get; set; }  
  11.         public string Pin { get; set; }  
  12.     }  
  13. }   

Step 4

Create a ListView for user list.

Go to UsersController -> right click on Index() action -> select "Add View".


 In Add View window, keep the View name as Index, select template of List type, select the model class UsersModel, and click "Add".


You will see a View page with the following code.

  1. @model IEnumerable<Xml_MVC.Models.UsersModel>  
  2. @{  
  3.     ViewBag.Title = "Index";  
  4. }  
  5. <h2>Index</h2>  
  6. <p>  
  7.     @Html.ActionLink("Create New""Create")  
  8. </p>  
  9. <table class="table">  
  10.     <tr>  
  11.         <th>  
  12.             @Html.DisplayNameFor(model => model.Name)  
  13.         </th>  
  14.         <th>  
  15.             @Html.DisplayNameFor(model => model.Gender)  
  16.         </th>  
  17.         <th>  
  18.             @Html.DisplayNameFor(model => model.Mobile)  
  19.         </th>  
  20.         <th>  
  21.             @Html.DisplayNameFor(model => model.StreetName)  
  22.         </th>  
  23.         <th>  
  24.             @Html.DisplayNameFor(model => model.City)  
  25.         </th>  
  26.         <th>  
  27.             @Html.DisplayNameFor(model => model.Pin)  
  28.         </th>  
  29.         <th></th>  
  30.     </tr>  
  31.   
  32. @foreach (var item in Model) {  
  33.     <tr>  
  34.         <td>  
  35.             @Html.DisplayFor(modelItem => item.Name)  
  36.         </td>  
  37.         <td>  
  38.             @Html.DisplayFor(modelItem => item.Gender)  
  39.         </td>  
  40.         <td>  
  41.             @Html.DisplayFor(modelItem => item.Mobile)  
  42.         </td>  
  43.         <td>  
  44.             @Html.DisplayFor(modelItem => item.StreetName)  
  45.         </td>  
  46.         <td>  
  47.             @Html.DisplayFor(modelItem => item.City)  
  48.         </td>  
  49.         <td>  
  50.             @Html.DisplayFor(modelItem => item.Pin)  
  51.         </td>  
  52.         <td>  
  53.             @Html.ActionLink("Edit""Edit"new { id=item.Id }) |  
  54.             @Html.ActionLink("Details""Details"new { id=item.Id }) |  
  55.             @Html.ActionLink("Delete""Delete"new { id=item.Id })  
  56.         </td>  
  57.     </tr>  
  58. }  
  59. </table>   

* Don’t run the View now, as there is no data in the Model  and it will return an error.

Step 5

As said earlier, we are parsing the XML which is saved on local machine, so we need an upload control in the View to upload the XML file. Let’s go for it. 

  1. @using (Html.BeginForm("Upload""Users", FormMethod.Post, new { enctype = "multipart/form-data" }))  
  2. {  
  3.     <div class="upload_file">  
  4.         <input type="file" id="fileUpload" name="fileUpload" style="float:left" /><input type="submit" value="Get User List" />  
  5.     </div>  
  6. }   

The file upload control has to be added inside HTML Form helper as we are performing a post action on file upload.

enctype = "multipart/form-data" - This is an encoding type that allows files to be sent through a POST request. Without this encoding, the files cannot be sent through POST. The enctype attribute specifies how the form-data should be encoded when submitting it to the Server.

As we are using the same View for file upload and display user list, let’s set a flag called @ViewBag.ShowList to show/hide the user list. Here, we are not performing any CRUD operations on the list. I am going to remove the unwanted code from the View.

Below is the final User List View code.

  1. @model IEnumerable<Xml_MVC.Models.UsersModel>  
  2. @{  
  3.     ViewBag.Title = "User List";  
  4. }  
  5. <h2>Display User List</h2>  
  6. @using (Html.BeginForm("Upload""Users", FormMethod.Post, new { enctype = "multipart/form-data" }))  
  7. {  
  8.     <div class="upload_file">  
  9.         <input type="file" id="fileUpload" name="fileUpload" style="float:left" /><input type="submit" value="Get User List" />  
  10.     </div>  
  11.     if (@ViewBag.ShowList)  
  12.     {  
  13.         <table class="table">  
  14.             <tr>  
  15.                 <th>  
  16.                     @Html.DisplayNameFor(model => model.Name)  
  17.                 </th>  
  18.                 <th>  
  19.                     @Html.DisplayNameFor(model => model.Gender)  
  20.                 </th>  
  21.                 <th>  
  22.                     @Html.DisplayNameFor(model => model.Mobile)  
  23.                 </th>  
  24.                 <th>  
  25.                     @Html.DisplayNameFor(model => model.StreetName)  
  26.                 </th>  
  27.                 <th>  
  28.                     @Html.DisplayNameFor(model => model.City)  
  29.                 </th>  
  30.                 <th>  
  31.                     @Html.DisplayNameFor(model => model.Pin)  
  32.                 </th>  
  33.             </tr>  
  34.             @foreach (var item in Model)  
  35.             {  
  36.                 <tr>  
  37.                     <td>  
  38.                         @Html.DisplayFor(modelItem => item.Name)  
  39.                     </td>  
  40.                     <td>  
  41.                         @Html.DisplayFor(modelItem => item.Gender)  
  42.                     </td>  
  43.                     <td>  
  44.                         @Html.DisplayFor(modelItem => item.Mobile)  
  45.                     </td>  
  46.                     <td>  
  47.                         @Html.DisplayFor(modelItem => item.StreetName)  
  48.                     </td>  
  49.                     <td>  
  50.                         @Html.DisplayFor(modelItem => item.City)  
  51.                     </td>  
  52.                     <td>  
  53.                         @Html.DisplayFor(modelItem => item.Pin)  
  54.                     </td>  
  55.                 </tr>  
  56.             }  
  57.         </table>  
  58.     }  

Step 6

Now, let's come to the actual implementation of UsersController. Create an action method called Upload() of request type POST.

  1. Make sure to include the below namespaces.
    1. using System.Xml;  
    2. using Xml_MVC.Models; (Xml_MVC - > project where the models are present)  
  1. Create a list type Model Oobject and go for parsing as below.
    1. List<UsersModel> userList = new List<UsersModel>();  
    2.             var file = Request.Files[0];  
    3.             if (file != null && file.ContentLength > 0)  
    4.             {  
    5.                 XmlDocument xmldoc = new XmlDocument();  
    6.                 xmldoc.Load(file.InputStream);  
    7.                 UsersModel user;  
    8.                 XmlNodeList usernodes = xmldoc.SelectNodes("Users/user");  
    9.                 foreach (XmlNode usr in usernodes)  
    10.                 {  
    11.                     user = new UsersModel();  
    12.                     user.Id = Convert.ToInt32(usr["id"].InnerText);  
    13.                     user.Name = usr["name"].InnerText;  
    14.                     user.Gender = usr["gender"].InnerText;  
    15.                     user.Mobile = usr["mobile"].InnerText;  
    16.                     XmlNodeList addrNodes = usr.SelectNodes("address");  
    17.                     foreach (XmlNode addrn in addrNodes)  
    18.                     {  
    19.                         user.StreetName = addrn["streetname"].InnerText;  
    20.                         user.City = addrn["city"].InnerText;  
    21.                         user.Pin = addrn["pin"].InnerText;  
    22.                     }  
    23.                     userList.Add(user);  
    24.                 }  
    25.                 TempData["userData"] = userList;  
    26.             }  
    27.             return RedirectToAction("Index");  
  1. XmlDocument - It represents an XML document which can be used to load, validate, edit, and add XML in a document.

    XmlNodeList - It represents an ordered collection of nodes and can retrieve a node at the given index.

    XmlNode - It represents a single node in the XML document and can access the attributes of the node.

    TempData["userData"] - It is used to save the user object which can be accessed in the Index() action method to display user list.

  1. Go to the Index() action and add the below code.
    1. public ActionResult Index()  
    2.         {  
    3.             if (TempData["userData"] == null)  
    4.             {  
    5.                 ViewBag.ShowList = false;  
    6.                 return View();  
    7.             }  
    8.             else  
    9.             {  
    10.                 List<UsersModel> lst = (List<UsersModel>)TempData["userData"];  
    11.                 ViewBag.ShowList = true;  
    12.                 return View(lst);  
    13.             }  
    14.         }  

Step 7

Below is the full code of UsersController.

  1. using System;  
  2. using System.Collections.Generic;  
  3. using System.Linq;  
  4. using System.Web;  
  5. using System.Web.Mvc;  
  6. using System.Xml;  
  7. using Xml_MVC.Models;  
  8.   
  9. namespace Xml_MVC.Controllers  
  10. {  
  11.     public class UsersController : Controller  
  12.     {  
  13.         // GET: Users  
  14.         public ActionResult Index()  
  15.         {  
  16.             if (TempData["userData"] == null)  
  17.             {  
  18.                 ViewBag.ShowList = false;  
  19.                 return View();  
  20.             }  
  21.             else  
  22.             {  
  23.                 List<UsersModel> lst = (List<UsersModel>)TempData["userData"];  
  24.                 ViewBag.ShowList = true;  
  25.                 return View(lst);  
  26.             }  
  27.         }  
  28.         [HttpPost]  
  29.         public ActionResult Upload()  
  30.         {  
  31.             try  
  32.             {  
  33.                 List<UsersModel> userList = new List<UsersModel>();  
  34.                 var file = Request.Files[0];  
  35.                 if (file != null && file.ContentLength > 0)  
  36.                 {  
  37.                     XmlDocument xmldoc = new XmlDocument();  
  38.                     xmldoc.Load(file.InputStream);  
  39.                     UsersModel user;  
  40.                     XmlNodeList usernodes = xmldoc.SelectNodes("Users/user");  
  41.                     foreach (XmlNode usr in usernodes)  
  42.                     {  
  43.                         user = new UsersModel();  
  44.                         user.Id = Convert.ToInt32(usr["id"].InnerText);  
  45.                         user.Name = usr["name"].InnerText;  
  46.                         user.Gender = usr["gender"].InnerText;  
  47.                         user.Mobile = usr["mobile"].InnerText;  
  48.                         XmlNodeList addrNodes = usr.SelectNodes("address");  
  49.                         foreach (XmlNode addrn in addrNodes)  
  50.                         {  
  51.                             user.StreetName = addrn["streetname"].InnerText;  
  52.                             user.City = addrn["city"].InnerText;  
  53.                             user.Pin = addrn["pin"].InnerText;  
  54.                         }  
  55.                         userList.Add(user);  
  56.                     }  
  57.                     TempData["userData"] = userList;  
  58.                 }  
  59.                 return RedirectToAction("Index");  
  60.             }  
  61.             catch (Exception ex)  
  62.             {  
  63.                 var error = ex;  
  64.                 throw;  
  65.             }  
  66.         }  
  67.     }  
  68. }   

Step 8

Run the project and go for the Users View.


Step 9

Choose the file from computer and click on "Get User List" button.


Step 10

Below is the user list table extracted from userlist.xml file.