Recently, in one of my attempt to write an API application in .Net core with Entity Framework Core (Code First) approach, I got ran into a couple of errors.
When I was looking for articles which can help me to get these issues resolved, all the articles were referring to the samples where the DbContext was created in the startup project instead of the separate assembly.
In my sample, the Entity Framework models were defined in the separate class library. Hence those articles were not of very great help for me to resolve this error.
After spending a lot of time, I got to know the solution. This article is to cover what were those errors and how to resolve them.
For making it easier to understand, you can refer the source code – MyCodeCamp – published in my github repository.
If you are using .NET Core 3, then please refer my other blog article. This article explains how to make dotnet ef migrations command work.
The Problem
I created two projects :
- MyCodeCamp – A web application project for hosting the APIs
- MyCodeCamp.Data – A class library project where all the EF Core entity models are placed.
The “MyCodeCamp.Data” project will contain only the entity models which are corresponding to the tables which are required to be created in database. It will also contain the CampContext which is derived from DbContext.
First Error
Then I tried to create the initial migration by using below command.
dotnet ef migrations add First
Please note that these migration commands used in this article are executed on command prompt using .Net Core CLI. These commands are executed inside the class library project folder.
After running this command I got below error suggesting that the project cannot be executed directly. So the error was suggesting to either change the project type OR to specify –startup-project .
Startup project ‘MyCodeCamp.Data.csproj’ targets framework ‘.NETStandard’. There is no runtime associated with this framework, and projects targeting it cannot be executed directly. To use the Entity Framework Core .NET Command-line Tools with this project, add an executable project targeting .NET Core or .NET Framework that references this project, and set it as the startup project using –startup-project; or, update this project to cross-target .NET Core or .NET Framework. For more information on using the EF Core Tools with .NET Standard projects, see https://go.microsoft.com/fwlink/?linkid=2034781
Second Error
When I specified –startup-project and specified MyCodeCamp csproj file path as a value of that switch, I got another error (shown in red font):
dotnet ef migrations add First --startup-project ../MyCodeCamp.csproj
Unable to retrieve project metadata. Ensure it’s an MSBuild-based .NET Core project. If you’re using custom BaseIntermediateOutputPath or MSBuildProjectExtensionsPath values, Use the –msbuildprojectextensionspath option.
The Solution
After spending a lot of time, I understood, that somehow this class library should have some implementation which can be used for identifying the additional details about generating migrations.
I fixed this issue using below two steps:
Implement IDesignTimeDbContextFactory
This factory can be used to create instances of the derived DbContext classes.
Add AppSettings.json in the Class Library
Add appsettings.json file in the class library. Change the properties of this file so that it gets copied to the output directory. This file can contain the connection string.
Let’s apply migrations now !
Then I used below command to add the migrations. Of course, I had to specify the –startup-project switch and my startup project name.
dotnet ef migrations add First --startup-project ..\MyCodeCamp
Migrations were created successfully.
Let’s create database in SQL Server
Below command can be used to apply the migrations and create database in SQL Server.
dotnet ef database update --startup-project ..\MyCodeCamp
I hope you enjoyed reading this article and provided you sufficient information on resolving these errors. Please do comment and let me know your comments.
Tried this, but still getting:
DbContext was found in assembly ‘FeynmanGroup.Common.Authorization.Functions’. Ensure that you’re using the correct assembly and that the type is neither abstract nor generic.
I have 3 projects:
FeynmanGroup.Common.Authorization.Functions – The main app. .net core 3.1
FeynmanGroup.Repositories.Server.Authorization – Contains the DbContext. .net core 3.1
FeynmanGroup.Repositories.Client.Authorization.DataModel – Contains the data model. .net standard 2.1
Any idea?
I cannot guess any definite reason as there can be many root causes. Can you check this tread on GitHub for further help. This thread talks about making sure that right packages and right versions are in place.
https://github.com/dotnet/efcore/issues/10287
Nice post. for “IDesignTimeDbContextFactory” part. you don’t need “appsettings.json” , you may simply put connection string in the code. and put this method in #ifdef debug to strip it out of release build.
Hi Manoj,
I have a class library in which I have entity framework implemented.
I want to add this class library as a reference in my web API.
But when I do so, it’s giving me database context not found error.
Can you guide me with this pls?
As I don’t know the code, I cannot exactly tell you the root cause. But I can certainly give some pointers. You can check if the class library which you are using as a DbContext class implementation in it. If DbContext implementation is not present, then probably you are missing the dependency of that assembly. Other thing is, make sure that you have specified the correct connection string, which can be understood by the DbContext class.
if you can’t find namespace for ConfigurationBuilder in your class library – use Microsoft.Extensions.Configuration.Abstractions
Pingback: The Code Blogger - Entity Framework Core – Migration Tool and Commands