27

I have the following Action method inside my Asp.net mvc web application:-

[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult Create(SDJoin sdj, FormCollection formValues)
{
    Try
    {
        //code goes here
        repository.InsertOrUpdateSD(sdj.StorageDevice, User.Identity.Name, assetid);
        repository.Save();
    }
    catch (Exception ex)
    {
        //code goes here
    }
    PopulateViewBagData();
    return View(sdj);
}

which calls the following method:-

public void InsertOrUpdateSD(TMSStorageDevice sd, string username, long assetid)
{
    var resource = entities.Resources.AsNoTracking().SingleOrDefault(a => a.RESOURCEID == assetid);
    if (sd.TMSStorageDeviceID == default(int))
    {
        // New entity
        int technologyypeID = GetTechnologyTypeID("Storage Device");
        Technology technology = new Technology
        {
            IsDeleted = true,
            IsCompleted = false,
            TypeID = technologyypeID,
            Tag = "SD" + GetTagMaximumeNumber2(technologyypeID).ToString(),
            StartDate = DateTime.Now,
            IT360ID = assetid
        };

        InsertOrUpdateTechnology(technology);
        Save();

        sd.TMSStorageDeviceID = technology.TechnologyID;
        tms.TMSStorageDevices.Add(sd);
    }
}

My model class is as follow:-

public partial class TMSStorageDevice
{
    public int TMSStorageDeviceID { get; set; }
    public string Name { get; set; }
    public Nullable<decimal> size { get; set; }
    public int RackID { get; set; }
    public string CustomerName { get; set; }
    public string Comment { get; set; }
    public byte[] timestamp { get; set; }

    public virtual Technology Technology { get; set; }
    public virtual TMSRack TMSRack { get; set; }
}

but if i call the Create action method i will get the following exception:-

System.Data.Entity.Validation.DbEntityValidationException was caught
  HResult=-2146232032
  Message=Validation failed for one or more entities. See 'EntityValidationErrors' property for more details.
  Source=EntityFramework
  StackTrace:
       at System.Data.Entity.Internal.InternalContext.SaveChanges()
       at System.Data.Entity.Internal.LazyInternalContext.SaveChanges()
       at System.Data.Entity.DbContext.SaveChanges()
       at TMS.Models.Repository.Save() in c:\Users\Administrator\Documents\Visual Studio 2012\Projects\TMS\TMS\Models\Repository.cs:line 1926
       at TMS.Controllers.StorageDeviceController.Create(SDJoin sdj, FormCollection formValues) in c:\Users\Administrator\Documents\Visual Studio 2012\Projects\TMS\TMS\Controllers\StorageDeviceController.cs:line 160
  InnerException:

Can anyone advice what is wrong, as i double check my code and every thing should work fine ? Thanks

Xaruth
  • 4,034
  • 3
  • 19
  • 26
John John
  • 1
  • 72
  • 238
  • 501
  • Did you "see the `EntityValidationErrors` property for details"? – Mansfield Oct 22 '13 at 14:01
  • it shows one error with the folloiwng description " System.Data.Entity.Validation.DbEntityValidationResult}" – John John Oct 22 '13 at 14:02
  • 1
    And looking at the `ValidationErrors` property should tell you exactly what the problem is. – Mansfield Oct 22 '13 at 14:03
  • there is no ValidationErros section.. – John John Oct 22 '13 at 14:05
  • 1
    Catch the object `DbEntityValidationException` within your method `InsertOrUpdateSD`. That should help you find the validation error. – Codes with Hammer Oct 22 '13 at 14:13
  • Also, what's your `Technology` class? That may be where the validation error lies. – Codes with Hammer Oct 22 '13 at 14:15
  • You've got 2 calls to `Save()` which doesn't look right - one in the `Create` method and another in the `InsertOrUpdateSD` method – qujck Oct 22 '13 at 14:38
  • but i am following the same approach on other model classes ()two .Save methods, as this is the requirement for my system , and the Create process is working well for these model classes. – John John Oct 22 '13 at 14:56
  • i catch the DbEntityValidationException , and it shows the folloiwng Object reference not set to an instance of an object. at TMS.Controllers.StorageDeviceController.Create(SDJoin sdj, FormCollection formValues) in c:\Users\Administrator\Documents\Visual Studio 2012\Projects\TMS\TMS\Controllers\StorageDeviceController.cs:line 218 at lambda_method(Closure , ControllerBase , Object[] ) at System.Web.Mvc.ActionMethodDispatcher.Execute(ControllerBase controller, Object[] parameters) – John John Oct 22 '13 at 15:06

3 Answers3

134

You haven't shown the Save() method but if you can add code like this to it you'll get an exception that contains all the details you're looking for

try
{
    this.context.SaveChanges();
}
catch (System.Data.Entity.Validation.DbEntityValidationException dbEx)
{
    Exception raise = dbEx;
    foreach (var validationErrors in dbEx.EntityValidationErrors)
    {
        foreach (var validationError in validationErrors.ValidationErrors)
        {
            string message = string.Format("{0}:{1}", 
                validationErrors.Entry.Entity.ToString(),
                validationError.ErrorMessage);
            // raise a new exception nesting
            // the current instance as InnerException
            raise = new InvalidOperationException(message, raise);
        }
    }
    throw raise;
}
qujck
  • 14,388
  • 4
  • 45
  • 74
  • thanks a lot , using you above code i got the following user friendly error message "TMS.Models.TMSStorageDevice:The Name field is required.". and now i fix the error. but i am not sure why i did not get the same error description by default !! – John John Oct 22 '13 at 15:41
  • 2
    Thanks bro. saved me a hell lot of time today. Wouldn't have been easy without your answer – Pankaj Upadhyay Jul 07 '15 at 08:15
  • 1
    I don't usually write comment just for say thank you, but I will make an exception this time. Thank you very much ! You saved me from a big trouble :) @qujck – Koray Durudogan Dec 20 '15 at 16:17
  • 1
    I second what @KorayDurudogan says. This was immensely helpful. – dionysus Jan 26 '16 at 22:44
  • 1
    Thanks a ton!! Literally just used this for the second time! – ChaseHardin Jul 19 '16 at 13:34
  • 1
    Exceptional answer !! Great work otherwise i wouldn't be able to find the bug in thousand years !! Thumbs Up – BILAL AHMAD Sep 27 '17 at 19:57
  • Where is the Exception messages visible in Visual Studio? I can't see them being thrown after using this. – naz786 Nov 20 '17 at 21:14
8

I know the question is old now, but I hope someone finds this useful, too.

  1. Most likely (and indeed, judging by your comments) the error was that your variable doesn't pass Model validation.
  2. The other way to see the errors you couldn't see (without changing the code) is to look at the exception using the QuickWatch window. The problem is that 'View Details' window that you can open from exception tooltip doesn't show EntityValidationErrors. And without a catch block you don't have any exception variable you can look at in QuickWatch. Luckily, QuickWatch has PseudoVariables. So, using "$exception" pseudovariable you can easily take a look at the current unhandled exception in QuickWatch window. (Please, see screenshots below) Exception Details window and QuickWatch window with $exception pseudovariable
Roman Lemko
  • 101
  • 1
  • 2
1

Although this is an old post but this approach can be more fruitful!

Credits

Try something like this

        try
        {
            pcontext.SaveChanges();
        }
       catch (System.Data.Entity.Infrastructure.DbUpdateConcurrencyException ex)
        {             
             Console.WriteLine(ex.InnerException);
        }
        catch (System.Data.Entity.Core.EntityCommandCompilationException ex)
        {
          Console.WriteLine(ex.InnerException);
        }
        catch (System.Data.Entity.Core.UpdateException ex)
        {
         Console.WriteLine(ex.InnerException);
        }

        catch (System.Data.Entity.Infrastructure.DbUpdateException ex) //DbContext
        {
            Console.WriteLine(ex.InnerException);
        }

        catch (Exception ex)
        {
            Console.WriteLine(ex.InnerException);
            throw;
        }
Community
  • 1
  • 1
singhswat
  • 832
  • 7
  • 20