Dan's Green Shoes

Got my green shoes on!

Using your “User” table with MVC4 Internet Template

1 Comment

The MVC4 Internet template assumes that it will be adding a user table called “UserProfile” to your database.  What I think a high percentage of developers would want is to use their domain model’s “user” entity and have SimpleMembership just manage the passwords.  In this blog post I will demonstrate how I did this and welcome alternative suggestions.
I recommend you first understand the authentication process provided by the MVC 4 Internet template.  There are 2 fantastic posts you should read first.

  1. MVC 4 Authentication
  2. SimpleMembership, Membership Providers, Universal Providers and the new ASP.NET 4.5 Web Forms and ASP.NET MVC 4 templates

In addition, please check out Scott Allen’s excellent Pluralsight course called “Building Applications with ASP.NET MVC 4”.

MVC 4 Internet Template with pre-existing Domain Model

Create a new ASP.NET MVC 4 Internet Application and name it “SimpleMemberExample”

image

Custom Domain Model/Database

The first thing I want to do is create the custom domain model/database.  In the “Model” directory, lets add a class that represents our custom “User” table.  Lets call this custom user entity “Administrator” as seen here:

namespace SimpleMembershipExample.Models
{
    public class Administrator
    {
        public Administrator(){}
        #region Fields and Properties
        public int Id { get; set; }
        public string Name { get; set; }
        public string Email { get; set; }
        #endregion
    }
}

(I was unable to figure out how my user table’s unique identifier could use a Guid.  I think the unique identifier of your custom user entity/table must be an int to use SimpleMembership.  anyone know?)

Lets add a custom DbContext as shown here to the root of the project.

using System.Data.Entity;
using SimpleMembershipExample.Models;

namespace SimpleMembershipExample
{
    public class SomeAppDbContext: DbContext
    {
        public SomeAppDbContext(): base(nameOrConnectionString: "SomeAppName"){}
        public DbSet<Administrator> Administrators { get; set; }
    }
}

The DbContext only contains a single table called Administrators just to keep this super duper easy.  Yours would contain lots more. Notice in the custom constructor, I am telling the DbContext to use a specific connection string.  Lets add that connection string to the Web.Config.

image

This connection string could be anything you want it to be.

Just for demo purposes, I am naming the database “SomeAppName”.  As a final step, in “Global.asax.cs”, put the following code:

public class MvcApplication : System.Web.HttpApplication
{
    protected void Application_Start()
    {
        SomeAppDbContext dbcontext = new SomeAppDbContext();
        dbcontext.Administrators.All(i => i.Name != "Dan");

Running the application, the magical EF Code First will create the following database.  We have a custom database with a custom user table called “Administrators”.

image

Customizing MVC 4 Internet Template

Remove InitializeSimpleMembershipAttribute

The Internet template contains an Action filter called “InitializeSimpleMembershipAttribute”.  I deleted that class and removed any references to it.

Replace UserProfile with your Custom User Entity

The Internet template assumes that it will be adding a user table called “UserProfile” to your database.  What I think a high percentage of developers would want is to use their domain model’s “user” entity and have SimpleMembership just manage the passwords.  Let me demonstrate how to do this.

In the “Model” folder, in the “AccountModel.cs” file, delete the “UserProfile” class.  We want to use our “Administrator” entity instead.  Wherever UserProfile is referenced elsewhere, replace with Administrator.   The original UserProfile had properties called “UserName” and “UserId”.  Administrator has properties “Name” and “Id”.  Make sure to sync those properties up.

I want to have only 1 DbContext and I want to use my DbContext.  In the “Model” folder, in the “AccountModel.cs” file, delete the “UsersContext” class.  Wherever UsersContext is referenced elsewhere, replace with SomeAppDbContext.

Call WebSecurity.InitializeDatabaseConnection

As a final step, in “Global.asax.cs”, put the following code:

public class MvcApplication : System.Web.HttpApplication
{
    protected void Application_Start()
    {
        SomeAppDbContext dbcontext = new SomeAppDbContext();
        dbcontext.Administrators.All(i => i.Name != "Dan");
        WebSecurity.InitializeDatabaseConnection("SomeAppName", 
            "Administrators", "Id", "Name", autoCreateTables: true);

WebSecurity.InitializeDatabaseConnection takes the web.config connection string name, the name of your custom user table (“Administrators”), the unique identifier field name of your user table (“Id”) and the user name field.  Running the InitializeDatabaseConnection method does several things:

  1. Initializes the static Roles and WebSecurity classes.
  2. Adds the following tables to your database: webpages_Membership, webpages_OAuthMembership, webpages_Roles, webpages_UsersInRoles, UserProfile.

Running the Internet Application

When you run the code with those changes, the following database is created:

image

The home screen looks like this:

image

Click on the Register link in the upper right.

image

Fill out the form and click the “Register” button.  The MVC 4 Internet template application will navigate you back to the home page.

image

Notice it knows the name you registered with.  If you check for cookies, you will see the typical ASPXAUTH as shown below.

image

If you click the “Log off” link and check cookies, the ASPXAUTH cookie disappears.  The ASPXAUTH cookie is the key to the authentication.

When you look at the database you will see the following:

image

Notice with the code changes, the MVC Internet template knew to save to the custom user table “Administrators”.  The password was saved to the webpages_Membership table with a foreign key relationship to the Administrators table.

Please download the code here.

Advertisements

Author: Dan Hickman

Chief Technology Officer ProModel Corporation

One thought on “Using your “User” table with MVC4 Internet Template

  1. It didn’t work for me. To table was created by EF. Also i downloaded the code, still the database I add with the name “SomeAppName” gets no new tables and no data were added when i register a user.

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s