Using Entity Framework in an ASP.NET MVC5 Application
November 30, 2013 1 Comment
In my previous two posts, I built a C# console application using Entity Framework (EF) in Microsoft Visual Studio 2013, and investigated how to perform CRUD operations on EF.
Building an ASP.NET MVC5 application using EF can become a straightforward job in Visual Studio 2013. It is very similar to building a J2EE MVC application by using JPA in Netbeans 7. The steps can be summarized as three steps: 1) create a ASP.NET MVC project; 2) add M: reversed engineer an EF model(M) from database; 3) Add C with V: scaffolding MVC 5 Controller (C) with views (V) using EF.
1. Create a ASP.NET MVC Project
In Microsoft Visual Studio 2013, create a new project (Ctrl-Shift-N) called EmployeeMVC using template (Visual C#->ASP.NET Web Application) and also select a template ‘MVC‘ and add folders and core references for ‘MVC’.
What will happene?
Visual Studio will create a few folders (App_Data, App_Start, Content, Controllers, fonts, Models, Scripts, Views) and files (Global.asax, packages.config, Web.config, Project_Readme.html, Startup.cs), also download a list of js scripts in Scripts folder, create AccountViewModels.cs and IdentityModels.cs in Models folder, AccountController.cs and HomeController.cs in Controllers folder, a list of *.shtml in various view folders, site style sheets in Contents folder and a few config.cs in App_Start.
Press F5 to build and run the empty application now.
2. Add ADO.NET Entity Data Model
Following the steps to reversed engineer EF 5 model from a table in the database into ASP.NET MVC (for reversed engineer an EF 6 model class, please use Entity Framework Power Tools):
This will add EmployeeModel.edmx (EF 5) as a folder under Models, and also add relevant references.
Build the solution.
3. Generate Controller and Views
To generate controller and views:
This will create EmployeeController.cs in Controllers:
using System;
using System.Collections.Generic;
using System.Data;
using System.Data.Entity;
using System.Linq;
using System.Net;
using System.Web;
using System.Web.Mvc;
using EmployeeMVC.Models;
namespace EmployeeMVC.Controllers
{
public class EmployeeController : Controller
{
private testEntities db = new testEntities();
// GET: /Employee/
public ActionResult Index()
{
var employees = db.Employees.Include(e => e.Employee1);
return View(employees.ToList());
}
// GET: /Employee/Details/5
public ActionResult Details(int? id)
{
if (id == null)
{
return new HttpStatusCodeResult(HttpStatusCode.BadRequest);
}
Employee employee = db.Employees.Find(id);
if (employee == null)
{
return HttpNotFound();
}
return View(employee);
}
// GET: /Employee/Create
public ActionResult Create()
{
ViewBag.mgrid = new SelectList(db.Employees, "empid", "lastname");
return View();
}
// POST: /Employee/Create
// To protect from overposting attacks, please enable the specific properties you want to bind to, for
// more details see http://go.microsoft.com/fwlink/?LinkId=317598.
[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult Create([Bind(Include="empid,lastname,firstname,title,titleofcourtesy,birthdate,hiredate,address,city,region,postalcode,country,phone,mgrid")] Employee employee)
{
if (ModelState.IsValid)
{
db.Employees.Add(employee);
db.SaveChanges();
return RedirectToAction("Index");
}
ViewBag.mgrid = new SelectList(db.Employees, "empid", "lastname", employee.mgrid);
return View(employee);
}
// GET: /Employee/Edit/5
public ActionResult Edit(int? id)
{
if (id == null)
{
return new HttpStatusCodeResult(HttpStatusCode.BadRequest);
}
Employee employee = db.Employees.Find(id);
if (employee == null)
{
return HttpNotFound();
}
ViewBag.mgrid = new SelectList(db.Employees, "empid", "lastname", employee.mgrid);
return View(employee);
}
// POST: /Employee/Edit/5
// To protect from overposting attacks, please enable the specific properties you want to bind to, for
// more details see http://go.microsoft.com/fwlink/?LinkId=317598.
[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult Edit([Bind(Include="empid,lastname,firstname,title,titleofcourtesy,birthdate,hiredate,address,city,region,postalcode,country,phone,mgrid")] Employee employee)
{
if (ModelState.IsValid)
{
db.Entry(employee).State = EntityState.Modified;
db.SaveChanges();
return RedirectToAction("Index");
}
ViewBag.mgrid = new SelectList(db.Employees, "empid", "lastname", employee.mgrid);
return View(employee);
}
// GET: /Employee/Delete/5
public ActionResult Delete(int? id)
{
if (id == null)
{
return new HttpStatusCodeResult(HttpStatusCode.BadRequest);
}
Employee employee = db.Employees.Find(id);
if (employee == null)
{
return HttpNotFound();
}
return View(employee);
}
// POST: /Employee/Delete/5
[HttpPost, ActionName("Delete")]
[ValidateAntiForgeryToken]
public ActionResult DeleteConfirmed(int id)
{
Employee employee = db.Employees.Find(id);
db.Employees.Remove(employee);
db.SaveChanges();
return RedirectToAction("Index");
}
protected override void Dispose(bool disposing)
{
if (disposing)
{
db.Dispose();
}
base.Dispose(disposing);
}
}
}
It will also create a folder ‘Employee‘ in Views with a list of cshtml (Create, Delete, Details, Edit, Index)
Build and run by pressing F5, and go to the similar link in the browser like:
http://localhost:49481/employee
I removed some of unwanted items in index.cshtml. My index page looked like:
Summary
Using Entity Framework, Visual Studio 2013 can easily generate a model from database, and scaffold a controller and generate all the views based on default templates and standard CRUD operations on EF.
The advantage of this process is that the model, controller and view can be easily re-generated by repeating the above step 2 and 3 if the table structure in the underlying physical table is changed.
The disadvantage is also obvious. Whatever customization made after the generation on (M. V. C) will have to be repeated after re-generation.
