Click here to Skip to main content
15,867,568 members
Articles / Web Development / HTML
Alternative
Article

EntityUI Automatic UI Generator

Rate me:
Please Sign up or sign in to vote.
4.69/5 (16 votes)
19 Mar 2014CPOL8 min read 40.5K   531   36   8
This is an alternative for "EntityUI Automatic UI Generator using CodeFirst Approach"

Introduction

EntityUI is basically an idea to be able to rapidly generate your application by automatically creating the User Interface and the Database repository in ASP.NET applications using Code First approach. As developers, you would write your Domain and View Models, and adjust those classes to create your application, without writing much code.

Working Demo

You can visit http://www.razisyed.com/entityui for a working demo and more details.

The source code is also available on git: https://github.com/razisyed/EntityUi

Background

I originally started on EntityUi with ASP.NET a few years ago, and wrote some simple code that used reflection to render the UI. That's the original article I had posted. However, since I started on EntityUI, a lot has changed. MVC and Knockout have been mainstream now for a while, and they are both excellent tools to implement the MVVM pattern.

So EntityUi is now a project that uses MVC and Knockout to automatically generate the UI from the model. It's basically aiming to be a rapid application development tool, to not just quickly generate common crud pages, but also attempt to handle much more advanced scenarios.

Pre-Requisite

This is for a Microsoft MVC project. You should be familiar with MVVM pattern, Domain Model, View Model, and need knockout knowledge to understand and use some of the advanced features. You also need to know Repository pattern and Microsoft Entity Framework Code First to fully understand how this all works. We will use nuget to download the EntityUi package, and bootstrap for a beautiful layout.

Using the Code

I'll demonstrate the usage with a brand new project to keep things simple. Start a blank MVC project, and then add 2 Class Library Projects to the Solution, one for Domain Model, and the other for Repository.

Then add EntityUi from nuget to the Domain Project and Repository Project in the solution. To install EntityUi, run the following command in the Package Manager Console:

PM> Install-Package EntityUi

In the blank MVC project, install the EntityUi.Web package:

PM> Install-Package EntityUi.Web

The EntityUi package has the following core concepts:

  • DomainModelBase - Base class that your Domain Model (really Data Model) objects need to inherit from.
  • ViewModelBase - Base class that your View Model objects need to inherit from.
  • ControllerBase - Base class for your Controller, it provides Crud methods built in.
  • RepositoryBase - Base class for your Repository, it provides Crud methods built in using Entity Framework.

The EntityUi.Web package adds several layouts and templates that are needed to use EntityUi.

Next, we need to write the Domain Model and Repository Methods.

In this example, we'll work with the following Sample "Department" Class. I picked it up from MSDN Entity Framework Code First Fluent API example.

C#
public class Department : DomainModelBase
{
    public Department()
    {
        Courses = new HashSet<Course>();
    }

    public string Name { get; set; }
    public decimal Budget { get; set; }
    public DateTime StartDate { get; set; }
    public int? Administrator { get; set; }

    // Navigation property
    public ICollection<Course> Courses { get; set; }
}

As you can see, it is inherited from the DomainModelBase class.

Next, let's setup the Repository. Add your Context class, inherited from Entity Framework's DbContext class, and add a simple Repository class for Department, "DepartmentRepository":

C#
 public class DataContext : DbContext
    {
        public DbSet<Department> Departments { get; set; } 
 
        protected override void OnModelCreating(DbModelBuilder modelBuilder)
        {
            Database.SetInitializer(new CreateDatabaseIfNotExists<DataContext>());
        } 
    }  

public class DepartmentRepository : RepositoryBase<Department, DataContext>
    {
        protected override DataContext GetContext()
        {
            return new DataContext();
        }
    } 

The DataContext class is a very simple Context class with just one property for Departments for now.

The Repository is also a very simple implementation. This class doesn't have any methods other than GetContext, and it is inherited from the DomainModelBase class. As you can see, when inheriting from RepositoryBase, you have to provide the Entity name and the DataContext to the Base so it knows what it's working with.

