我正在使用Entity Framework 4和动态数据站点向少数用户公开一个简单的管理界面。一般来说工作得很好,但我在模型的几个字段上遇到了这个问题。
有几个表有一些与审计相关的字段 - CreatedBy,CreatedDate,ModifiedBy和ModifiedDate。这些字段在数据库中是必需的,并且关联的模型将属性标记为不可为空(全部应该是)。但是,我正在设置代码中这些字段的值 - 字段类型的字段模板在页面上将这些特定字段标记为已禁用,而在SavingChanges事件中,我将这些字段设置为适当的值。当我更新现有项目时,所有工作很好。
当我尝试创建新项目时出现问题。我希望这些字段在页面上保持为空并在提交时由我的代码自动填充,但字段模板为这些字段设置了RequiredFieldValidators,并且不允许我在没有值的情况下提交它们。通常情况下这很好,除了我想阻止EF在页面提交时验证这些字段。
我意识到我可以在数据库中将这些字段标记为可空并且可以解决问题 - 从数据的角度来看,它甚至可能会很好,但我不喜欢这样做 - 有一件事它不是这些字段出现的某些模型不太可能在以后被其他人批量加载。我宁愿让数据库强制执行这些字段的不可为空性。在字段模板中,我尝试移动内置的SetUpValidator()调用,以便在加载这些特定字段时不运行RequiredFieldValidator,并且我还尝试禁用RequiredFieldValidators并强制将其IsValid属性设置为true。这些操作都不允许我提交页面。
有没有办法告诉EF /动态数据跳过某些字段的验证?
修改
如下所述,我也尝试在模型中将它们标记为可空,而不是在数据库中,这会导致错误:Problem in mapping fragments...Non-nullable column...in table...is mapped to a nullable entity property.
编辑#2
我找到了一个有效的解决方案,但需要修改实体集的自动生成的设计器文件,这个文件最多是脆弱的。我很想知道一种“更为严谨”的方式,但如果在接下来的几天内没有任何明显变化,我会发布自己的答案。
答案 0 :(得分:1)
所以这里是我发现我必须做的编辑。当允许工具在edmx Designer.cs文件中创建实体时,我得到如下属性:
表示服务器端的日期时间
[EdmScalarPropertyAttribute(EntityKeyProperty=false, IsNullable=false)]
[DataMemberAttribute()]
public global::System.DateTime CreatedDate
{
get
{
return _CreatedDate;
}
set
{
OnCreatedDateChanging(value);
ReportPropertyChanging("CreatedDate");
_CreatedDate = StructuralObject.SetValidValue(value);
ReportPropertyChanged("CreatedDate");
OnCreatedDateChanged();
}
}
表示varchar
[EdmScalarPropertyAttribute(EntityKeyProperty=false, IsNullable=false)]
[DataMemberAttribute()]
public global::System.String CreatedBy
{
get
{
return _CreatedBy;
}
set
{
OnCreatedByChanging(value);
ReportPropertyChanging("CreatedBy");
_CreatedBy = StructuralObject.SetValidValue(value, false);
ReportPropertyChanged("CreatedBy");
OnCreatedByChanged();
}
}
要使其无需验证DateTime属性设置,EdmScalarPropertyAttribute的IsNullable参数为true就足以避免此问题。对于String属性,您还必须将SetValidValue方法调用的第二个参数更改为“true”。
所有这些都说,我离开这个的唯一原因是因为我不希望在我们迁移到这个站点的不同平台之前不得不重新生成实体一次或两次。在这种情况下,合并我已经使用该工具生成的版本签入git允许我避免大部分的麻烦,
答案 1 :(得分:0)
这是我的只读自动生成日期字段的元信息。我没有验证控件来验证这些字段。希望这会有所帮助。
[ReadOnly(true)]
[DataType(DataType.Date)]
[Column(IsDbGenerated = true, UpdateCheck = UpdateCheck.Never, AutoSync = AutoSync.Never)]
[UIHint("DateTime")]
[Display(Name = "Modified", Order = 1000)]
[DisplayFormat(ApplyFormatInEditMode = true, DataFormatString = "{0:d}")]
public object DateModified { get; private set; }