在控制器内循环遍历模型类

时间:2019-01-16 00:03:49

标签: c# asp.net-mvc

此帖子与Nested Try/Catch Blocks

有关

这是我的模特:

 public class Benefits
    {
        public int Id { get; set; }
        public Guid? ResponseId { get; set; }
        public decimal? MedicalTotal { get; set; }
        public decimal? StdSicknessAccident { get; set; }
        public decimal? LtdWage { get; set; }
        public decimal? MedicalPremiums { get; set; }
        public decimal? DentalPremiums { get; set; }
        public decimal? VisionCare { get; set; }
        public decimal? RetireePremiums { get; set; }
        public decimal? LifeInsurance { get; set; }
        public decimal? Prescription { get; set; }
        public decimal? MedAdmin { get; set; }
        public decimal? MedOther { get; set; }
        public decimal? HsaFsa { get; set; }
        public decimal? PtoTotal { get; set; }
        public decimal? Holidays { get; set; }
        public decimal? Pto { get; set; }
        public decimal? Vacations { get; set; }
        public decimal? SickLeave { get; set; }
        public decimal? PtoOther { get; set; }
        public decimal? RetirementTotal { get; set; }
        public decimal? X401k {get; set; }
        public decimal? DefinedBenefit { get; set; }
        public decimal? CashBalance { get; set; }
        public decimal? RetirementAdmin { get; set; }
        public decimal? RetirementOther { get; set; }
        public decimal? MiscTotal { get; set; }
        public decimal? Severance { get; set; }
        public decimal? Dependent { get; set; }
        public decimal? Tuition { get; set; }
        public decimal? Relocation { get; set; }
        public decimal? Total { get; set; }
    }

用户正在以相同的顺序上载具有行的Excel文件(他们没有上载自己的ID或ResponseId。我已经开始编写if语句来捕获此类错误:

                    bool success = Decimal.TryParse(table[0], out decimal MedicalTotal);
                    if (success)
                    {
                        b.MedicalTotal = MedicalTotal;
                    }
                    else
                    {
                        model.ErrorList.Add("Medical total cell should be formatted as Currency, Accounting, or Number.");
                    }


                    bool success1 = Decimal.TryParse(table[1], out decimal StdSicknessAccident);
                    if (success1)
                    {
                        b.StdSicknessAccident = StdSicknessAccident;
                    }
                    else
                    {
                        model.ErrorList.Add("STD, Sickness, and Accident Insurance cell should be formatted as Currency, Accounting, or Number.");
                    }



                    bool success2 = Decimal.TryParse(table[2], out decimal LtdWage);
                    if (success2)
                    {
                        b.LtdWage = LtdWage;
                    }
                    else
                    {
                        model.ErrorList.Add("LTD & Wage Insurance cell should be formatted as Currency, Accounting, or Number.");
                    }

                    bool success3 = Decimal.TryParse(table[3], out decimal MedicalPremiums);
                    if (success3)
                    {
                        b.MedicalPremiums = MedicalPremiums;
                    }
                    else
                    {
                        model.ErrorList.Add("Medical Premiums cell should be formatted as Currency, Accounting, or Number.");
                    }

这是一个非常容易的过程,但是我认为,鉴于其重复性,可能会有某种方法可以遍历我的模型字段并完成相同的任务。我可以向每个模型字段中添加一个[Display(Name="Medical Total")]或其他一些元数据。我还考虑过在上下文中添加一个新表来容纳所有错误消息(这是最佳做法吗?)。

那么我的解决方案是否有替代方案,它会大大缩短呢?像这样:

List<bool> success = new List<bool>();
for(var i = 1; i<Benefits.FieldCount; i++)
{
    success[i] = decimal.TryParse(Table[i], out decimal Benefits.Field[i]
};
if(success[i])
{
    b.Field[i] = Benefits.Field[i];
}
else
{
    model.ErrorList.Add(Benefits.Field[i].Name "must be formatted as Accounting, Currency, or Number.");
}

2 个答案:

答案 0 :(得分:0)

您可以为此使用反射,这是一个示例:

    Type type = typeof(Benefits);
    PropertyInfo[] properties = type.GetProperties();
    foreach (PropertyInfo property in properties)
    {
         // your logic here
        Console.WriteLine("{0} = {1}", property.Name, property.GetValue(benefitsInstance, null));
    }

    Console.Read();

答案 1 :(得分:0)

我会放弃所有的复杂性,而只使用自定义Validation Attributes

public class Foo : ValidationAttribute
{
    private readonly string _name;

    public Foo(string name)
    {
        _name = name;
    }

    protected override ValidationResult IsValid(object value, ValidationContext context)
    {
        // if the value is null, don't go further
        if (value == null) return ValidationResult.Success;

        // if the value cannot be parsed as a decimal (not valid)
        if (!Decimal.TryParse(value, out decimal d))
        {
            // return an error message
            return new ValidationResult($"{_name} cell should be formatted as...");
        }

        // if the parsed decimal is negative
        if (d < 0)
        {
            // return an error message
            return new ValidationResult($"{_name} cell cannot be negative.");
        }

        // if we got this far it was a success
        return ValidationResult.Success;
    }        
}

然后只需使用验证属性装饰您的属性

[Foo("STD, Sickness, and Accident Insurance")]
decimal? StdSicknessAccident { get; set; }

[Foo("LTD & Wage Insurance")]
decimal? LtdWage { get; set; }