Entity Framework MigrationSqlGenerator for SQLite

is there a MigrationSqlGenerator for SQLite to use with entity framework? I only found one from devart which is commercial.

No MigrationSqlGenerator found for provider 'System.Data.SQLite'. Use the SetSqlGenerator method in the target migrations configuration class to register additional SQL generators.

This is what I do: http://msdn.microsoft.com/en-gb/data/jj591621

I don't think there is any, free one, to my knowledge.

If you don't care for the Devart commercial dotConnect for SQLite - you could try implementing one yourself - it may not be as simple but you have the EF source code at your disposal (for EF6 but those parts are quite similar I'd say). http://entityframework.codeplex.com/

If you take a look at the SqlCeMigrationSqlGenerator source code (the other source, I couldn't find one on offical site, but you can download and check)

...you'll see that the generator is relatively simplistic. Of course that goes for Ce which is using standard Sql client as underlying generator.

SQLite will require more work but may not be that hard.

Also, similar thing coming from a well know source on EF here - Can we use EF migrations with MySql


And don't 'yell at me' :) I know this isn't what you're looking for - but I think that's the only alternative really.


http://entityframework.codeplex.com/ SqlCeMigrationSqlGenerator Can we use EF migrations with MySql

Entity Framework MigrationSqlGenerator for SQLite, I don't think there is any, free one, to my knowledge. If you don't care for the Devart commercial dotConnect for SQLite - you could try  EntityFramework.dll. Common base class for providers that convert provider agnostic migration operations into database provider specific SQL commands.

For anyone who is looking for a generator that handles migrations as well I found a nuget package at https://sqliteef6migrations.codeplex.com called "System.Data.SQLite.EF6.Migrations".

After you have installed the package you will need to make the following changes to the Migrations Configuration Method.

 public Configuration()
 {
    AutomaticMigrationsEnabled = false;
    SetSqlGenerator("System.Data.SQLite", new SQLiteMigrationSqlGenerator());
 }

The complete class should look something like this.

namespace YourNamespace
{
    using System.Data.Entity.Migrations;
    using System.Data.SQLite.EF6.Migrations;

    internal sealed class Configuration : DbMigrationsConfiguration<YourContext>
    {
        public Configuration()
        {
            AutomaticMigrationsEnabled = false;
            SetSqlGenerator("System.Data.SQLite", new SQLiteMigrationSqlGenerator());
        }

        protected override void Seed(YourContext context)
        {
            //  This method will be called after migrating to the latest version.
        }
    }
}

System.Data.SQLite.EF6.Migrations, Project Description Migrations for Entity Framework 6 SQLite provider. Limitations​: - Relationships are not enforced with constraints - There can be only one  is there a MigrationSqlGenerator for SQLite to use with entity framework? I only found one from devart which is commercial. No MigrationSqlGenerator found for provider 'System.Data.SQLite'. Use the SetSqlGenerator method in the target migrations configuration class to register additional SQL generators.

Although the post was open for a long time, I'll post what I got to do based on what our friend NSGaga showed up.

I managed to create a class "MigrationSqLiteGenerator", based on what was developed for SQLCE. The code of the class was too large, more can download it on my blog.

On Google Drive: https://drive.google.com/file/d/0B-NCqWnMQpBrQjkxMkxnVlRzb00/view?usp=sharing

This class has only the basics, plus is a starting point for improvement.

22.Mar.2017 EDIT by @shiva : Here's the code inline so if the Google Drive link breaks again, you can still access the code. Just found out SO has a 30,000 character limit in answer posts, so I had to delete the comments in the code. It was over 32,000 character with comments :)

//           *-----------------------------------------------------------------*
//           *                                                                 *
//           *    CRIADO POR...: Julio C. Borges.                              *
//           *    DATA.........: 19/07/2013.                                   *
//           *    MOTIVO.......:                                               *
//           *                                                                 *
//           *-----------------------------------------------------------------*

using System;
using System.CodeDom.Compiler;
using System.Collections.Generic;
using System.Data.Common;
using System.Data.Entity.Migrations.Model;
using System.Data.Entity.Migrations.Sql;
using System.Data.Metadata.Edm;
using System.Data.SQLite;
using System.Globalization;
using System.IO;
using System.Linq;
using System.Text;

namespace ICM_Conexao.SqLite.Classes
{
    /// <sumary>
    /// MigrationSqLiteGenerator 
    /// </sumary>
    public class MigrationSqLiteGenerator : MigrationSqlGenerator
    {
        #region Constantes

        private const string pstrDefaultDateTime = "yyyy-MM-dd hh:mm:ss";
        private const int pintDefaultStringMaxLength = 255;
        private const int pintDefaultPrecisaoNumerica = 10;
        private const byte pbytDefaultPrecisaoTempo = 7;
        private const byte pintDefaultEscala = 0;
        //private const string pstrNomeTabelaMigration = "__MigrationHistory"; 

        #endregion

        #region Instancias

        private DbProviderManifest pprovProviderManifest;
        private List<MigrationStatement> plstComandos;
        private bool pblnGerouPrimaryKey;

        #endregion

        #region Método de Geração sobrescrito de MigratioSqlGenerator

        public override IEnumerable<MigrationStatement> Generate(
            IEnumerable<MigrationOperation> lstOperacoesMigrations, string strManifestoProvider)
        {
            plstComandos = new List<MigrationStatement>();

            InicializaServicosProvider(strManifestoProvider);
            GeraComandos(lstOperacoesMigrations);

            return plstComandos;
        }

        #endregion

        #region Métodos de geração dos comandos

        protected virtual void Generate(CreateTableOperation opeCriacaoTabela)
        {
            // Preferencialmente não iremos gerar a tabela de dados do Migration
            if (opeCriacaoTabela.Name.Contains("MigrationHistory"))
                return;

            using (var ltextWriter = TextWriter())
            {
                GeraComandoCriacaoTabela(opeCriacaoTabela, ltextWriter);

                ComandoSQL(ltextWriter);
            }
        }

        protected virtual void Generate(AddForeignKeyOperation opeChaveEstrangeira)
        {
            // Inicialmente não havera a criação de chave estrangeira
        }

         protected virtual void Generate(DropForeignKeyOperation dropForeignKeyOperation)
        {
            // Inicalmente não haverá a criação de chave estrangeira
        }

        protected virtual void Generate(CreateIndexOperation opeCriacaoIndex)
        {
            using (var ltextWriter = TextWriter())
            {
                ltextWriter.Write("CREATE ");

                if (opeCriacaoIndex.IsUnique)
                    ltextWriter.Write(" UNIQUE ");

                ltextWriter.Write("INDEX ");
                ltextWriter.Write(opeCriacaoIndex.Name);
                ltextWriter.Write(" ON ");
                ltextWriter.Write(RemoveDBO(opeCriacaoIndex.Table));
                ltextWriter.Write("(");

                for (int lintCount = 0; lintCount < opeCriacaoIndex.Columns.Count; lintCount++)
                {
                    var lstrDadosColuna = opeCriacaoIndex.Columns[lintCount];

                    ltextWriter.Write(lstrDadosColuna);

                    if (lintCount < opeCriacaoIndex.Columns.Count - 1)
                        ltextWriter.WriteLine(",");
                }

                ltextWriter.Write(")");

                ComandoSQL(ltextWriter);
            }
        }

         protected virtual void Generate(DropIndexOperation opeDropIndex)
        {
            using (var ltextWriter = TextWriter())
            {
                ltextWriter.Write("DROP INDEX ");
                ltextWriter.Write(opeDropIndex.Name);

                ComandoSQL(ltextWriter);
            }
        }

         protected virtual void Generate(AddPrimaryKeyOperation opeAdicionaPrimaryKey)
        {
            using (var ltextWriter = TextWriter())
            {
                ltextWriter.Write("ALTER TABLE ");
                ltextWriter.Write(RemoveDBO(opeAdicionaPrimaryKey.Table));
                ltextWriter.Write(" ADD CONSTRAINT ");
                ltextWriter.Write(opeAdicionaPrimaryKey.Name);
                ltextWriter.Write(" PRIMARY KEY ");
                ltextWriter.Write("(");

                for (int li = 0; li < opeAdicionaPrimaryKey.Columns.Count; li++)
                {
                    var lstrDadosColuna = opeAdicionaPrimaryKey.Columns[li];

                    ltextWriter.Write(lstrDadosColuna);

                    if (li < opeAdicionaPrimaryKey.Columns.Count - 1)
                        ltextWriter.WriteLine(",");
                }

                ltextWriter.Write(")");

                ComandoSQL(ltextWriter);
            }
        }

        protected virtual void Generate(DropPrimaryKeyOperation opeDropPrimaryKey)
        {
            using (var ltextWriter = TextWriter())
            {
                ltextWriter.Write("ALTER TABLE ");
                ltextWriter.Write(RemoveDBO(opeDropPrimaryKey.Table));
                ltextWriter.Write(" DROP CONSTRAINT ");
                ltextWriter.Write(opeDropPrimaryKey.Name);

                ComandoSQL(ltextWriter);
            }
        }

        protected virtual void Generate(AddColumnOperation opeAdicionaColuna)
        {
            using (var ltextWriter = TextWriter())
            {
                ltextWriter.Write("ALTER TABLE ");
                ltextWriter.Write(RemoveDBO(opeAdicionaColuna.Table));
                ltextWriter.Write(" ADD ");

                var lcmColuna = opeAdicionaColuna.Column;

                Generate(lcmColuna, ltextWriter, null);

                if ((lcmColuna.IsNullable != null)
                    && !lcmColuna.IsNullable.Value
                    && (lcmColuna.DefaultValue == null)
                    && (string.IsNullOrWhiteSpace(lcmColuna.DefaultValueSql))
                    && !lcmColuna.IsIdentity
                    && !lcmColuna.IsTimestamp
                    && !lcmColuna.StoreType.Equals("rowversion", StringComparison.InvariantCultureIgnoreCase)
                    && !lcmColuna.StoreType.Equals("timestamp", StringComparison.InvariantCultureIgnoreCase))
                {
                    ltextWriter.Write(" DEFAULT ");

                    if (lcmColuna.Type == PrimitiveTypeKind.DateTime)
                    {
                        ltextWriter.Write(Generate(DateTime.Parse("1900-01-01 00:00:00", CultureInfo.InvariantCulture)));
                    }
                    else
                    {
                        ltextWriter.Write(Generate((dynamic)lcmColuna.ClrDefaultValue));
                    }
                }

                ComandoSQL(ltextWriter);
            }
        }

         protected virtual void Generate(DropColumnOperation opeRemoveColuna)
        {
            using (var ltextWriter = TextWriter())
            {
                ltextWriter.Write("ALTER TABLE ");
                ltextWriter.Write(RemoveDBO(opeRemoveColuna.Table));
                ltextWriter.Write(" DROP COLUMN ");
                ltextWriter.Write(opeRemoveColuna.Name);

                ComandoSQL(ltextWriter);
            }
        }

        protected virtual void Generate(AlterColumnOperation opeAlteraColuna)
        {
            var lcmColuna = opeAlteraColuna.Column;

            using (var ltextWriter = TextWriter())
            {
                ltextWriter.Write("ALTER TABLE ");
                ltextWriter.Write(RemoveDBO(opeAlteraColuna.Table));
                ltextWriter.Write(" ALTER COLUMN ");
                ltextWriter.Write(lcmColuna.Name);
                ltextWriter.Write(" ");
                ltextWriter.Write(ConstruirTipoColuna(lcmColuna));

                if ((lcmColuna.IsNullable != null)
                    && !lcmColuna.IsNullable.Value)
                {
                    ltextWriter.Write(" NOT NULL");
                }

                ComandoSQL(ltextWriter);
            }

            if ((lcmColuna.DefaultValue == null) && string.IsNullOrWhiteSpace(lcmColuna.DefaultValueSql))
                return;

            using (var ltextWriter = TextWriter())
            {
                ltextWriter.Write("ALTER TABLE ");
                ltextWriter.Write(RemoveDBO(opeAlteraColuna.Table));
                ltextWriter.Write(" ALTER COLUMN ");
                ltextWriter.Write(lcmColuna.Name);
                ltextWriter.Write(" DROP DEFAULT");

                ComandoSQL(ltextWriter);
            }

            using (var ltextWriter = TextWriter())
            {
                ltextWriter.Write("ALTER TABLE ");
                ltextWriter.Write(RemoveDBO(opeAlteraColuna.Table));
                ltextWriter.Write(" ALTER COLUMN ");
                ltextWriter.Write(lcmColuna.Name);
                ltextWriter.Write(" SET DEFAULT ");
                ltextWriter.Write(
                    (lcmColuna.DefaultValue != null)
                        ? Generate((dynamic)lcmColuna.DefaultValue)
                        : lcmColuna.DefaultValueSql
                    );

                ComandoSQL(ltextWriter);
            }
        }

        protected virtual void Generate(DropTableOperation opeDropTable)
        {
            using (var ltextWriter = TextWriter())
            {
                ltextWriter.Write("DROP TABLE ");
                ltextWriter.Write(RemoveDBO(opeDropTable.Name));

                ComandoSQL(ltextWriter);
            }
        }

        protected virtual void Generate(SqlOperation opeSQL)
        {
            ComandoSQL(opeSQL.Sql, opeSQL.SuppressTransaction);
        }

         protected virtual void Generate(RenameColumnOperation opeRenomearColuna)
        {
            // Inicialmente não suportada
        }

        protected virtual void Generate(RenameTableOperation opeRenameTable)
        {
        }

        protected virtual void Generate(MoveTableOperation opeMoveTable)
        {
        }

        private void Generate(ColumnModel cmDadosColuna, IndentedTextWriter textWriter, PrimaryKeyOperation opePrimaryKey)
        {
            textWriter.Write(cmDadosColuna.Name);
            textWriter.Write(" ");
            bool lblnEhPrimaryKey = false;

            if (opePrimaryKey != null)
                lblnEhPrimaryKey = opePrimaryKey.Columns.Contains(cmDadosColuna.Name);


            if (lblnEhPrimaryKey)
            {
                if ((cmDadosColuna.Type == PrimitiveTypeKind.Int16) ||
                    (cmDadosColuna.Type == PrimitiveTypeKind.Int32))
                    textWriter.Write(" INTEGER ");
                else
                    textWriter.Write(ConstruirTipoColuna(cmDadosColuna));

                if (cmDadosColuna.IsIdentity)
                {
                    textWriter.Write(" PRIMARY KEY AUTOINCREMENT ");
                    pblnGerouPrimaryKey = true;
                }
            }
            else
            {
                textWriter.Write(ConstruirTipoColuna(cmDadosColuna));

                if ((cmDadosColuna.IsNullable != null)
                    && !cmDadosColuna.IsNullable.Value)
                {
                    textWriter.Write(" NOT NULL");
                }

                if (cmDadosColuna.DefaultValue != null)
                {
                    textWriter.Write(" DEFAULT ");
                    textWriter.Write(Generate((dynamic)cmDadosColuna.DefaultValue));
                }
                else if (!string.IsNullOrWhiteSpace(cmDadosColuna.DefaultValueSql))
                {
                    textWriter.Write(" DEFAULT ");
                    textWriter.Write(cmDadosColuna.DefaultValueSql);
                }
            }
        }

        protected virtual void Generate(HistoryOperation opeHistorico)
        {
            // Foi removido, pois atualmente não usaremos o Migration
            //using (var ltextWriter = TextWriter())
            //{
            //    if (opeHistorico is InsertHistoryOperation)
            //    {
            //        InsertHistoryOperation lhisOperacaoInsert = opeHistorico as InsertHistoryOperation;
            //        ltextWriter.Write(" INSERT INTO ");
            //        ltextWriter.Write(pstrNomeTabelaMigration);
            //        ltextWriter.Write(" ( MigrationId, Model, ProductVersion) VALUES ");
            //        ltextWriter.Write(string.Format(" ('{0}', {1}, '{2}')",
            //            lhisOperacaoInsert.MigrationId,
            //            Generate(lhisOperacaoInsert.Model), lhisOperacaoInsert.ProductVersion));
            //    }
            //    else if (opeHistorico is DeleteHistoryOperation)
            //    {
            //        DeleteHistoryOperation lhisOperacaoInsert = opeHistorico as DeleteHistoryOperation;
            //        ltextWriter.Write(" DELETE FROM ");
            //        ltextWriter.Write(pstrNomeTabelaMigration);
            //        ltextWriter.Write(string.Format(" WHERE MigrationId = '{0}'",
            //            lhisOperacaoInsert.MigrationId));
            //    }

            //    ComandoSQL(ltextWriter);
            //}
        }

        protected virtual string Generate(byte[] bytDefaultValue)
        {
            var lstrbHexString = new StringBuilder();

            foreach (var lbtByte in bytDefaultValue)
                lstrbHexString.Append(lbtByte.ToString("X2", CultureInfo.InvariantCulture));

            return "x'" + lstrbHexString + "'";
        }

        protected virtual string Generate(bool blnDefaultValue)
        {
            return blnDefaultValue ? "1" : "0";
        }

        protected virtual string Generate(DateTime dtmDefaultValue)
        {
            return "'" + dtmDefaultValue.ToString(pstrDefaultDateTime, CultureInfo.InvariantCulture) + "'";
        }

        protected virtual string Generate(DateTimeOffset dtfDefaultValue)
        {
            return "'" + dtfDefaultValue.ToString(pstrDefaultDateTime, CultureInfo.InvariantCulture) + "'";
        }

        protected virtual string Generate(Guid guidDefaultValue)
        {
            return "'" + guidDefaultValue + "'";
        }

        protected virtual string Generate(string strDefaultValue)
        {
            return "'" + strDefaultValue + "'";
        }

        protected virtual string Generate(TimeSpan tsDefaultValue)
        {
            return "'" + tsDefaultValue + "'";
        }

        protected virtual string Generate(object objDefaultValue)
        {
            return string.Format(CultureInfo.InvariantCulture, "{0}", objDefaultValue);
        }

        #endregion

        #region Métodos auxiliares

        protected virtual string ConstruirTipoColuna(ColumnModel cmModeloColuna)
        {
            return cmModeloColuna.IsTimestamp ? "rowversion" : ConstruirTipoPropriedade(cmModeloColuna);
        }

        private string ConstruirTipoPropriedade(ColumnModel propModeloPropriedade)
        {
            var lstrOriginalStoreTypeName = propModeloPropriedade.StoreType;

            if (string.IsNullOrWhiteSpace(lstrOriginalStoreTypeName))
            {
                var ltypeUsage = pprovProviderManifest.GetStoreType(propModeloPropriedade.TypeUsage).EdmType;
                lstrOriginalStoreTypeName = ltypeUsage.Name;
            }

            var lstrStoreTypeName = lstrOriginalStoreTypeName;

            const string lstrSufixoMax = "(max)";

            if (lstrStoreTypeName.EndsWith(lstrSufixoMax, StringComparison.Ordinal))
                lstrStoreTypeName = lstrStoreTypeName.Substring(0, lstrStoreTypeName.Length - lstrSufixoMax.Length) + lstrSufixoMax;

            switch (lstrOriginalStoreTypeName.ToLowerInvariant())
            {
                case "decimal":
                case "numeric":
                    lstrStoreTypeName += "(" + (propModeloPropriedade.Precision ?? pintDefaultPrecisaoNumerica)
                                     + ", " + (propModeloPropriedade.Scale ?? pintDefaultEscala) + ")";
                    break;
                case "datetime":
                case "time":
                    lstrStoreTypeName += "(" + (propModeloPropriedade.Precision ?? pbytDefaultPrecisaoTempo) + ")";
                    break;
                case "blob":
                case "varchar2":
                case "varchar":
                case "char":
                case "nvarchar":
                case "nvarchar2":
                    lstrStoreTypeName += "(" + (propModeloPropriedade.MaxLength ?? pintDefaultStringMaxLength) + ")";
                    break;
            }

            return lstrStoreTypeName;
        }

        protected void ComandoSQL(string strInstrucaoSQL, bool blnSuprimeTransacao = false)
        {
            plstComandos.Add(new MigrationStatement
            {
                Sql = strInstrucaoSQL,
                SuppressTransaction = blnSuprimeTransacao
            });
        }

        protected void ComandoSQL(IndentedTextWriter writer)
        {
            ComandoSQL(writer.InnerWriter.ToString());
        }


        protected static IndentedTextWriter TextWriter()
        {
            return new IndentedTextWriter(new StringWriter(CultureInfo.InvariantCulture));
        }

        private static string RemoveDBO(string strTexto)
        {
            return strTexto.Replace("dbo.", string.Empty);
        }

        private void GeraComandos(IEnumerable<MigrationOperation> lstOperacoesMigrations)
        {
            foreach (dynamic ldynOperacao in lstOperacoesMigrations)
                Generate(ldynOperacao);
        }


        private void InicializaServicosProvider(string strManifestoProvider)
        {
            using (var lconConexao = CreateConnection())
            {
                pprovProviderManifest = DbProviderServices
                    .GetProviderServices(lconConexao)
                    .GetProviderManifest(strManifestoProvider);
            }
        }

        protected virtual DbConnection CreateConnection()
        {
            return new SQLiteConnection();
        }

        private void GeraComandoCriacaoTabela(CreateTableOperation opeCriacaoTabela, IndentedTextWriter textWriter)
        {

            textWriter.WriteLine("CREATE TABLE " + RemoveDBO(opeCriacaoTabela.Name) + " (");
            textWriter.Indent++;

            for (int i = 0; i < opeCriacaoTabela.Columns.Count; i++)
            {
                ColumnModel lcmDadosColuna = opeCriacaoTabela.Columns.ToList()[i];
                Generate(lcmDadosColuna, textWriter, opeCriacaoTabela.PrimaryKey);

                if (i < opeCriacaoTabela.Columns.Count - 1)
                    textWriter.WriteLine(",");
            }

            if ((opeCriacaoTabela.PrimaryKey != null) && !pblnGerouPrimaryKey)
            {
                textWriter.WriteLine(",");
                textWriter.Write("CONSTRAINT ");
                textWriter.Write(RemoveDBO(opeCriacaoTabela.PrimaryKey.Name));
                textWriter.Write(" PRIMARY KEY ");
                textWriter.Write("(");

                for (int li = 0; li < opeCriacaoTabela.PrimaryKey.Columns.Count; li++)
                {
                    var lstrNomeColuna = opeCriacaoTabela.PrimaryKey.Columns[li];

                    textWriter.Write(lstrNomeColuna);

                    if (li < opeCriacaoTabela.PrimaryKey.Columns.Count - 1)
                        textWriter.WriteLine(",");
                }

                textWriter.WriteLine(")");
            }
            else
            {
                textWriter.WriteLine();
            }

            textWriter.Indent--;
            textWriter.Write(")");
        }

        #endregion

    }
}

Connection string for SQLite with Entity Framework code-first approach, >> No MigrationSqlGenerator found for provider 'System.Data.SQLite'. Use the SetSqlGenerator method in the target migrations configuration  However, as we all know, the Sqlite driver for Entity Framework doesn’t support Migration. When we make changes to our value objects, we have to update the database ourselves outside of the application, be sure that everything correct before connecting our new version to the updated database.

I think we can use the same concept of Android for making a simple Migration engine for SQLite. This post shows that concept. Of course we don't have any working MigrationSqlGenerator but that concept is reliable und useful.

Entity Framework MigrationSqlGenerator for SQLite, is there a MigrationSqlGenerator for SQLite to use with entity framework? I only found one from devart which is commercial. No MigrationSqlGenerator found for​  SQLite is one of cheapest choice to implement the Relational Database (RDB), that my reason to change from SQL Server to SQLite instead but there are many constraint indeed. run this snippet to…

I don't know of any for SQLite, but if you were to try to create one as others have suggested, you could use this open source project to start with. Or you might find this will suffice on its own?

http://www.codeproject.com/Articles/32977/Upgrade-framework-for-SQLite-databases

Experiments with SQLite – Gallery Server, SQLite'. Make sure the provider is registered in the 'entityFramework' section of there is no freely available MigrationSqlGenerator for SQLite. Migrations for Entity Framework 6 SQLite provider. Limitations: Relationships are not enforced with constraints; There can be only one identity column per table and will be created as integer and primary key (other primary keys will be ignored) How to use it. Download the library (using NuGet) Create a migration configuration

c#, migrationsqlgenerator sqlite use entity framework? found 1 devart commercial. no migrationsqlgenerator found provider 'system.data.sqlite'. Microsoft.EntityFrameworkCore.Sqlite database provider allows Entity Framework Core to be used with to be used with SQLite. The provider is maintained as part of the Entity Framework Core Project. How to Use SQLite Provider. To use SQLite database provider, the first step is to install Microsoft.EntityFrameworkCore.Sqlite NuGet package. Let's consider a simple model which contains three entities.

Entity Framework Code-First Migrations support for Oracle, MySQL , Entity Framework Code-First Migrations support for Oracle, MySQL, PostgreSQL and SQLite. February 13th, 2012. ADO.NET EF providers Devart dotConnect for  >> No MigrationSqlGenerator found for provider 'System.Data.SQLite'. Use the SetSqlGenerator method in the target migrations configuration class to register additional SQL generators. You have to contact to author of SQLite provider to check if there is a code first migration project for EF. Or maybe you could create a new one by yourself.

sqlite-provider | Entity Framework sqlite-provider, Entity Framework Extensions SQLite Provider. SQLite is a software library that implements a self-contained, serverless, zero-configuration, transactional SQL  [InvalidOperationException: No Entity Framework provider found for the ADO.NET provider with invariant name ‘System.Data.SQLite’. Make sure the provider is registered in the ‘entityFramework’ section of the application config file] This line could be missing in your configuration file (inside <providers>)

Comments
  • As I know only one way to communicate with SQLite from C# is to use sqlite-net
  • the communication is no problem. But for a migration-worklfow entity framework needs a MigrationSqlGenerator which is not delivered with the sqlite library
  • Here is one version being worked on: github.com/msallin/SQLiteCodeFirst/issues/4
  • I tried to start a custom MigrationSqlGenerator but that is not as trivial as you said... :-) I don't know if I really build this MigrationSqlGenerator or if I run self written sql-querys by hand on startup which is faster to realize... if anybody has a SQLite MigrationSqlGenerator I would take it... Devarts free dotConnect doesn't support migration
  • I know it's not trivial :) but that's the best I have - there seem to be no other solutions.
  • The link is broken. Can you please update it or post the code?
  • Ok @RobotMess I edited the post and sent the file to Google Drive
  • @RobotMess I posted it inline. Looks like SO has a 30K character limit and the code was over 32K characters, so I deleted the code comments only and brought it down to under 30K total.
  • I'm using this class and it works good, but only the first time. When I alter my model and want to add a new migration using Add-Migration I get the msg I have pending migrations. I also don't see the MigrationsHistory table in my SQLite file. My current workaround is to drop the table and delete the migration file and run from scratch.