How to get entity validation errors in Entity Framework Core 3.1.31 - entity-framework-core

I'm trying to migrate an older EF6 project to a NetStandard 2.0 EF Core 3.1.31 project. One of the final issues I'm running into is catching and reporting entity validation errors. This is what we had previously.
catch (DbEntityValidationException dbexc)
{
var sb = new StringBuilder();
foreach (var eve in dbexc.EntityValidationErrors)
{
sb.AppendLine($"Entity of type {eve.Entry.Entity.GetType().Name} in state {eve.Entry.State} has the following validation errors:<br />");
foreach (var ve in eve.ValidationErrors)
{
sb.AppendLine($" - Property: {ve.PropertyName}, Error: {ve.ErrorMessage}<br />");
}
}
retval.ErrorMessages.Add(sb.ToString());
}
I can't find clear direction on how to do something similiar in EF Core.

Related

ToListAsync() leads DbContext to crash using ef core

I am writing a simple query to get all the data from a table in a .net core project. When using ToListAsync(), the process crashed without any exceptions thrown. And after changing to ToList(), the process run successfully. I am really curious about the reason behind.
The EF-Core version is 2.2.6.
The same method using TolistAsync(), failed.
public async Task<ICollection<TariffType>> GetAllTariffTypes()
{
using(var dbContext = _dbContextFactory.CreateDbContext(_appConfig.DbContextConnectionString))
{
var tariffTypes = await dbContext.TariffType.ToListAsync();
return tariffTypes;
}
}
The method using ToList(), it worked.
public ICollection<TariffType> GetAllTariffTypes()
{
using(var dbContext = _dbContextFactory.CreateDbContext(_appConfig.DbContextConnectionString))
{
var tariffTypes = dbContext.TariffType.ToList();
return tariffTypes;
}
}

Entity Framework Core 1.0 CurrentValues.SetValues() does not exist

I'm attempting to update an entity and its related child entities using Entity Framework Core 1.0 RC 1, where the entities are detached from DbContext. I've done this previously using a solution similar to the one described in this answer.
However, it seems that we are no longer able to do the following using Entity Framework 7:
DbContext.Entry(existingPhoneNumber).CurrentValues.SetValues();
Visual Studio complains that:
EntityEntry does not contain a definition for 'CurrentValues'
etc...
I presume this means that this has not (yet?) been implemented for EF Core 1.0? Apart from manually updating the properties, is there any other solution?
As you have noticed, this API is not implemented yet in EF Core. See this work item: https://github.com/aspnet/EntityFramework/issues/1200
I know this is an old question but I ran into this issue today, and it appears it still isn't implemented in EF Core. So I wrote an extension method to use in the meantime that will update any object's properties with the matching values of any other object.
public static class EFUpdateProperties
{
public static TOrig UpdateProperties<TOrig, TDTO>(this TOrig original, TDTO dto)
{
var origProps = typeof(TOrig).GetProperties();
var dtoProps = typeof(TDTO).GetProperties();
foreach(PropertyInfo dtoProp in dtoProps)
{
origProps
.Where(origProp => origProp.Name == dtoProp.Name)
.Single()
.SetMethod.Invoke(original, new Object[]
{
dtoProp.GetMethod.Invoke(dto, null) });
}
);
return original;
}
}
Usage:
public async Task UpdateEntity(EditViewModel editDto)
{
// Get entry from context
var entry = await _context.Items.Where(p => p.ID == editDto.Id).FirstOrDefaultAsync();
// Update properties
entry.UpdateProperties(editDto);
// Save Changes
await _context.SaveChangesAsync();
}

MetadataWorkspaceExtensions.GetDbProviderManifest in Entity Framework 6.0

In EF 5, there was a T4 utility template named GenerateEDM.Utility.ttinclude that started with the following code:
internal DbProviderManifest GetDbProviderManifest(string providerInvariantName, string providerManifestToken)
{
DbProviderManifest providerManifest = null;
try
{
providerManifest = MetadataWorkspaceExtensions.GetDbProviderManifest(providerInvariantName, providerManifestToken);
}
Now I'm rewriting some of our EF5 code generation templates for EF6, and I cannot find the method MetadataWorkspaceExtensions.GetDbProviderManifest.
Where was this method moved to in Entity Framework 6.0?

Entity Framework 5 Generates SQL Referencing NotMapped Property

I just set about updating a project from Entity Framework 4.3.1 and .NET 4 to Entity Framework 5.0 and .NET 4.5. I updated the .NET version first, and ensured that I'm referencing EF 5.0.0.0 rather than the .NET 4 compatible 4.4.0.0.
I have a class structure like
public class MyBase
{
[NotMapped]
public bool MyProperty { get; set; }
}
public class MyDefinition : MyBase
{
// Some other properties
}
When I attempt to load some MyDefinition instances
using (MyContext ctx = new MyContext())
{
ctx.Configuration.AutoDetectChangesEnabled = false;
ctx.Configuration.LazyLoadingEnabled = false;
ctx.Configuration.ProxyCreationEnabled = false;
var defs = from def in ctx.MyDefinitions.AsNoTracking() select def;
foreach (MyDefinition def in defs) // <-- Exception here
{
// Do stuff
}
}
I get a SqlException
Invalid column name 'MyProperty'.
It is as if NotMapped is respected for purposes of determining whether the existing schema is valid, but the SELECT generated by EF 5 expects there to be a MyProperty column.
The base class and derived class are defined in different assemblies. Both assemblies were carefully checked to ensure they reference EF 5.0.0.0 and target .NET 4.5.
Intellisense claims that NotMapped is System.ComponentModel.DataAnnotations.Schema.NotMapped
How can I prevent EF 5 from selecting that non-existent column?
Add this
using System.ComponentModel.DataAnnotations.Schema
D'oh!
I also updated to VS 2012 today. Something unrelated broke with a post-build event, which caused an earlier version of the assembly containing the base class to be available to the derived class. Fixing the post build event resolved the issue.

How to catch Exceptions from System.Data namespace?

I started using Entity Framework 4.3.1 with code first approach.
I want to avoid application crash when database server is shut down or unavailable catching specific exceptions.
Imagine this short sample piece of code:
using (var db = new MyContext())
{
var people = new People();
db.People.AddObject(people);
db.SaveChanges();
}
When server is shut down, I receive ProviderIncompatibleException.
If I try to modify code catching ProviderIncompatibleException like this
using (var db = new MyContext())
{
try
{
var people = new People();
db.People.AddObject(people);
db.SaveChanges();
}
catch(ProviderIncopatibleException)
{
}
}
I receive compiler error "The type caught or thrown must be derived from System.Exception".
How can I catch most specific Exception using Entity framework?
Thank you for help.
There's a typo in the class name - you missed out an 'm' in Incompatible.
Try again with ProviderIncompatibleException