Now let's move on to the View, and add the Model, View and Controller classes. I always promote a separate Domain and View Model classes, even though for simple cases they are mostly the same. We will use AutoMapper to easily convert between Domain and View models.

So here is the Controller Class:

C#
public class DepartmentController : ControllerBase<Department, DepartmentView, DataContext>
{
    public DepartmentController()
    {
        Repository=new DepartmentRepository();
    }
}

The controller is inherited from ControllerBase, similar to the other classes. It needs to know the Domain Model, View Model and the DataContext.

You need to map the properties between the Domain Model and the View Model to convert them to one another. EntityUi automatically creates a default Mapper for you where the values are copied if the property names are the same.

If you want, you can also setup a custom mapping between the Domain and View Model objects in global.aspx for AutoMapper:

C#
  Mapper.CreateMap<Department, DepartmentView>();
  Mapper.CreateMap<DepartmentView, Department>()
.ForMember(d => d.Id, o => o.Condition(s => s.Id > 0))
        .ForMember(d => d.Courses, o => o.Ignore());;

The above is a simple Domain View to Model View mapping using AutoMapper. Behind the scenes, it basically uses reflection to copy the property values from one object to another. Basically with this tool, we are telling EntityUi how to convert between the Domain and Model view objects.

Now you should be able to build and run the application, and when you navigate to "department", it should render the department screen for you, which includes complete crud functionality, including rendering pages and saving it to the database.

Image 1

So this is the most basic and simplistic use of EntityUi. Let's try something a little more interesting now.

Using Drop Down

Here is how to use a drop down list by just modifying your view Model. Let's start by adding Course concept as follows:

Here is the Domain Model:

C#
public class Course : DomainModelBase
  {
      public Course()
      {
          Instructors = new HashSet<Instructor>();
      }

      public string Title { get; set; }
      public int Credits { get; set; }

      // Foreign key
      public int DepartmentID { get; set; }

      // Navigation properties
      public Department Department { get; set; }
      public ICollection<Instructor> Instructors { get; set; }

  }

As you can see, it has Department as a Navigation Property, which indicates that in the UI, we'd like to see a drop down that lists all the Departments, and the user should be able to select the department.

Here is the Repository and the Controller:

C#
public class CourseRepository : RepositoryBase<Course, DataContext>
{
    protected override DataContext GetContext()
    {
        return new DataContext();
    }
}

They are both just bare bones, by simply inheriting from EntityUi's RepositoryBase and Controller Base.

Now, here is the Model View:

C#
public class CourseView : ViewModelBase
   {
       public string Title { get; set; }
       public int Credits { get; set; }

       public DropDown Departments { get; set; }

       public CourseView()
       {
           Departments = new DropDown
           {
               Items = (new DepartmentRepository())
                         .List()
                         .ToList()
                         .ConvertAll(x => new SelectListItem
                         {
                             Text = x.Name,
                             Value = x.Id.ToString()
                         })
           };
       }
   }

This is a little different. To render a dropdown list for Department, we defined the Departments Property as EntityUi's helper type "DropDown". Also, in the constructor, we load it up with a list of Departments from the database. I hope the code is self explanatory, and doesn't need too much explanation. All we are doing is calling the "List()" method (provided by EntityUi) on the DepartmentRepository to get all the Departments, and using "ConvertAll()" method (provided by Linq) to convert it to SelectListItem.

The next interesting part will be where we map the Model View and the Domain View. Here is the code that needs to be added to Global.asax:

C#
Mapper.CreateMap<CourseView, Course>()
      .ForMember(d => d.Id, o => o.Condition(s => s.Id > 0))
      .ForMember(d => d.DepartmentID, o => o.MapFrom(s => s.Departments.SelectedId))
      .ForMember(d => d.Department, o => o.Ignore());

Mapper.CreateMap<Course, CourseView>()
      .ForMember(d => d.Departments, o => o.Ignore())
      .AfterMap((s, d) => d.Departments.SelectedId = s.DepartmentID.ToString());

