Il y a déjà un objet nommé "AspNetRoles" dans la base de données

il y a quelque temps, j'ai créé un ASP.NET MVC 5 site Web avec la version D'identité 1.0, et j'ai créé les tables D'identité avec ce projet. Maintenant je dois faire un autre site Web en utilisant la même base de données pour l'authentification, mais maintenant la version D'identité est 2.0. Donc, quand j'essaie de m'authentifier sur le nouveau site web, j'obtiens des erreurs.

J'essaie de migrer la base de données en utilisant L'approche Migrations, mais c'est confus et je reçois cette erreur There is already an object named 'AspNetRoles' in the database. quand je tape Update-Database dans le PM console.

ma question Est, Comment est la meilleure façon d'utiliser la même base de données pour l'authentification des deux sites (l'un utilisant la version d'identité 1.0 et l'autre utilisant 2.0). Ai-je vraiment besoin de migrer la base de données?

Si oui, comment puis-je résoudre cette erreur que je suis?

16
demandé sur gog 2014-06-11 21:33:32

2 réponses

Add-Migration InitialMigrations -IgnoreChanges

cela devrait générer un fichier "migration initiale" vierge. Maintenant, ajoutez tous les changements désirés à la classe que vous voulez. Une fois les modifications ajoutées, Lancez à nouveau la commande update:

update-database -verbose

Maintenant, la migration automatique sera appliquée et la table sera modifié avec vos modifications.

Edit: Voici une solution pour migrer l'identité 1 à 2 Upgrading from ASP.NET.Identité 1,0 à 2,0 Utilisez cette migration manuelle

public override void Up()
    {
        RenameColumn(table: "dbo.AspNetUserClaims", name: "User_Id", newName: "UserId");
        RenameIndex(table: "dbo.AspNetUserClaims", name: "IX_User_Id", newName: "IX_UserId");
        DropPrimaryKey("dbo.AspNetUserLogins");
        AddColumn("dbo.AspNetUsers", "Email", c => c.String(maxLength: 256));
        AddColumn("dbo.AspNetUsers", "EmailConfirmed", c => c.Boolean(nullable: false));
        AddColumn("dbo.AspNetUsers", "PhoneNumber", c => c.String()); 
        AddColumn("dbo.AspNetUsers", "PhoneNumberConfirmed", c => c.Boolean(nullable: false));
        AddColumn("dbo.AspNetUsers", "TwoFactorEnabled", c => c.Boolean(nullable: false));
        AddColumn("dbo.AspNetUsers", "LockoutEndDateUtc", c => c.DateTime());
        AddColumn("dbo.AspNetUsers", "LockoutEnabled", c => c.Boolean(nullable: false));
        AddColumn("dbo.AspNetUsers", "AccessFailedCount", c => c.Int(nullable: false));
        AlterColumn("dbo.AspNetUsers", "UserName", c => c.String(nullable: false, maxLength: 256));
        AlterColumn("dbo.AspNetUsers", "FirstName", c => c.String(nullable: false));
        AlterColumn("dbo.AspNetUsers", "LastName", c => c.String(nullable: false));
        AddColumn("dbo.AspNetUsers", "CreatedDateTime", c => c.DateTime(nullable: false));
        AlterColumn("dbo.AspNetRoles", "Name", c => c.String(nullable: false, maxLength: 256));
        AddPrimaryKey("dbo.AspNetUserLogins", new[] { "LoginProvider", "ProviderKey", "UserId" });
        CreateIndex("dbo.AspNetUsers", "UserName", unique: true, name: "UserNameIndex");
        CreateIndex("dbo.AspNetRoles", "Name", unique: true, name: "RoleNameIndex");
        DropColumn("dbo.AspNetUsers", "Discriminator");
    } 
35
répondu Mohsen Esmailpour 2014-06-11 19:16:11

alors que vous pouvez (depuis EF6) utiliser les migrations dans deux projets distincts pour la même base de données, il ne peut y avoir aucun chevauchement. La façon dont les migrations fonctionnent est à travers un dbo._MigrationHistory table qui stocke le contexte qui a généré la migration et l'État modèle de votre application, qui inclut les modèles D'identité.

lorsque vous essayez de connecter votre deuxième application, elle ne trouve aucune migration antérieure, et a donc besoin de générer sa migration initiale, qui inclura des tables pour le Modèles d'identité, qui sont dans son contexte. C'est là où est ton problème.

Pour les fins de l'Identité, vous devez choisir un projet à rendre le maître. Celui-ci utilisera un standard IdentityDbContext où les modèles D'identité seront migrés.

l'autre projet devra être transformé en esclave, du moins en termes D'utilisation de L'identité. Ainsi, vous aurez besoin d'interagir avec au moins deux contextes dans cette application. On va être une sous-classe de IdentityDbContext, mais traités en tant que base de données-première:

public class MyIdentityContext : IdentityDbContext<ApplicationUser>
{
    public MyIdentityContext()
        : base("ConnectionStringNameForYourSharedDB")
    {
        Database.SetInitializer<MyIdentityContext>(null);
    }
}

L'autre contexte sera juste un DbContext sous-classe qui sera migrée comme d'habitude. Vous devrez le répéter pour tout autre projet qui pourrait avoir besoin d'accéder aux mêmes renseignements D'identité provenant de la même base de données. En outre, en raison du code répétitif cela conduira à (et le fait que votre ApplicationUser classe devra être partagé), vous devez déplacer ce code dans une bibliothèque de classe que chaque projet peut faire référence.

10
répondu Chris Pratt 2014-06-11 18:37:11