Wednesday, August 6, 2014

Building Blocks: XML Data Repository for Asp.Net MVC with all CRUD Operations

The following code is the complete C# code to create an XML Data Repository for Asp.Net MVC with all CRUD Operations  , connected to a single XML file , and exposing all CRUD operations, everything using XDocument. The base class is "Note", and the Repository is "INotesRepository". A little XML bootstrap file is at the end of this post.
This code can also be downloaded from the following GitHub repository:
https://github.com/CarmelSoftware/MVCDataRepositoryXML
The whole application can show as follows:
Building Blocks: XML Data Repository for Asp.Net MVC with all CRUD Operations


Just COPY-PASTE it inside your Models folder and initialize it inside some Controller:


using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Xml.Linq;

namespace IoCDependencyInjection.Models
{

public class Note
{
public int ID { get; set; }
public string To { get; set; }
public string From { get; set; }
public string Heading { get; set; }
public string Body { get; set; }
}


public interface INotesRepository
{
IEnumerable
<Note> GetAll();
Note Get(int id);
Note Add(Note item);
bool Update(Note item);
bool Delete(int id);
}


public class NotesRepository : INotesRepository
{
private List
<Note> notes = new List<Note>();
private int iNumberOfEntries = 1;
private XDocument doc;

public NotesRepository()
{
doc = XDocument.Load(HttpContext.Current.Server.MapPath("~/App_Data/data.xml"));
foreach (var node in doc.Descendants("note"))
{
notes.Add(new Note
{
ID = Int32.Parse(node.Descendants("id").FirstOrDefault().Value),
To = node.Descendants("to").FirstOrDefault().Value,
From = node.Descendants("from").FirstOrDefault().Value,
Heading = node.Descendants("heading").FirstOrDefault().Value,
Body = node.Descendants("body").FirstOrDefault().Value
});
}

iNumberOfEntries = notes.Count;
}

public IEnumerable
<Note> GetAll()
{
return notes;
}
public Note Get(int id)
{
return notes.Find(p => p.ID == id);
}
public Note Add(Note item)
{
if (item == null)
{
throw new ArgumentNullException("item");
}

item.ID = iNumberOfEntries++;

XElement newNode = new XElement("note");
XElement id = new XElement("id"); id.Value = item.ID.ToString() ;
XElement to = new XElement("to");to.Value = item.To;
XElement from = new XElement("from"); from.Value = item.From;
XElement heading = new XElement("heading"); heading.Value = item.Heading;
XElement body = new XElement("body"); body.Value = item.Body;
newNode.Add(id, to, from, heading, body);
doc.Root.Add(newNode);
SaveXML();
return item;
}
public bool Update(Note item)
{
if (item == null)
{
throw new ArgumentNullException("item");
}
XElement note = doc.Descendants("note").Where(n => Int32.Parse( n.Descendants("id").FirstOrDefault().Value ) == item.ID ).FirstOrDefault();
note.Descendants("to").FirstOrDefault().Value = item.To;
note.Descendants("from").FirstOrDefault().Value = item.From;
note.Descendants("heading").FirstOrDefault().Value = item.Heading;
note.Descendants("body").FirstOrDefault().Value = item.Body;
SaveXML();
return true;
}
public bool Delete(int id)
{
doc.Root.Descendants("note").Where(n => Int32.Parse(n.Descendants("id").First().Value ) == id).Remove() ;
SaveXML();
return true;
}

private void SaveXML()
{
doc.Save(HttpContext.Current.Server.MapPath("~/App_Data/data.xml"));
}
}
}

This is the XML initial file:



<?xml version="1.0" encoding="utf-8"?>
<notes>
  <note>
    <id>0</id>
    <to>Fry</to>
    <from>Leela</from>
    <heading>Reminder</heading>
    <body>Don't forget me this weekend!!!</body>
  </note>
  <note>
    <id>1</id>
    <to>Leela</to>
    <from>Fry</from>
    <heading>Finally!!!</heading>
    <body>Leela, have you asked permission from the Professor?</body>
  </note>
  <note>
    <id>2</id>
    <to>Fry</to>
    <from>Leela</from>
    <heading>Rejection</heading>
    <body>You know what? In second thoughts, i'm going out with Lars this weekend. Sorry...</body>
  </note>

</notes>


Some important points are the XDocument utilization:
Building Blocks: XML Data Repository for Asp.Net MVC with all CRUD Operations 1
 We are using essentially the Descendants("") & the Load() methods, to read the XML document into memory and inside a List<>.
The Get method uses Find(p => p):

XML Data Repository for Asp.Net MVC with all CRUD Operations

To INSERT a new node, we CREATE an XElement with its inner XElement CHILDS , and then add it to the ROOT of the XDocument:

Data Repository for Asp.Net MVC


If you liked the look of this site, learn how to create it using open source CSS templates in this tutorial.

A Generic Data Repository is built step by step in the following Tutorial: http://themvcclub.blogspot.co.il/2014/06/generic-data-Repository-ASP.NET-MVC.html

A GitHub repository containing a Data Repository With Caching can be found here:
https://github.com/CarmelSoftware/Data-Repository-with-Data-Caching-in-ASP.NET-MVC-4

That's all!!  
Happy programming.....
        By Carmel Schvartzman
כתב: כרמל שוורצמן