This is actually a fairly advanced use of Auto Mapper. You might want to look at AutoMapper's documentation.

In the first Mapping statement, we are mapping the CourseView (View Model) to Course (Domain Model). The interesting part here is that we are mapping the Domain's Department ID to the SelectedId property in the View's Departments Dropdown. In the second mapping, where we go from Domain to View Model, it's the exact reverse.

This is pretty much all the coding that's needed. If you run now and navigate to "Courses", you will be able to add/edit/delete with Department showing as a drop down:

Image 2

Adding User Interface Interactions

So far, we have looked at some basic crud functionality. The idea is to be able to more than just crud by just working with Model View. So let's say we have a business requirement that the Department should ask for budget only if Budget is allocated, otherwise, the budget input should not be shown.

The best approach for this would be JavaScript in the view. One of the easiest ways to handle these scenarios is through knockout. EntityUi allows you to add knockout binding to any property by using the DataBind data annotation.

So we can accomplish this requirement by simply modifying the Department View as follows:

C#
 public class DepartmentView : ViewModelBase
 {
    public string Name { get; set; }
    public bool HasBuget { get; set; }
    [DataBind("visible:HasBuget()")]
    public decimal Budget { get; set; }
    public DateTime StartDate { get; set; }
 } 

So what I did here is that first I added a boolean property HasBudget. This would be rendered as a checkbox.

Next, I added the DataBind attribute and provided my knockout binding that I would have generally added to the view. EntityUi automatically renders it. You need to be familiar with knockout bindings to fully utilize this feature, and if not, please visit www.knockoutjs.com for documentation. All we are doing here is setting the visibility to the HasBudget property. Behind the scene, EntityUi uses knockoutmvc to setup each Model View as knockout view model, making each property observable.

What this code change will do is that when you view the page in edit mode, it will show the Budget input field and label when you check the "HasBudget" checkbox, and it will hide them if you uncheck them.

Summary

So hopefully with the details provided above, you can see how EnitityUi can be used for Rapid Application Development using tools to handle all aspects for code writing, from working with Data all the way to the User Interface.

As developer, the main task is to write the Domain Model and View Model. Then, most of the other things will happen by adding Attributes and/or Fluent API configuration and following conventions, and we will have a fully functional application.

EntityUi is also very flexible, and provides full control to the developer. Developers can overload or add any method to any of their class, whether it's the Repository, Controller or View. You can also very easily write complete pages or classes on your own within the same application without utilizing EntityUi, or add to the view and controller that utilizes EntityUi's framework.

References

I wrote EntityUi using many different open source libraries. Here are some of the main ones:

License

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


Written By
Software Developer (Senior)
United States United States
My area of expertise is developing management database systems for business so that they can efficiently store and lookup existing customer's information and related data, and be able to generate various reports. My goal is to always deliver innovative design and a user friendly interface.

Comments and Discussions

 
QuestionThe Navigation Menu is not getting rendered. any idea Pin
Member 1046887428-Dec-23 5:52
Member 1046887428-Dec-23 5:52 
QuestionSource code Pin
Francois Botha20-May-16 2:16
Francois Botha20-May-16 2:16 
AnswerRe: Source code Pin
Razi Syed3-Nov-17 8:06
Razi Syed3-Nov-17 8:06 
GeneralMy vote of 5 Pin
Abhishek Pant5-Apr-15 11:01
professionalAbhishek Pant5-Apr-15 11:01 
QuestionDataAnnotations Pin
jan grygerek9-Apr-14 1:41
jan grygerek9-Apr-14 1:41 
AnswerRe: DataAnnotations Pin
Razi Syed9-Apr-14 8:48
Razi Syed9-Apr-14 8:48 
QuestionAuto UI Generation Pin
gillindsay25-Mar-14 4:58
professionalgillindsay25-Mar-14 4:58 
AnswerRe: Auto UI Generation Pin
Razi Syed25-Mar-14 8:37
Razi Syed25-Mar-14 8:37 

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Praise Praise    Rant Rant    Admin Admin   

Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.