InitializeSimpleMembership Attribute and SimpleMembership Exceptions
The InitializeSimpleMembership Attribute ensures that before any membership (login/register) related functionality is run, that the membership database has been created. If the database is not yet created, the code will automatically create one. If the simple membership initialization fails, the Web Application can continue to run requests that don’t require membership.
Simple membership initialization failure can occur for the following reasons.
- The most common reason is the connection string to SQL Server is not valid. For example, you might not have SQL Server available. This is a frequent cause of failure in Azure. The ASP.NET MVC 4 templates by default use SqlExpress when created with Visual Studio 2010 and LocalDB when using Visual Studio 2012. SqlExpress is not installed on Azure and LocalDB does not run on Azure.
- Multiple DBContext objects on the same database.
The following code shows the InitializeSimpleMembership Attribute code that is added to a new ASP.NET MVC application. The code is found in the Filters folder:
using System;
using System.Data.Entity;
using System.Data.Entity.Infrastructure;
using System.Threading;
using System.Web.Mvc;
using WebMatrix.WebData;
using MvcV4.Models;
namespace MvcV4.Filters
{
[AttributeUsage(AttributeTargets.Class | AttributeTargets.Method, AllowMultiple = false, Inherited = true)]
public sealed class InitializeSimpleMembershipAttribute : ActionFilterAttribute
{
private static SimpleMembershipInitializer _initializer;
private static object _initializerLock = new object();
private static bool _isInitialized;
public override void OnActionExecuting(ActionExecutingContext filterContext)
{
// Ensure ASP.NET Simple Membership is initialized only once per app start
LazyInitializer.EnsureInitialized(ref _initializer, ref _isInitialized, ref _initializerLock);
}
private class SimpleMembershipInitializer
{
public SimpleMembershipInitializer()
{
Database.SetInitializer<UsersContext>(null);
try
{
using (var context = new UsersContext())
{
if (!context.Database.Exists())
{
// Create the SimpleMembership database without Entity Framework migration schema
((IObjectContextAdapter)context).ObjectContext.CreateDatabase();
}
}
WebSecurity.InitializeDatabaseConnection("DefaultConnection", "UserProfile", "UserId", "UserName", autoCreateTables: true);
}
catch (Exception ex)
{
throw new InvalidOperationException("The ASP.NET Simple Membership database could not be initialized. For more information, please see https://go.microsoft.com/fwlink/?LinkId=256588", ex);
}
}
}
}
}
Comments
Anonymous
August 21, 2012
Have you changed something with the connection strings? I can't see it documented anywhere, but with SQL Server the username parameter name seems to have been changed from "User Name" to "User".Anonymous
August 26, 2012
I have the exception when using Azure (it works fine on my computer connecting to SQL Azure). What do we need to do when dealing with Azure?Anonymous
September 13, 2012
So, what should we do? I am using SQL Server 2008 and I have connection string pointing to my application. I am not sure I'd like to use the default provider, I already have Operators (Users) table in my database and I want to use that table instead. What / where should I change? Thanks in advanceAnonymous
September 17, 2012
Thanks for your article But I have search all over the internet to resolve the situation below : How to Handle the initialization when Simplemebership and context share the same database and the same context ? I have a Database and I want to store the simplemembership information and my domain model tables too. But how to Initialize them at the same time and seeding them ? This seems to be impossible ThanksAnonymous
September 26, 2012
Article post is as useless as they come.Anonymous
September 27, 2012
The comment has been removedAnonymous
October 10, 2012
Here is a great primer for learing about SimpleMembership: weblogs.asp.net/.../simplemembership-membership-providers-universal-providers-and-the-new-asp-net-4-5-web-forms-and-asp-net-mvc-4-templates.aspxAnonymous
October 14, 2012
@Mirza you need to have the correct values in the defaultconnection connection string. I copied mine into thereAnonymous
October 26, 2012
Hi, I just questioning why we need this filter here stackoverflow.com/.../why-initializesimplemembershipattribute-in-mvc-4-app Initially I think this filter only useful for controllers/actions that has Membership aware and provide something like lazy initialization but after sometimes, I quickly used this filter everywhere until I realize I don't need this filter but WebSecurity.InitializeDatabaseConnection required to be called in Application_Start. Lazy initialization is not really necessary because not only this way will make non-membership controllers/views loads faster but initialize in app start once also do the same. Sorry to say that, based on my point of view, using this filter is impractical because anyone definitely use Membership API anywhere like calling User.IsInRole in _Layout.cshtml to show menu for admin. WebSecurity.InitializeDatabaseConnection required to be called before using any of the Membership or Role API. The existence of LazyInitializer.EnsureInitialized in the filter makes move this code into Application_Start. I hope by moving the filter to Application_Start save other developers time. There is no reason not to initialize membership database in Application_Start unless you are designing non-membership application. Initialization for SimpleMembership is required even though you declare the SimpleMembershipProvider in the web.config to replace the default membership provider defined in machine.config. It is not worth by having this filter but later introduce a few problems It is too late to initialize database (and/or membership related objects) when the first request has been called.Anonymous
November 24, 2012
Can someone please post a correct connection string example for using simple membership and sqlazure.Anonymous
January 07, 2013
Why would multiple DbContext on one database cause errors?Anonymous
January 20, 2013
The comment has been removedAnonymous
June 30, 2013
You need to ACTUALLY explain scenario 2 where multiple DB Contexts cause an error. Are you saying to change the attrbiute to use the same context as the rest of your application? I can't get that working.Anonymous
July 13, 2013
The comment has been removedAnonymous
July 24, 2013
It's a little frustrating that this is the target of the error link go.microsoft.com/fwlink, but you don't actually address 'half' the causes of errors - WHY would having more than one DbContext cause problems, and HOW should we resolve those problems? In fact you don''t seem really to address the case where connecting to azure either.Anonymous
August 28, 2013
I struggled with the same issue, and only just realized that if you look at the constructor of UsersContext it is initialized with a hardcoded connectionstring name of "DefaultConnection". If you have this connection string name in Web.Config (or Machine.Config) it will work. But if you don't have that name in Web.Config it may very well take the connection details from Machine.Config which will probably not point to the right server in a hosted environment.Anonymous
October 08, 2013
If you're using SQL Server, be sure to have your connection string include providerName="System.Data.SqlClient" (That was a long hunt)Anonymous
November 05, 2013
Point 2 is referring to the fact you cannot have two objects in the database with the same name. If you don't modify the SimpleMembership it will try and create a table named UserProfile. If you have the universal providers set up to use the same database it has a foreign key constraint on the Profiles table with the same name UserProfile. Renaming the foreign key constraint should stop the error. If you still get an error then try setting the SimpleMembership to use an empty database. You can then get scripts for everything it creates and run them on your main database to find where the conflict occurs.Anonymous
November 10, 2013
The comment has been removedAnonymous
February 12, 2014
What's wrong with Microsoft ASP Team? Poor docu.Anonymous
March 24, 2014
I have tried in SQLServer 2008, mentioned the connection string in web.config file Solution: <add name="DefaultConnection" connectionString="uid=****;pwd=*****;server=(local); database=aspnet-SampleMVC4Layout-20140325111706" providerName="System.Data.SqlClient" /> If Membership db does not exists, system automatically creates the db. Issue was identified in FiltersInitializeSimpleMembershipAttribute.cs WebSecurity.InitializeDatabaseConnection("DefaultConnection", "UserProfile", "UserId", "UserName", autoCreateTables: true);Anonymous
June 03, 2014
what is the actual meaning of UsersContext mvc.netAnonymous
July 07, 2014
Add a connection string in web.config named "DefaultConnection" pointing to the correct datasource, that did the trick for me :o) <connectionStrings> <add name="MvcAuction.Models.AuctionsDataContext" connectionString="Data Source=(LocalDb)v11.0;Integrated Security=SSPI;AttachDBFilename=|DataDirectory|MvcAuction.Models.AuctionDataContext.mdf" providerName="System.Data.SqlClient" /> <add name="DefaultConnection" connectionString="Data Source=(LocalDb)v11.0;Integrated Security=SSPI;AttachDBFilename=|DataDirectory|MvcAuction.Models.AuctionDataContext.mdf" providerName="System.Data.SqlClient" /> </connectionStrings>Anonymous
September 16, 2014
here is the working connection string: <add name="DefaultConnection" connectionString="server=WKMJ84N9BSQLEXPRESS;Database=aspnet-MvcApplication1-20140916105626;Integrated Security=SSPI;" providerName="System.Data.SqlClient" /> replace WKMJ84N9B with you machine idAnonymous
September 26, 2014
How can I change this class to connect with Azure? I tried with: "data source=:azuredbname.database.windows.net;initial catalog=mydb;persist security info=True;user id=username;password=pasword;MultipleActiveResultSets=True;App=EntityFramework;" The same in the web.config, but it still not work.Anonymous
November 03, 2014
The comment has been removedAnonymous
December 16, 2014
How can i use EF5 codefirst model to create oracle database? Thank you.Anonymous
March 30, 2015
thanks suresh ganapa for provide right information.Anonymous
April 14, 2015
Ahmed Salah your answer works for me i just wrote my server name and it works, thak you so much.Anonymous
April 19, 2015
Needed the correct connection string. Needed to comment out a few things in the Filters folder > InitializeSimpleMembershipAttribute.vb I have a hosted account where I cannot make databases. It has to use the only one there that I have access. So I had to comment out the part that was trying to make a new database. This is what I ended up with in InitializeSimpleMembershipAttribute.vb Private Class SimpleMembershipInitializer Public Sub New() 'Database.SetInitializer(Of UsersContext)(Nothing) Try 'Using context As New UsersContext() ' If Not context.Database.Exists() Then ' ' Create the SimpleMembership database without Entity Framework migration schema ' CType(context, IObjectContextAdapter).ObjectContext.CreateDatabase() ' End If 'End Using WebSecurity.InitializeDatabaseConnection("DefaultConnection", "UserProfile", "UserId", "UserName", autoCreateTables:=True) Catch ex As Exception Throw New InvalidOperationException("The ASP.NET Simple Membership database could not be initialized. For more information, please see go.microsoft.com/fwlink, ex) End Try End Sub End Class Notice that most of it was commented out except for the initilzeDatabaseConnection part.Anonymous
October 12, 2015
when i am clciking on login or register then error--exception has been thrown by target of invocation