Oracle code first DropCreateDatabaseIfModelChanges and DropCreateDatabaseAlways

Discussion of open issues, suggestions and bugs regarding Entity Framework support in ADO.NET Data providers
Post Reply
Amplus
Posts: 3
Joined: Wed 26 Sep 2012 21:56

Oracle code first DropCreateDatabaseIfModelChanges and DropCreateDatabaseAlways

Post by Amplus » Thu 27 Sep 2012 00:34

Greetings,

I'm experimenting with Devart and EF 5 (although using VS 2010). I'm unable to get DropCreateDatabaseIfModelChanges or DropCreateDatabaseAlways to work. The database is created with no problems the first time around with sequences, triggers, primary and foreign keys, but when it is supposed to be dropped it gives me an error: ORA-00955: name is already used by an existing object. Isn't this supposed to drop all user objects in the schema for me? Am I missing something? I'm using Oracle 11g express locally

Context:

Code: Select all

using System.Data.Entity;
using Devart.Data.Oracle;
using Devart.Data.Oracle.Entity.Configuration;

namespace CodeFirstConsole.EF
{
    public class Context : DbContext
    {
        public Context() : this(ConfigurationManager.ConnectionStrings["Model1Container"].ConnectionString)
        {
            
        }

        public Context(string connectionString) : base(new OracleConnection(connectionString), true)
        {
            var config = OracleEntityProviderConfig.Instance;
            config.Workarounds.ColumnTypeCasingConventionCompatibility = true;
        }

        protected override void OnModelCreating(DbModelBuilder modelBuilder)
        {
            base.OnModelCreating(modelBuilder);
        }

        public DbSet<Country> Countries { get; set; }
    }
}
One class in the project

Code: Select all

    
public class Country
    {
        [Key(),DatabaseGenerated(DatabaseGeneratedOption.Identity)]
        public int CountryID { get; set; }
        public string CountryName { get; set; }
        public int RegionID { get; set; }
        public string Continent { get; set; }
        //public Language Language { get; set; }
    }
The console test program:

Code: Select all

    class Program
    {
        static void Main(string[] args)
        {
            Database.SetInitializer(new Initializer());
            try
            {
                using (var ctx = new Context(ConfigurationManager.ConnectionStrings["Model1Container"].ConnectionString))
                {
                    var data = ctx.Countries.ToList();
                    Console.WriteLine(string.Format("Got countries from Oracle DB.  Total count is {0}", data.Count));
                    ctx.Countries.Add(new Country { CountryName = "Chile", RegionID = 2, Continent = "South America" });
                    ctx.SaveChanges();
                }
            }
            catch (Exception e)
            {
                Console.Write(e.ToString());
            }
            Console.Read();

        }
    }
Initializer:

Code: Select all

    public class Initializer : DropCreateDatabaseAlways<Context>
    {
        protected override void Seed(Context context)
        {
            base.Seed(context);
        }
    }
And finally App.config:

Code: Select all

<?xml version="1.0" encoding="utf-8"?>
<configuration>
  <configSections>
    <!-- For more information on Entity Framework configuration, visit http://go.microsoft.com/fwlink/?LinkID=237468 -->
    <section name="entityFramework" type="System.Data.Entity.Internal.ConfigFile.EntityFrameworkSection, EntityFramework, Version=4.4.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" requirePermission="false" />
  </configSections>
  <entityFramework>
    <defaultConnectionFactory type="System.Data.Entity.Infrastructure.SqlConnectionFactory, EntityFramework" />
  </entityFramework>
  <connectionStrings>
    <add name="Model1Container" connectionString="DATA SOURCE=localhost;PASSWORD=codefirst;PERSIST SECURITY INFO=True;USER ID=codefirst" providerName="System.Data.EntityClient" />
  </connectionStrings>
</configuration>
I have another test project set up with quite complex class model with inheritance and relationships. The db is successfully created in that case the first time around but when I run it the second time I get the following error:

Devart.Data.Oracle.OracleException (0x80004005): ORA-02449: unique/primary keys in table referenced by foreign keys

If I specify that I want to drop and recreate the database do I have to worry about foreign key constraints?

In both projects I reference the following assemblies:
  • C:\Program Files (x86)\Common Files\Devart\dotConnect\5.0\Net2\Common\Devart.Data.Oracle.dll (version 7.2.77.0)
  • C:\Program Files (x86)\Devart\dotConnect\Oracle\Entity\EF4\Devart.Data.Oracle.Entity.dll (version 7.2.77.0)
  • C:\Program Files (x86)\Devart\dotConnect\Oracle\Entity\EF4\Devart.Data.Oracle.Entity.Migrations.dll (version 7.2.77.0)
  • Installed EntityFramework 5 via Nuget
All help would be greatly appreciated.

Shalex
Site Admin
Posts: 9543
Joined: Thu 14 Aug 2008 12:44

Re: Oracle code first DropCreateDatabaseIfModelChanges and DropCreateDatabaseAlways

Post by Shalex » Thu 27 Sep 2012 12:50

Amplus wrote:I'm unable to get DropCreateDatabaseIfModelChanges or DropCreateDatabaseAlways to work.
Please refer to http://forums.devart.com/viewtopic.php?t=24861 (dotConnect for Oracle behaves correspondingly).
Amplus wrote:I have another test project set up with quite complex class model with inheritance and relationships. The db is successfully created in that case the first time around but when I run it the second time I get the following error:
Devart.Data.Oracle.OracleException (0x80004005): ORA-02449: unique/primary keys in table referenced by foreign keys
If I specify that I want to drop and recreate the database do I have to worry about foreign key constraints?
If the options from http://forums.devart.com/viewtopic.php?t=24861 do not help, please send us a small test project to reproduce the issue in our environment.

