7

I am working with oracles odp.net core beta 3. Specifically, The dll is Oracle.ManagedDataAccess.Core.2.12.0-beta3. The project is to create a web api that sits on top of an oracle instance.

My question - Is the command "Scaffold-DBContext" supported with this provider. If so what am I doing wrong... I've made the attempt using a connection string similar to the following.

Data Source={databasename}/{TNS}.domain.local; User ID={UserName};Password={Password};

And the actual command in the Package Manager terminal

Scaffold-DbContext Data Source={databasename}/{TNS}.domain.local; User ID={UserName};Password={Password};" Oracle.ManagedDataAccess -OutputDir Models -Tables {TableName}

I get the following error which sugests it cannot fond a DesignTimeServiceAttribute in the provider assembly.

I also have Microsoft.EntityFrameworkCore.Tools (2.2.0) referenced which includes the design tools.

ERROR

    System.InvalidOperationException: Unable to find expected assembly attribute named DesignTimeProviderServicesAttribute in provider assembly Oracle.ManagedDataAccess. This attribute is required to identify the class which acts as the design-time service provider factory.
   at Microsoft.EntityFrameworkCore.Design.Internal.DesignTimeServicesBuilder.ConfigureProviderServices(String provider, IServiceCollection services, Boolean throwOnError)
   at Microsoft.EntityFrameworkCore.Design.Internal.DesignTimeServicesBuilder.Build(String provider)
   at Microsoft.EntityFrameworkCore.Design.Internal.DatabaseOperations.ScaffoldContext(String provider, String connectionString, String outputDir, String outputContextDir, String dbContextClassName, IEnumerable`1 schemas, IEnumerable`1 tables, Boolean useDataAnnotations, Boolean overwriteFiles, Boolean useDatabaseNames)
   at Microsoft.EntityFrameworkCore.Design.OperationExecutor.ScaffoldContextImpl(String provider, String connectionString, String outputDir, String outputDbContextDir, String dbContextClassName, IEnumerable`1 schemaFilters, IEnumerable`1 tableFilters, Boolean useDataAnnotations, Boolean overwriteFiles, Boolean useDatabaseNames)
   at Microsoft.EntityFrameworkCore.Design.OperationExecutor.ScaffoldContext.<>c__DisplayClass0_1.<.ctor>b__0()
   at Microsoft.EntityFrameworkCore.Design.OperationExecutor.OperationBase.<>c__DisplayClass3_0`1.<Execute>b__0()
   at Microsoft.EntityFrameworkCore.Design.OperationExecutor.OperationBase.Execute(Action action)
LCaraway
  • 1,257
  • 3
  • 20
  • 48
  • This has nothing to do with the provider. Since EF Core uses DI now, it needs a project to "run" to satisfy its dependencies. Most likely, you have your context in a class library, which you cannot migrate against unless you provide an implementation of `IDesignTimeDbContextFactory`. See: https://learn.microsoft.com/en-us/ef/core/miscellaneous/cli/dbcontext-creation#from-a-design-time-factory – Chris Pratt Sep 11 '18 at 16:39
  • I'm attempting to us the "Scaffold-DbContext" command to create the context itself. How do I ensure it can implement `IDesignTimeContextFactory`? – LCaraway Sep 11 '18 at 18:00
  • *You* need to implement `IDesignTimeDbContextFactory`. The command is fairly inconsequential at this point. *Any* EF command is going to need to instantiate an instance of your context, which it cannot do unless your context is in a startup project or your implement this interface. See the docs I linked to. – Chris Pratt Sep 11 '18 at 18:14
  • Ok, I have a stronger grasp on what you are saying now. Any thoughts as to what to use for the OptionsBuilder component. Is there something like `options.UseOracle` or `options.UseODPNET` ?? Do I need to build one mself? – LCaraway Sep 13 '18 at 14:48
  • I think there is. It comes from the provider itself, so once you've installed the appropriate package, you should get whatever extension method you need there. – Chris Pratt Sep 13 '18 at 14:50

4 Answers4

8

I experienced the problems that you experienced, even after downloading the ODP.NET Core driver for production (2.18.3, released on 20-Sept-2018 and available from nuget at https://www.nuget.org/packages/Oracle.ManagedDataAccess.Core/).

I contacted the Oracle community for help. A kind soul answered that there's another piece of the puzzle if we want to have a ready access to goodness such as "UseOracle." It is the Oracle provider for the Entity Framework Core. See the thread at https://community.oracle.com/thread/4180739.

The only other way to use it, to my knowledge and based on his answer, is the way described in the Oracle Help Center, Getting Started with ODP.NET Core (https://www.oracle.com/webfolder/technetwork/tutorials/obe/db/dotnet/ODPNET_Core_get_started/index.html).

Elsa
  • 96
  • 1
  • 4
  • 1
    I too discovered this. I was able to get my solution up and running by bypassing Entity framework completely and went with using `dapper`. I must say I have been very satisfied with it though it lacks some of the helpful tooling is packaged with EF – LCaraway Oct 25 '18 at 19:25
5

I managed to scaffold it using

scaffold-dbcontext "Data Source=(DESCRIPTION=(ADDRESS=(PROTOCOL=TCP)(HOST=1.1.1.1)(PORT=1521))(CONNECT_DATA=(SERVICE_NAME=MYdb)));Persist Security Info=True;User Id=MYUSER;Password=mypass;" Oracle.EntityFrameworkCore

But it's an unusable mess. tons of errors

Could not scaffold the foreign key 'XX.TABLE1(USER_ID,USER_ID)'. A key for 'ID,ID' was not found in the principal entity type 'Aspnetusers'.

Seems like Dapper is my friend...

Toolkit
  • 10,779
  • 8
  • 59
  • 68
2

I scaffolded some tables using this:

Scaffold-DbContext "Data Source=myDatabase.example.com/servicename; User ID=username;Password=password;" Oracle.EntityFrameworkCore -OutputDir myModels -Tables FIRSTTABALE,SECONDTABLE

The table names must be in uppercase and Oracle EntityFrameworkCore version was 2.19.30.

The produced models were totally fine. Maybe it depends on the EF Core version or on specifying the table names.

volkit
  • 1,173
  • 14
  • 21
2

For oracle db use this into View->Other Windows->Package Manager Console:

Scaffold-DbContext "Data Source=(DESCRIPTION=(ADDRESS=(PROTOCOL=TCP)(HOST=localhost)(PORT={your port}))(CONNECT_DATA=(SERVER=DEDICATED)(SERVICE_NAME={db SID})));User ID={username};Password={pass};Persist Security Info=True" Oracle.EntityFrameworkCore -Tables TABLE1, TABLE2, ..., TABLEK -OutputDir Models -force