ASP.NET Identity: Uso de almacenamiento MySQL con un proveedor de MySQL EntityFramework (C#)

de Maurycy Markowski, Sara Soares de Almeida, Robert McMurray

En este tutorial se muestra cómo reemplazar el mecanismo de almacenamiento de datos predeterminado para ASP.NET Identity por EntityFramework (proveedor de cliente SQL) por un proveedor mySQL.

En este tutorial se tratarán los temas siguientes:

  • Creación de una base de datos MySQL en Azure
  • Creación de una aplicación MVC mediante la plantilla de MVC de Visual Studio 2013
  • Configuración de EntityFramework para trabajar con un proveedor de bases de datos MySQL
  • Ejecución de la aplicación para comprobar los resultados

Al final de este tutorial, tendrá una aplicación MVC con el almacén de identidades de ASP.NET que usa una base de datos MySQL hospedada en Azure.

Creación de una instancia de base de datos MySQL en Azure

  1. Inicie sesión en Azure Portal.

  2. Haz clic en NUEVO en la parte inferior de la página y, a continuación, selecciona STORE:

    Captura de pantalla del menú de Azure Portal con el elemento de menú Tienda resaltado en la parte inferior y descrito con un rectángulo rojo.

  3. En el Asistente para elegir un complemento , seleccione ClearDB MySQL Database y, a continuación, haga clic en la flecha Siguiente en la parte inferior del marco:

    [Haga clic en la siguiente imagen para expandirla. ] Captura de pantalla del Asistente para elegir un complemento, con Clear D B My S Q L Database resaltado con un rectángulo rojo.

  4. Mantenga el plan gratis predeterminado, cambie el nombre a IdentityMySQLDatabase, seleccione la región más cercana a usted y, a continuación, haga clic en la flecha Siguiente en la parte inferior del marco:

    [Haga clic en la siguiente imagen para expandirla. ] Captura de pantalla del cuadro de diálogo Personalizar complemento que muestra la opción Plan gratis y los campos Nombre y región seleccionados y resaltados con un rectángulo rojo.

  5. Haga clic en la marca de verificación COMPRAR para completar la creación de la base de datos.

    [Haga clic en la siguiente imagen para expandirla. ] Captura de pantalla del cuadro de diálogo Revisar compra que muestra el botón Comprar resaltado con un rectángulo rojo.

  6. Una vez creada la base de datos, puede administrarla desde la pestaña ADD-ONS del portal de administración. Para recuperar la información de conexión de la base de datos, haga clic en INFORMACIÓN DE CONEXIÓN en la parte inferior de la página:

    [Haga clic en la siguiente imagen para expandirla. ] Captura de pantalla del portal de administración con la pestaña Agregar, el elemento de base de datos Identificar mi S Q L y el botón Información de conexión resaltado en rojo.

  7. Copie la cadena de conexión haciendo clic en el botón copiar por el campo CONNECTIONSTRING y guárdelo; Usará esta información más adelante en este tutorial para la aplicación MVC:

    [Haga clic en la siguiente imagen para expandirla. ] Captura de pantalla del cuadro de diálogo Información de conexión con el botón copiar resaltado a la derecha del campo Cadena de conexión.

Creación de un proyecto de aplicación MVC

Para completar los pasos de esta sección del tutorial, primero deberá instalar Visual Studio Express 2013 para Web o Visual Studio 2013. Una vez instalado Visual Studio, siga estos pasos para crear un nuevo proyecto de aplicación MVC:

  1. Abra Visual Studio 2103.

  2. Haga clic en Nuevo proyecto en la página Inicio , o bien puede hacer clic en el menú Archivo y, a continuación, en Nuevo proyecto:

    [Haga clic en la siguiente imagen para expandirla. ] Captura de pantalla de la página de inicio de Visual Studio que muestra la opción Nuevo proyecto resaltada con un rectángulo rojo.

  3. Cuando se muestre el cuadro de diálogo Nuevo proyecto , expanda Visual C# en la lista de plantillas, haga clic en Web y seleccione ASP.NET Aplicación web. Asigne al proyecto el nombre IdentityMySQLDemo y haga clic en Aceptar:

    [Haga clic en la siguiente imagen para expandirla. ] Captura de pantalla del cuadro de diálogo Nuevo proyecto, con la almohadilla de Visual C expandida a la izquierda y Web resaltada. Aplicación web ASP.NET seleccionada a la derecha con el nombre del proyecto Identity MySQL Demo en el campo de nombre en la parte inferior.

  4. En el cuadro de diálogo Nuevo ASP.NET Proyecto , seleccione la plantilla MVC con las opciones predeterminadas; esto configurará cuentas de usuario individuales como método de autenticación. Haga clic en Aceptar:

    [Haga clic en la siguiente imagen para expandirla. ] Captura de pantalla del cuadro de diálogo Nuevo proyecto de A S P punto NET, con la plantilla M V C seleccionada y con las opciones predeterminadas activadas.

Configuración de EntityFramework para trabajar con una base de datos MySQL

Actualización del ensamblado de Entity Framework para el proyecto

La aplicación MVC que se creó a partir de la plantilla de Visual Studio 2013 contiene una referencia al paquete EntityFramework 6.0.0 , pero ha habido actualizaciones en ese ensamblado desde su versión que contienen mejoras de rendimiento significativas. Para usar estas actualizaciones más recientes en la aplicación, siga estos pasos.

  1. Abra el proyecto MVC en Visual Studio.

  2. Haga clic en Herramientas y, a continuación, en Administrador de paquetes NuGet y, a continuación, haga clic en Consola del Administrador de paquetes:

    [Haga clic en la siguiente imagen para expandirla. ] Captura de pantalla del proyecto de M V C en Visual Studio, con herramientas seleccionadas en el menú superior, Administrador de paquetes de biblioteca seleccionado a la izquierda y Consola del Administrador de paquetes seleccionada a la derecha.

  3. La consola del Administrador de paquetes aparecerá en la sección inferior de Visual Studio. Escriba "Update-Package EntityFramework" y presione Entrar:

    [Haga clic en la siguiente imagen para expandirla. ] Captura de pantalla de la consola del Administrador de paquetes en la sección inferior de Visual Studio, con la instrucción Update Package Entity Framework mostrada en la línea de comandos.

Instalación del proveedor MySQL para EntityFramework

Para que EntityFramework se conecte a la base de datos MySQL, debe instalar un proveedor de MySQL. Para ello, abra la consola del Administrador de paquetes y escriba "Install-Package MySql.Data.Entity -Pre" y presione Entrar.

Nota:

Se trata de una versión preliminar del ensamblado y, como tal, puede contener errores. No debe usar una versión preliminar del proveedor en producción.

[Haga clic en la siguiente imagen para expandirla.]

Captura de pantalla de la Consola del Administrador de Paquetes en la sección inferior de Visual Studio, con la instrucción Install-Package MySql.Data.Entity-Pre mostrada en la línea de comandos.

Realizar cambios en la configuración del proyecto en el archivo Web.config de la aplicación

En esta sección, configurará Entity Framework para que use el proveedor mySQL que acaba de instalar, registre el generador de proveedores de MySQL y agregue la cadena de conexión desde Azure.

Nota:

Los ejemplos siguientes contienen una versión de ensamblado específica para MySql.Data.dll. Si cambia la versión del ensamblado, deberá modificar las opciones de configuración adecuadas con la versión correcta.

  1. Abra el archivo Web.config del proyecto en Visual Studio 2013.

  2. Busque las siguientes opciones de configuración, que definen el proveedor de base de datos predeterminado y el generador para Entity Framework:

    <entityFramework>
      <defaultConnectionFactory
          type="System.Data.Entity.Infrastructure.LocalDbConnectionFactory, EntityFramework">
        <parameters>
          <parameter value="v11.0" />
        </parameters>
      </defaultConnectionFactory>
      <providers>
        <provider
          invariantName="System.Data.SqlClient"
          type="System.Data.Entity.SqlServer.SqlProviderServices, EntityFramework.SqlServer" />
      </providers>
    </entityFramework>
    
  3. Reemplace esos valores de configuración por lo siguiente, que configurará Entity Framework para que use el proveedor MySQL:

    <entityFramework>
      <providers>
        <provider invariantName="MySql.Data.MySqlClient"
          type="MySql.Data.MySqlClient.MySqlProviderServices, MySql.Data.Entity"/> 
      </providers>
    </entityFramework>
    <system.data>
      <DbProviderFactories>
        <remove invariant="MySql.Data.MySqlClient"></remove>
        <add name="MySQL Data Provider"
          invariant="MySql.Data.MySqlClient"
          description=".Net Framework Data Provider for MySQL"
          type="MySql.Data.MySqlClient.MySqlClientFactory, MySql.Data, Version=6.7.2.0"/>
      </DbProviderFactories>
    </system.data>
    
  4. Busque la <sección connectionStrings> y reemplácela por el código siguiente, que definirá la cadena de conexión para la base de datos MySQL hospedada en Azure (tenga en cuenta que el valor providerName también ha cambiado del original):

    <connectionStrings>
      <add name="DefaultConnection"
        providerName="MySql.Data.MySqlClient"
        connectionString="[Insert your ConnectionString from Azure here]"/>
    </connectionStrings>
    

La adición de un contexto de historial de migración personalizado

Entity Framework Code First usa una tabla MigrationHistory para realizar un seguimiento de los cambios del modelo y garantizar la coherencia entre el esquema de la base de datos y el esquema conceptual. Sin embargo, esta tabla no funciona para MySQL de forma predeterminada porque la clave principal es demasiado grande. Para solucionar esta situación, deberá reducir el tamaño de la clave de esa tabla. Para ello, siga estos pasos:

  1. La información de esquema de esta tabla se captura en un HistoryContext, que se puede modificar como cualquier otro DbContext. Para ello, agregue un nuevo archivo de clase denominado MySqlHistoryContext.cs al proyecto y reemplace su contenido por el código siguiente:

    using System.Data.Common;
    using System.Data.Entity;
    using System.Data.Entity.Migrations.History;
     
    namespace IdentityMySQLDemo
    {
      public class MySqlHistoryContext : HistoryContext
      {
        public MySqlHistoryContext(
          DbConnection existingConnection,
          string defaultSchema)
        : base(existingConnection, defaultSchema)
        {
        }
     
        protected override void OnModelCreating(DbModelBuilder modelBuilder)
        {
          base.OnModelCreating(modelBuilder);
          modelBuilder.Entity<HistoryRow>().Property(h => h.MigrationId).HasMaxLength(100).IsRequired();
          modelBuilder.Entity<HistoryRow>().Property(h => h.ContextKey).HasMaxLength(200).IsRequired();
        }
      }
    }
    
  2. A continuación, deberá configurar Entity Framework para que use HistoryContext modificado, en lugar de uno predeterminado. Esto se puede hacer aprovechando las características de configuración basadas en código. Para ello, agregue un nuevo archivo de clase denominado MySqlConfiguration.cs al proyecto y reemplace su contenido por:

    using System.Data.Entity;
     
    namespace IdentityMySQLDemo
    {
      public class MySqlConfiguration : DbConfiguration
      {
        public MySqlConfiguration()
        {
          SetHistoryContext(
          "MySql.Data.MySqlClient", (conn, schema) => new MySqlHistoryContext(conn, schema));
        }
      }
    }
    

Creación de un inicializador EntityFramework personalizado para ApplicationDbContext

El proveedor MySQL que se incluye en este tutorial no admite actualmente migraciones de Entity Framework, por lo que deberá usar inicializadores de modelos para conectarse a la base de datos. Dado que este tutorial usa una instancia de MySQL en Azure, deberá crear un inicializador personalizado de Entity Framework.

Nota:

Este paso no es necesario si se conecta a una instancia de SQL Server en Azure o si usa una base de datos hospedada en el entorno local.

Para crear un inicializador de Entity Framework personalizado para MySQL, siga estos pasos:

  1. Agregue un nuevo archivo de clase denominado MySqlInitializer.cs al proyecto y reemplace su contenido por el código siguiente:

    using IdentityMySQLDemo.Models;
    using System.Data.Entity;
    using System.Data.Entity.Infrastructure;
    using System.Linq;
    
    namespace IdentityMySQLDemo
    {
      public class MySqlInitializer : IDatabaseInitializer<ApplicationDbContext>
      {
        public void InitializeDatabase(ApplicationDbContext context)
        {
          if (!context.Database.Exists())
          {
            // if database did not exist before - create it
            context.Database.Create();
          }
          else
          {
            // query to check if MigrationHistory table is present in the database 
            var migrationHistoryTableExists = ((IObjectContextAdapter)context).ObjectContext.ExecuteStoreQuery<int>(
              "SELECT COUNT(*) FROM information_schema.tables WHERE table_schema = 'IdentityMySQLDatabase' AND table_name = '__MigrationHistory'");
    
            // if MigrationHistory table is not there (which is the case first time we run) - create it
            if (migrationHistoryTableExists.FirstOrDefault() == 0)
            {
              context.Database.Delete();
              context.Database.Create();
            }
          }
        }
      }
    }
    
  2. Abra el archivo IdentityModels.cs del proyecto, que se encuentra en el directorio Models y reemplace el contenido por lo siguiente:

    using Microsoft.AspNet.Identity.EntityFramework;
    using System.Data.Entity;
    
    namespace IdentityMySQLDemo.Models
    {
      // You can add profile data for the user by adding more properties to your ApplicationUser
      // class, please visit https://go.microsoft.com/fwlink/?LinkID=317594 to learn more.
      public class ApplicationUser : IdentityUser
      {
      }
    
      public class ApplicationDbContext : IdentityDbContext<ApplicationUser>
      {
        static ApplicationDbContext()
        {
          Database.SetInitializer(new MySqlInitializer());
        }
    
        public ApplicationDbContext()
          : base("DefaultConnection")
        {
        }
      }
    }
    

Ejecución de la aplicación y comprobación de la base de datos

Una vez que haya completado los pasos de las secciones anteriores, debe probar la base de datos. Para ello, siga estos pasos:

  1. Presione Ctrl + F5 para compilar y ejecutar la aplicación web.

  2. Haga clic en la pestaña Registrar de la parte superior de la página:

    [Haga clic en la siguiente imagen para expandirla. ] Captura de pantalla del sitio web de ASP.NET, con la pestaña de registro resaltada en el menú de la esquina superior derecha.

  3. Escriba un nuevo nombre de usuario y una contraseña y, a continuación, haga clic en Registrar:

    [Haga clic en la siguiente imagen para expandirla. ] Captura de pantalla del cuadro de diálogo de registro de ASP.NET, con el campo de nombre de usuario, la contraseña, el campo 'confirmar contraseña' completados y el botón Registrar resaltado a continuación.

  4. En este momento, las tablas ASP.NET Identity se crean en la base de datos MySQL y el usuario se registra e inicia sesión en la aplicación:

    [Haga clic en la siguiente imagen para expandirla. ] Captura de pantalla del sitio web de ASP.NET después de que el usuario haya completado el registro. La pestaña con el saludo 'Hola', seguido del nombre de usuario, se resalta en el menú de la esquina superior derecha.

Instalación de la herramienta MySQL Workbench para comprobar los datos

  1. Instalación de la herramienta MySQL Workbench desde la página de descargas de MySQL

  2. En el Asistente para la instalación: pestaña Selección de características , seleccione MySQL Workbench en la sección aplicaciones .

  3. Inicie la aplicación y agregue una nueva conexión mediante los datos de cadena de conexión de la base de datos de Azure MySQL que creó al principio de este tutorial.

  4. Después de establecer la conexión, inspeccione las tablas ASP.NET Identity creadas en IdentityMySQLDatabase.

  5. Verá que todas las tablas necesarias de identidad de ASP.NET se crean como se muestra en la imagen siguiente:

    [Haga clic en la siguiente imagen para expandirla. ] Captura de pantalla del cuadro de diálogo de la herramienta My S Q L Workbench. Las tablas S P dot NET Identity creadas en la base de datos Identity My S Q L se resaltan en la parte inferior izquierda.

  6. Inspeccione la tabla aspnetusers para que, por ejemplo, compruebe las entradas a medida que registra nuevos usuarios.

    [Haga clic en la siguiente imagen para expandirla. ] Captura de pantalla de una tabla de usuarios de s p net, con entradas que muestran las columnas I D, Nombre de usuario, Hash de contraseña, Marca de seguridad y Discriminador.