我正致力于在ASP.NET MVC视图中渲染动态表单,以满足这些要求:
我正在研究创建一个自定义模型绑定器来实现这一目标。我一般打算这样做:
我不确定我是以最好还是最简单的方式做这件事。这种方法会给我带来很多问题甚至工作吗?我该怎么做才能改进它?
答案 0 :(得分:8)
我写了一个类库,它基本上完全符合我的问题中描述的psuedocode。它很棒。
我终于清理了我的班级图书馆。我添加了一些新功能,并创建了一个记录良好的演示Web应用程序。
所有这些都是hosted here on CodePlex。我希望这有助于某人。
答案 1 :(得分:0)
我不是专家,但如果你是ASP.NET MVC的新手,那么我建议你在开始自己的内置功能之前先使用内置功能。它完成了你所描述的大部分内容,除了不鼓励在控制器中定义/构建UI,因为这是视图的工作。
通过ModelStateDictionary,您可以添加模型错误并设置模型值,然后在验证失败时将其绑定到表单输入。
更新:另一种看待它的方法:问问自己为什么使用MVC而不是经典的ASP.NET构建技术,然后看看你提出的方法是否符合这些原因。对我来说,分离关注点是一个很大的原因,以及对生成的HTML的精细控制,我觉得你的方法可能会颠覆这些事情。
专门解决您的编辑问题:
第1步到第1步是针对MVC范例的。 第4步,很好。 步骤5到7是非常标准的MVC实践,并且完全受框架支持。例如,Performing Simple Validation (C#)显示了验证和错误消息表示的示例。
答案 2 :(得分:0)
虽然不是专家,但我必须创建一个解决方案,其中我的主对象有一个值列表。让我们称之为对象A有一个映射在数据库中的ApplicationValues列表。 ApplicationValues有一个Key(表单字段,例如PhoneNumber)和Value。
由于ApplicationValues是一个EntitySet,我必须创建get和set方法来正确处理设置特定的ApplicationValue。我在我的数据库中还有一个ApplicationRules列表,它定义了这些应用程序值可以采用的内容。
以下是一段代码,可帮助您根据自己的需求开发解决方案。
public partial ApplicationValue
{
public string Key;
public string Value;
}
public partial ApplicationRule
{
public string ValidationFormat;
public string ValidationError;
public bool Required;
}
public partial class A
{
public void SetValue(string key, string value)
{
//ApplicationValues is the list of values associated to object A
ApplicationValue v = ApplicationValues.SingleOrDefault
(k => k.Key == key);
//if we already have this value
if (v != null)
{ //...then we can simply set and return
v.Value = value;
return;
}
//else we need to create a new ApplicationValue
v = new ApplicationValue
{
AffinityID = this.ID,
Key = key,
Value = value
};
ApplicationValues.Add(v);
}
public string GetValue(ApplicationField key)
{
return GetValue(key, String.Empty);
}
public string GetValue(ApplicationField key, string defaultValue)
{
if (ApplicationValues == null)
return defaultValue;
ApplicationValue value = ApplicationValues.SingleOrDefault
(f => f.Key == key.ToString());
return (value != null) ? value.Value : defaultValue;
}
然后进行表单验证,我遍历ApplicationRules(定义是否需要字段,包含正则表达式等)并将其与FormCollection匹配。
public ActionResult Details(FormCollection form)
{
IList<ApplicationRule> applicationRules = //get my rules from the DB
if (!(ValidateApplication(applicationRules, form, a)))
{
ModelState.AddModelError("message", "Please review the errors below.");
return View(a);
}
...
}
private bool ValidateApplication(IList<ApplicationRule> applicationRules,
FormCollection form, A a)
{
//loop through the application rules
foreach (ApplicationRule ar in applicationRules)
{
//try and retrieve the specific form field value using the key
string value = form[ar.Key];
if (value == null)
continue;
//set the model value just in case there is an error
//so we can show error messages on our form
ModelState.SetModelValue(ar.Key, ValueProvider[ar.Key]);
//if this rule is required
if (ar.Required)
{ //...then check if the field has a value
if (String.IsNullOrEmpty(value))
{
ModelState.AddModelError(ar.Key, "Field is required");
continue;
}
}
//if this rule has a validation format
if (!String.IsNullOrEmpty(ar.ValidationFormat))
{ //...then check the value is of the correct format
Regex re = new Regex(ar.ValidationFormat);
if (!re.IsMatch(value))
{
ModelState.AddModelError(ar.Key, ar.ValidationError);
continue;
}
}
a.SetValue(ar.Key, value);
}
return ModelState.IsValid;
}
答案 3 :(得分:0)
您的字段定义有多动态?如果它们不经常更改,则可以在创建定义后使用代码dom生成模型和控制器。我没有在ASP.NET MVC中尝试这个,但它可能是一个好方法。
http://msdn.microsoft.com/en-us/library/y2k85ax6.aspx
本文使用代码dom进行ActionLink生成。