Question

I am using code first migrations in an asp.net mvc program.

I am using the default authenticion and roles which is provided in the project.

Now when I enabled migrations it automatically generated a migration class which generates all of the tables etc.

Here is an excample of the specific table which I wqish to edit.

 CreateTable(
            "dbo.AspNetUserRoles",
            c => new
                {
                    UserId = c.String(nullable: false, maxLength: 128),
                    RoleId = c.String(nullable: false, maxLength: 128),
                })
            .PrimaryKey(t => new { t.UserId, t.RoleId })
            .ForeignKey("dbo.AspNetRoles", t => t.RoleId, cascadeDelete: true)
            .ForeignKey("dbo.AspNetUsers", t => t.UserId, cascadeDelete: true)
            .Index(t => t.RoleId)
            .Index(t => t.UserId);

Now I would like to add a description field to this table. It would be really easy if i just added it in the database but then I will loose my code first migrations.

1> Where does Entity framework get all its commands for the initial migration? Because there are no models in my project that I can see which specify the tables it creates.

2> How can I modify or edit some of the original tables which are generated? I have tried just editing the initial migrations folder but that does not work?

(Just my thinking) Is it not that maybe the Roles and users models are stored in the framework and that is where it gets the structure of the tables from? If so Can i not extend the default model to add more attributes? Cause I know you can do it for the ApplicationUser, I have done so before, here is an example of it:

 // You can add profile data for the user by adding more properties to your ApplicationUser class, please visit http://go.microsoft.com/fwlink/?LinkID=317594 to learn more.
public class ApplicationUser : IdentityUser
{
    [Required]
    [MaxLength(50)]
    [Display(Name = "Email Address")]
    public string email { get; set; }
 }

Thats how i can add a email address field to the default user. Can I not maybe do this with the roles as well.

Was it helpful?

Solution

You dit it perfectly for the ApplicationUser, just continue like that for the other stuff. If you want to add description to the table of the users. Just add it to the ApplicationUser model. Don't mind the foreign keys and virtual properties.

    public class ApplicationUser : IdentityUser
    {
        [Required]
        public string FirstName { get; set; }
        [Required]
        public string LastName { get; set; }
        public string GroupName { get; set; }
        [Required]
        public string Email { get; set; }
        [Required]
        [StringLength(15)]
        public string Phone { get; set; }
        public string Remark { get; set; }
        public DateTime? BirthDate { get; set; }
        public DateTime ValidFrom { get; set; }
        public DateTime ValidUntil { get; set; }

        // Foreign keys
        [ForeignKey("Bank")]
        public string AccountNumber { get; set; }
        [ForeignKey("Address")]
        public int? AddressId { get; set; }

        public virtual Bank Bank { get; set; }
        public virtual Address Address { get; set; }
        public virtual ICollection<Request> Requests { get; set; } 
    }

For editing the role class, you should inherit IdentityRole on your class and add the properties:

public class ApplicationRole : IdentityRole
{
    public string Description { get; set; }
}

The framework will generate new migration classes which will be ran when you use the Update-Database command.

You have to change your identityManager (Use ApplicationRole here):

public class IdentityManager
{

    public bool RoleExists(string name)
    {
        var rm = new RoleManager<ApplicationRole>(new RoleStore<ApplicationRole>(new ApplicationDbContext()));

        return rm.RoleExists(name);
    }

    public bool CreateRole(string name)
    {
        var rm = new RoleManager<ApplicationRole>(new RoleStore<ApplicationRole>(new ApplicationDbContext()));

        var idResult = rm.Create(new ApplicationRole(name));

        return idResult.Succeeded;
    }
}

You have to overwrite the Role in ApplicationDbContext doing like following (don't forget the new):

public class ApplicationDbContext : IdentityDbContext<ApplicationUser>
{
    public ApplicationDbContext()
        : base("DefaultConnection")
    {
    }

    ...
    public DbSet<Product> Products { get; set; }
    new public DbSet<ApplicationRole> Roles { get; set; }
}
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top