开发者

Determine source of a ConstraintException in an EF entity

I have an entity class with a bunch of non-nullable string properties. If I try and set one of these to null, I get a ConstraintException and the message "This property cannot be set to a null value."

Without setting tracker variable to the name of each 开发者_Go百科property before assignment, is there a way I can determine which property assignment caused the exception to be thrown?


In side of your POCO Class you can use Checker pattern for this validation. Use constructor injection for not nullable properties to inject.

public class Product:Entity<long>
{
    public Product(string description, string productNo, double? unitPrice, Category category)
    {           

       Check.Require(unitPrice.HasValue, "Unit price can not be null in Product");
       Check.Require(!string.IsNullOrEmpty(description),
              "Description can not be null in Product");            

        Check.Require(!string.IsNullOrEmpty(productNo), 
           "Product number can not be null in Product");

        Check.Require(category != null, "Category can not be null in Product");

        UnitPrice = unitPrice.Value;
        Description = description;
        ProductNumber = productNo;
        Category = category;
    }  



    /// <summary>
    /// Gets or sets the product id.
    /// </summary>
    /// <value>
    /// The product id.
    /// </value>
    public int ProductId { get; set; }

    /// <summary>
    /// Gets or sets the name.
    /// </summary>
    /// <value>
    /// The name.
    /// </value>
    public string Name { get; set; }

    /// <summary>
    /// Gets or sets the category id.
    /// </summary>
    /// <value>
    /// The category id.
    /// </value>
    public long CategoryId { get; set; }

    /// <summary>
    /// Gets or sets the category.
    /// </summary>
    /// <value>
    /// The category.
    /// </value>
    public Category Category { get; set; }

    /// <summary>
    /// Gets or sets the unit price.
    /// </summary>
    /// <value>
    /// The unit price.
    /// </value>
    public double UnitPrice
    {
        get; 
        set;
    }

    /// <summary>
    /// Gets or sets the description.
    /// </summary>
    /// <value>
    /// The description.
    /// </value>
    public String Description
    {
        get;
        set;
    }

    /// <summary>
    /// Gets or sets the product number.
    /// </summary>
    /// <value>
    /// The product number.
    /// </value>
    public string ProductNumber
    {
        get; 
        set;
    }
}

}

public class Check
{
       /// <summary>
    /// Requires the specified assertion.
    /// </summary>
    /// <param name="assertion">if set to <c>true</c> [assertion].</param>
    /// <param name="message">The message.</param>
    public static void Require(bool assertion, string message)
    {
        if(!assertion)
        {
            throw new PreConditionException(message);
        }
    }

    /// <summary>
    /// Ensures the specified assertion.
    /// </summary>
    /// <param name="assertion">if set to <c>true</c> [assertion].</param>
    /// <param name="message">The message.</param>
    public static void Ensure(bool assertion, string message)
    {
        if (!assertion)
        {
            throw new PostConditionException(message);
        }
    }
}

/// <summary>
/// Exception raised when a precondition fails.
/// </summary>
public class PreConditionException : Exception
{
    /// <summary>
    /// Initializes a new instance of the <see cref="PreConditionException"/> class.
    /// </summary>
    /// <param name="message">The message.</param>
    public PreConditionException(string message):base(message)
    {

    }
}

/// <summary>
/// Exception raised when a postcondition fails.
/// </summary>
public class PostConditionException:Exception
{
    /// <summary>
    /// Initializes a new instance of the <see cref="PostConditionException"/> class.
    /// </summary>
    /// <param name="message">The message.</param>
    public PostConditionException(string message):base(message)
    {

    }
}


Can you access the stacktrace? It will have something like 'MyEntity.set_MyNotNullableProperty42' which tells you which property is being set to null.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