Amplus
Posts: 3
Joined: Wed 26 Sep 2012 21:56

Re: Oracle code first DropCreateDatabaseIfModelChanges and DropCreateDatabaseAlways

Post by Amplus » Thu 27 Sep 2012 15:59

Thanks for the reply Shalex! I got this working by adding this line:

Code: Select all

config.DatabaseScript.Schema.DeleteDatabaseBehaviour = DeleteDatabaseBehaviour.AllSchemaObjects;
However when I used this option:

Code: Select all

config.DatabaseScript.Schema.DeleteDatabaseBehaviour = DeleteDatabaseBehaviour.Schema;
I got an error:

System.FormatException: Input string was not in a correct format.
at System.Text.StringBuilder.AppendFormat(IFormatProvider provider, String fo
rmat, Object[] args)
at Devart.Common.Entity.a4.b(String A_0)
at Devart.Data.Oracle.Entity.y.b(String A_0)
at Devart.Common.Entity.a4.a(bj A_0)
at Devart.Common.Entity.bj.a(bd A_0)
at Devart.Common.Entity.a4.a(List`1 A_0)
at Devart.Common.Entity.cf.aa()
at Devart.Data.Oracle.Entity.OracleEntityProviderServices.DbDeleteDatabase(Db
Connection connection, Nullable`1 commandTimeout, StoreItemCollection storeItemC
ollection)
at System.Data.Objects.ObjectContext.DeleteDatabase()
at System.Data.Entity.Internal.DatabaseOperations.DeleteIfExists(ObjectContex
t objectContext)
at System.Data.Entity.Database.Delete()
at System.Data.Entity.DropCreateDatabaseIfModelChanges`1.InitializeDatabase(T
Context context)
at System.Data.Entity.Database.<>c__DisplayClass2`1.<SetInitializerInternal>b
__0(DbContext c)
at System.Data.Entity.Internal.InternalContext.<>c__DisplayClass8.<PerformDat
abaseInitialization>b__6()
at System.Data.Entity.Internal.InternalContext.PerformInitializationAction(Ac
tion action)
at System.Data.Entity.Internal.InternalContext.PerformDatabaseInitialization(
)
at System.Data.Entity.Internal.LazyInternalContext.<InitializeDatabase>b__4(I
nternalContext c)
at System.Data.Entity.Internal.RetryAction`1.PerformAction(TInput input)
at System.Data.Entity.Internal.LazyInternalContext.InitializeDatabaseAction(A
ction`1 action)
at System.Data.Entity.Internal.LazyInternalContext.InitializeDatabase()
at System.Data.Entity.Internal.InternalContext.Initialize()
at System.Data.Entity.Internal.InternalContext.GetEntitySetAndBaseTypeForType
(Type entityType)
at System.Data.Entity.Internal.Linq.InternalSet`1.Initialize()
at System.Data.Entity.Internal.Linq.InternalSet`1.GetEnumerator()
at System.Data.Entity.Infrastructure.DbQuery`1.System.Collections.Generic.IEn
umerable<TResult>.GetEnumerator()
at System.Collections.Generic.List`1..ctor(IEnumerable`1 collection)
at System.Linq.Enumerable.ToList[TSource](IEnumerable`1 source)
at CodeFirstConsole.Program.Main(String[] args) in C:\Umsoknarkerfi\CodeFirst
Console\CodeFirstConsole\Program.cs:line 20

Shalex
Site Admin
Posts: 9543
Joined: Thu 14 Aug 2008 12:44

Re: Oracle code first DropCreateDatabaseIfModelChanges and DropCreateDatabaseAlways

Post by Shalex » Tue 02 Oct 2012 09:10

We have reproduced the problem with DeleteDatabaseBehaviour.Schema and dotConnect for Oracle. We will post here when the issue is fixed.

angleblue63
Posts: 1
Joined: Wed 03 Oct 2012 12:41

Re: Oracle code first DropCreateDatabaseIfModelChanges and DropCreateDatabaseAlways

Post by angleblue63 » Wed 03 Oct 2012 12:45

If I specify that I want to drop and recreate the database do I have to worry about foreign key constraints?

Shalex
Site Admin
Posts: 9543
Joined: Thu 14 Aug 2008 12:44

Re: Oracle code first DropCreateDatabaseIfModelChanges and DropCreateDatabaseAlways

Post by Shalex » Fri 05 Oct 2012 14:19

DeleteDatabaseBehaviour.AllSchemaObjects drops objects taking into account foreign key constraints and then recreates schema objects.

Shalex
Site Admin
Posts: 9543
Joined: Thu 14 Aug 2008 12:44

Re: Oracle code first DropCreateDatabaseIfModelChanges and DropCreateDatabaseAlways

Post by Shalex » Thu 25 Oct 2012 07:06

  • The bug with DropDatabase() and CreateDatabase(), when DeleteDatabaseBehaviour.ModelObjectsOnly is used, in EF v4.3 and higher is fixed
  • The bug with DropDatabase() and CreateDatabase(), when IgnoreDboSchemaName option is enabled and DeleteDatabaseBehaviour.Schema is used, in EF v4.3 and higher is fixed
These fixes are available in the latest (7.2.104) version of dotConnect for Oracle: http://www.devart.com/dotconnect/oracle ... story.html.

Post Reply