나는 이것을 잃어 버렸다.
엔티티 프레임 워크 (4.1.3) 코드 첫 번째 접근 방식에 대한 클래스를 정의했습니다. 내가 씨앗을 시작할 때까지 모든 것이 잘되었습니다 (테이블 등을 만들고있었습니다).
이제 내가 할 때
Add-Migration "remigrate" ; Update-Database;
패키지 콘솔에 “하나 이상의 엔터티에 대한 유효성 검사에 실패했습니다. 자세한 내용은 ‘EntityValidationErrors’속성을 참조하십시오.”라는 오류가 발생합니다.
내 Seed () 메서드에 중단 점이 있지만 프로젝트가 실행되고 있지 않을 때 콘솔에서이를 실행하기 때문에 세부 정보를 얻는 방법에 대한 단서가 없습니다 (PS-스레드 유효성 검사에 실패했습니다. Entity Framework 를 사용하여 SQL Server 데이터베이스에 변경 사항을 저장하는 동안 하나 이상의 엔터티에 대해 속성을 볼 수있는 방법을 보여줍니다.)
메서드 호출 직후에 반환하면 오류가 사라지기 때문에 Seed () 메서드에 문제가 있음을 알고 있습니다. 그렇다면 유효성 검사 오류가 무엇인지 알 수 있도록 중단 점을 어떻게 설정합니까? 졌어요 아니면 너겟 콘솔에서 추적 할 수있는 다른 방법이 있습니까 ??
답변
최근에도 이것에 짜증이났습니다. Seed 메서드의 Configuration 클래스에 래퍼 함수를 넣어서 수정하고 SaveChanges
대신 호출을 내 함수 호출로 대체 했습니다. 이 함수는 단순히 EntityValidationErrors
콜렉션 내의 오류를 열거 하고 예외 메시지가 개별 문제점을 나열하는 예외를 다시 발생시킵니다. 그러면 NuGet 패키지 관리자 콘솔에 출력이 표시됩니다.
코드는 다음과 같습니다.
/// <summary>
/// Wrapper for SaveChanges adding the Validation Messages to the generated exception
/// </summary>
/// <param name="context">The context.</param>
private void SaveChanges(DbContext context) {
try {
context.SaveChanges();
} catch (DbEntityValidationException ex) {
StringBuilder sb = new StringBuilder();
foreach (var failure in ex.EntityValidationErrors) {
sb.AppendFormat("{0} failed validation\n", failure.Entry.Entity.GetType());
foreach (var error in failure.ValidationErrors) {
sb.AppendFormat("- {0} : {1}", error.PropertyName, error.ErrorMessage);
sb.AppendLine();
}
}
throw new DbEntityValidationException(
"Entity Validation Failed - errors follow:\n" +
sb.ToString(), ex
); // Add the original exception as the innerException
}
}
seed 메소드에서 호출을 context.SaveChanges()
로 바꾸 SaveChanges(context)
십시오.
답변
부분 클래스 정의로 DBContext 클래스를 이미 확장하십시오!
DbContext의 클래스 정의를 보면 다음과 같습니다.
// DatabaseContext.cs -- This file is auto generated and thus shouldn't be changed.
public partial class [DatabaseContextName] : DbContext { ... }
따라서 다른 파일에서 동일한 정의를 작성하고 원하는 부분을 대체 할 수 있습니다.
// partialDatabaseContext.cs -- you can safely make changes
// that will not be overwritten in here.
public partial class [DatabaseContextName] : DbContext { // Override defaults here }
부분 클래스와 전체 아이디어는 당신이 알 –did DbContext이 부분 그 수업은 당신이 생성 된 클래스를 확장 (또는 여러 개의 파일로 클래스를 구성하는) 우리의 경우 우리는 또한 할 수 있다는 것입니다 오버라이드 (override) SaveChanges를의 방법을 DbContext에 추가하는 부분 클래스 내에서 .
이 방법으로 모든 기존 DbContext / SaveChanges 호출에서 오류 디버깅 정보를 얻을 수 있으며 시드 코드 또는 개발 코드를 전혀 변경할 필요가 없습니다.
이것은 (내가 할 것 인 것이다 참고 차이가 난 그냥 저작 우리 자신에 SaveChanges를 메소드를 오버라이드 (override)이다 DbContext에게 부분 클래스, NOT 생성 된 하나 ). 또한 부분 클래스가 올바른 네임 스페이스를 사용하는지 확인하십시오. 그렇지 않으면 벽에 머리가 부딪 칠 것입니다.
public partial class Database : DbContext
{
public override int SaveChanges()
{
try
{
return base.SaveChanges();
}
catch (DbEntityValidationException ex)
{
var sb = new StringBuilder();
foreach (var failure in ex.EntityValidationErrors)
{
sb.AppendFormat("{0} failed validation\n", failure.Entry.Entity.GetType());
foreach (var error in failure.ValidationErrors)
{
sb.AppendFormat("- {0} : {1}", error.PropertyName, error.ErrorMessage);
sb.AppendLine();
}
}
throw new DbEntityValidationException(
"Entity Validation Failed - errors follow:\n" +
sb.ToString(), ex
); // Add the original exception as the innerException
}
}
}
답변
Richards 답변을 확장 방법으로 변환했습니다.
public static int SaveChangesWithErrors(this DbContext context)
{
try
{
return context.SaveChanges();
}
catch (DbEntityValidationException ex)
{
StringBuilder sb = new StringBuilder();
foreach (var failure in ex.EntityValidationErrors)
{
sb.AppendFormat("{0} failed validation\n", failure.Entry.Entity.GetType());
foreach (var error in failure.ValidationErrors)
{
sb.AppendFormat("- {0} : {1}", error.PropertyName, error.ErrorMessage);
sb.AppendLine();
}
}
throw new DbEntityValidationException(
"Entity Validation Failed - errors follow:\n" +
sb.ToString(), ex
); // Add the original exception as the innerException
}
}
이런 식으로 전화하십시오 :
context.SaveChangesWithErrors();
답변
craigvl의 버전을 C #으로 변환했는데 context.SaveChanges (); 다음과 같이 나를 위해 작동합니다.
try
{
byte[] bytes = System.IO.File.ReadAllBytes(@"C:\Users\sheph_000\Desktop\Rawr.png");
Console.WriteLine(bytes);
context.BeverageTypes.AddOrUpdate(
x => x.Name,
new AATPos.DAL.Entities.BeverageType { ID = 1, Name = "Sodas" }
);
context.Beverages.AddOrUpdate(
x => x.Name,
new AATPos.DAL.Entities.Beverage { ID = 1, Name = "Coke", BeverageTypeID = 1, ImageData = bytes, IsStocked = true, StockLevel = 10, Price = 10.00M, ImageMimeType = "test" },
new AATPos.DAL.Entities.Beverage { ID = 2, Name = "Fanta", BeverageTypeID = 1, ImageData = bytes, IsStocked = true, StockLevel = 10, Price = 10.00M, ImageMimeType = "test" },
new AATPos.DAL.Entities.Beverage { ID = 3, Name = "Sprite", BeverageTypeID = 1, ImageData = bytes, IsStocked = true, StockLevel = 10, Price = 10.00M, ImageMimeType = "test" },
new AATPos.DAL.Entities.Beverage { ID = 4, Name = "Cream Soda", BeverageTypeID = 1, ImageData = bytes, IsStocked = true, StockLevel = 10, Price = 10.00M, ImageMimeType = "test" },
new AATPos.DAL.Entities.Beverage { ID = 5, Name = "Pepsi", BeverageTypeID = 1, ImageData = bytes, IsStocked = true, StockLevel = 10, Price = 10.00M, ImageMimeType = "test" }
);
context.SaveChanges();
}
catch (System.Data.Entity.Validation.DbEntityValidationException ex)
{
var sb = new System.Text.StringBuilder();
foreach (var failure in ex.EntityValidationErrors)
{
sb.AppendFormat("{0} failed validation", failure.Entry.Entity.GetType());
foreach (var error in failure.ValidationErrors)
{
sb.AppendFormat("- {0} : {1}", error.PropertyName, error.ErrorMessage);
sb.AppendLine();
}
}
throw new Exception(sb.ToString());
}
답변
아래의 올바른 경로를 찾아 주셔서 감사합니다. (같은 문제가 있음) 마이그레이션 구성 시드 방법에서 나에게 도움이되는 래퍼가없는 대안입니다.
Protected Overrides Sub Seed(context As NotificationContext)
Try
context.System.AddOrUpdate(
Function(c) c.SystemName,
New E_NotificationSystem() With {.SystemName = "System1"},
New E_NotificationSystem() With {.SystemName = "System2"},
New E_NotificationSystem() With {.SystemName = "System3"})
context.SaveChanges()
Catch ex As DbEntityValidationException
Dim sb As New StringBuilder
For Each failure In ex.EntityValidationErrors
sb.AppendFormat("{0} failed validation" & vbLf, failure.Entry.Entity.[GetType]())
For Each [error] In failure.ValidationErrors
sb.AppendFormat("- {0} : {1}", [error].PropertyName, [error].ErrorMessage)
sb.AppendLine()
Next
Next
Throw New Exception(sb.ToString())
End Try
End Sub
그런 다음 패키지 관리자 콘솔에서 예외를 볼 수있었습니다. 이것이 누군가를 돕기를 바랍니다.
답변
I Also had same model validation problem but successfully catch by myself after lot of thinking;
I use reverse engineering method to catch the problem out of Over 80 + Model Classes;
1> Made copy of dbcontext, changing the name (I add "1" at end and make respective changes in class constructor and initialization etc.
Old:
>public class AppDb : IdentityDbContext<ApplicationUser>
>
> {
> public AppDb(): base("DefaultConnection", throwIfV1Schema: false)
> {
>
> }
>
> public static AppDb Create()
>{
>return new AppDb();
>}
**New:**
>public class AppDb1 : IdentityDbContext<ApplicationUser>
>{
>public AppDb1()
>: base("DefaultConnection", throwIfV1Schema: false)
>{
>}
>
>public static AppDb1 Create()
> {
> return new AppDb1();
> }`
...
2> Make changes to Codefirst Migration Configuration from Old DbContext to my new Context.
> internal sealed class Configuration :
> DbMigrationsConfiguration<DAL.AppDb1> { public Configuration() {
> AutomaticMigrationsEnabled = false; } protected override void
> Seed(DAL.AppDb1 context) {`
3> Comment the Dbsets in new DbContext which was doubt.
4> Apply update migration if succeeded the probelm lye in Commented section.
5> if not then commented section is clear of bug clear.
6> repeat the (4) until found the right place of bug.
7> Happy Codding