In a VS 2013 RTM, MVC 5 project with EF 6, I tried to scaffold a controller based on the ApplicationUser (default with individual accounts authentication). Both ApplicationUser
and IdentityUser
are mapped to a Users table.
The wizard opens the context file for editing and tries to add a new db set for ApplicationUser (ApplicationUsers) and then fails with this error:
Unable to retrieve metadata for ApplicationUser. Multiple object sets per type are not supported. The object sets ApplicationUsers and Users can both contain instances of type ApplicationUser
The solution does not have any reference to, or instance of ApplicationUsers
.
Is this a known issue? Can the scaffolding be run using command line with options (from PMC)? Note: scaffolding also adds an extra db set to the context class if I specify a model that references ApplicationUser (the app works if I remove it and fix references in the generate controller).
Wow. I'm really surprise that no one actually got to the root of this, and instead, are just recommending workarounds.
IdentityDbContext
already contains a property:
`public virtual IDbSet<TUser> Users { get; set; }
When you subclass IdentityDbContext
to create your own application-specific context, you must specify what class satisfies the TUser
generic. The default is:
public ApplicationDbContext : IdentityDbContext<ApplicationUser>
Which then means that you functionally have a property already via inheritance in the form of:
public IDbSet<ApplicationUser> Users { get; set; }
If you then add another property to your application-specific context such as:
public DbSet<ApplicationUser> ApplicationUsers { get; set; }
You now have the same entity tracked by two DbSet
s, and you get that error. The solution? Simply don't add your own DbSet
for ApplicationUser
. There's no need to rename or override anything.
Short-Version: Rename your ApplicationUser class to User.
I've been running into this problem for about a month with absolutely no luck...until now!
Initially, I thought it was a preview issue, but after persisting into the RTM along with the latest libraries, I became incredibly annoyed, since this problem persisted into Migrations too.
However, IdentityDbContext, according to the error message, seems to be creating two DbSets: ApplicationUsers and Users. We only want Users when looking at the source code:
public class IdentityDbContext<TUser> : DbContext where TUser : Microsoft.AspNet.Identity.EntityFramework.IdentityUser
{
...
public virtual IDbSet<TUser> Users { get; set; }
...
}
From this, we (and the scaffolding engine, and the migrations engine) should only see "Users", not "ApplicationUsers".
To rectify this situation, you will need to adjust your application class to account for this rather strange error. Simply rename your ApplicationUser class to User:
using Microsoft.AspNet.Identity.EntityFramework
...
public class ApplicationUser : IdentityUser
{
Your Stuff
}
To:
using Microsoft.AspNet.Identity.EntityFramework
...
public class User: IdentityUser
{
Your Stuff
}
Attempt to Scaffold again. If you receive another error along the lines of the class cannot be found, save your project, close VS2013, re-open VS2013, load the project, re-build the project, and finally attempt to scaffold. The IdentityDBContext should no longer be creating a dummy "ApplicationUsers" DBSet object causing both Entity Migrations and Scaffolding to issue these errors.
Hope this helps!
P.S. Any mapping done ought not to affect this problem, so you should be able to still map to the same table if you wish to.
EDIT:
If you receive further problems, undo the rename. I ran into some problems (more scaffolding and query errors), and after I went back to ApplicationUser
, those problems disappeared and the problem above did not re-occur. Just a heads up.
Read the above problems en solutions. My error text was:
Multiple object sets per type are not supported. The object sets 'ApplicationUsers' and 'Users' can both contain instances of type 'DataLayerIdentity.Models.ApplicationUser'
I suspect the error was created when I was playing around and scaffolded the model: ApplicationUser in a new controller.
Solved it by removing the below from : ApplicationDbContext.cs
public System.Data.Entity.DbSet<DataLayerIdentity.Models.ApplicationUser> ApplicationUsers
{
get;
set;
}
No Other changes where made to solve the problem. I hope this helps someone.
When you use scaffolding to generate control, vs will auto insert 1 line to your db context
public System.Data.Entity.DbSet<...API.Models.ApplicationUser> ApplicationUsers { get; set; }
Just delete that line, and in your controller. change
db.ApplicationUsers
to db.Users
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With