使用一对多关系保存对象

时间:2016-11-06 20:17:28

标签: c# asp.net-mvc asp.net-mvc-5

我有一个Company模型,我想更新Company记录并一次保存一个电话号码列表。有一个1- *的关系。

我的ViewModel看起来像:

public class CompanyRegisterViewModel
{
    public int CompanyId { get; set; }

    public int CompanyTypeId { get; set; }

    public IEnumerable<SelectListItem> CompanyTypes { get; set; }

    [Required(ErrorMessageResourceName = "Required", ErrorMessageResourceType = typeof(ValidationStringResource))]
    [MaxLength(250, ErrorMessageResourceName = "MaximumLength", ErrorMessageResourceType = typeof(ValidationStringResource))]
    public string LicensedCompanyName { get; set; }

    public List<Phone> Phones { get; set; }
}

Save(Company company)方法中,如果我致电:

_context.Companies.Add(company);
_context.SaveChanges();

这会保存新的公司记录并保存List<Phone> Phones,还是我需要交易并再次致电SaveChanges()以保存Phones。我还需要为每个CreatedBy记录设置DateCreatedPhone。在保存和更新Phone循环中的每条记录之前,我是否应该遍历foreach条记录?我希望在后端自动设置此设置,而不是在UI中。

1 个答案:

答案 0 :(得分:2)

如果您想在每次调用SaveChanges或SaveChangesAsync时自动设置ModifiedModifiedBy等属性,则必须执行两项操作。

创建一个基础接口,所有实体都从

继承
public interface IEntityRoot
{
    public DateTime Created { get; set; }
    public string CreatedBy { get; set; }
    public DateTime Modified { get; set; }
    public string ModifiedBy { get; set; }
}

继承此界面中的所有参与者:

  public class Company : IEntityRoot { ... }

这样,从该接口继承的所有实体都将具有属性Created&amp; CreatedBy。最后一步是创建一个小方法,每次保存更改时都会调用该方法,并自动设置当前日期和用户。

public class ApplicationContext : DbContext
{
    /* ... */
    public override int SaveChanges()
    {
        TrackModifiedDates();
        return base.SaveChanges();
    }

    public override async Task<int> SaveChangesAsync()
    {
        TrackModifiedDates();
        return await base.SaveChangesAsync();
    }

    private void TrackModifiedDates()
    {
        var entities = ChangeTracker.Entries()
                                    .Where(x => x.Entity is IEntityRoot && (x.State == EntityState.Added) || (x.State == EntityState.Modified));
        //if anonymous access is possible, do a null check here.
        var userName = HttpContext.Current.User.Identity.Name

        foreach (var entity in entities)
        {
            if(entity.State == EntityState.Added) 
            {
                ((IEntityRoot)entity.Entity).Created = DateTime.UtcNow;
                ((IEntityRoot)entity.Entity).CreatedBy = userName;
            }  

            ((IEntityRoot)entity.Entity).Modified = DateTime.UtcNow;
            ((IEntityRoot)entity.Entity).ModifiedBy = userName;
        }
    }
}