2010-12-17 6 views
1

Ich versuche, ein Viewmodel mit flüssiger Validierung zu validieren. Wenn ich das viewmodel-Objekt posten, gibt die modelstate.isvalid immer false zurück. Wenn ich die Werte auf dem gebuchten Objekt überprüft habe, werden auch die Eigenschaften überprüft, die verwendet wurden, um die Daten in Dropdown-Listen anzuzeigen. Wie man das löst. Tue ich es falsch, bitte hilfe. Ich bin neu bei ASP.net MVC und versuche nur mit fließenden Validierung und fließenden NHibernate Mappings in diesem Projekt.Problem beim Validieren eines Viewmodels mit fließender Validierung

Weitere Details wie folgt:

I wie unten ein Domänenmodell bezwecken:

[Validator(typeof(TestRequirementValidator))] 
public class TestRequirement 
{ 
    public virtual int Id { get; private set; } 
    public virtual int SampleId { get; set; } 
    public virtual int TestId { get; set; } 
    public virtual int StandardId { get; set; }  
    public virtual string Description { get; set; } 
    public virtual Sample Sample { get; set; } 
    public virtual Test Test { get; set; } 
    public virtual Standard Standard { get; set; } 
} 

I wie unten ein View-Modell erstellt haben:

[Validator(typeof(TestRequirementViewModelValidator))] 
public class TestRequirementViewModel 
{ 
    public TestRequirement TestRequirement; 
    public SelectList Samples; 
    public SelectList Tests; 
    public SelectList Standards; 

    public TestRequirementViewModel() 
    { 
    ISession _session = FNHsessionFactory.GetSessionFactory(); 
    this.TestRequirement = new TestRequirement(); 
    this.Samples = new SelectList(from S in _session.Linq<Sample>() select S, "Id", "Name"); 
    this.Tests = new SelectList(from T in _session.Linq<Test>() select T, "Id", "Name"); 
    this.Standards = new SelectList(from St in _session.Linq<Standard>() select St, "Id", "Name"); 
    } 
} 

Modell Validator ist als unten :

public class TestRequirementValidator : AbstractValidator<TestRequirement> 
{ 
    public TestRequirementValidator() 
    {  
    RuleFor(x => x.SampleId) 
    .NotEmpty() 
    .WithMessage("This field is required") 
    .DisplayName("Sample Name"); 

    RuleFor(x => x.TestId) 
     .DisplayName("Test Name"); 

    RuleFor(x => x.StandardId) 
     .NotEmpty() 
     .WithMessage("This field is required") 
     .DisplayName("Standard Name"); 

    RuleFor(x => x.Description) 
     .NotEmpty() 
     .WithMessage("This field is required")     
     .Length(0, 10) 
     .WithMessage("Length of this field cannot be more than 10 characters"); 
    } 
} 

Ansicht Modell Validator ist als unten:

public class TestRequirementViewModelValidator:AbstractValidator-TestRequirementViewModel- 
{ 
    public TestRequirementViewModelValidator() 
    {    
    RuleFor(x => x.TestRequirement) 
     .SetValidator(new TestRequirementValidator()); 
    } 
} 

View ist wie folgt:

<%@ Page Language="C#" Inherits="System.Web.Mvc.ViewPage<foo.Models.ViewModels.TestRequirementViewModel>" MasterPageFile="~/Views/shared/site.master" %> 
<asp:Content ContentPlaceHolderID="MainContent" ID="MainContentContent" runat="server"> 
    <h3><%= Html.Encode(ViewData["Message"]) %></h3> 

    <% using (Html.BeginForm()) {%> 
    <%= Html.ValidationSummary(true) %> 
    <fieldset> 
     <legend>Create Test Requirement</legend> 

     <div class="editor-label"> 
     <%= Html.LabelFor(model => model.TestRequirement.SampleId) %> 
     </div> 

     <div class="editor-field"> 
     <%= Html.DropDownListFor(model => model.TestRequirement.SampleId, new SelectList(Model.Samples.Items, Model.Samples.DataValueField, Model.Samples.DataTextField), "Select Sample") %> 
     <%= Html.ValidationMessageFor(model => model.TestRequirement.SampleId) %> 
     </div> 

     <div class="editor-label"> 
     <%= Html.LabelFor(model => model.TestRequirement.TestId) %> 
     </div> 

     <div class="editor-field"> 
     <%= Html.DropDownListFor(model => model.TestRequirement.TestId, new SelectList(Model.Tests.Items, Model.Tests.DataValueField, Model.Tests.DataTextField), "Select Test") %> 
     <%= Html.ValidationMessageFor(model => model.TestRequirement.TestId) %> 
     </div> 

     <div class="editor-label"> 
     <%= Html.LabelFor(model => model.TestRequirement.StandardId) %> 
     </div> 

     <div class="editor-field"> 
     <%= Html.DropDownListFor(model => model.TestRequirement.StandardId, new SelectList(Model.Standards.Items, Model.Standards.DataValueField, Model.Standards.DataTextField), "Select Standard") %> 
     <%= Html.ValidationMessageFor(model => model.TestRequirement.StandardId) %> 
     </div> 

     <div class="editor-label"> 
     <%= Html.LabelFor(model => model.TestRequirement.Description) %> 
     </div> 

     <div class="editor-field"> 
     <%= Html.TextBoxFor(model => model.TestRequirement.Description) %> 
     <%= Html.ValidationMessageFor(model => model.TestRequirement.Description) %> 
     </div> 

     <p> 
     <input type="submit" value="Create" /> 
     </p> 
    </fieldset> 
    <% } %> 

    <%= Html.ClientSideValidation<TestRequirement>("TestRequirement") %> 
</asp:Content> 

Controller ist wie folgt:

public ActionResult TestRequirement() 
{ 
    TestRequirementViewModel NewTestRequirement = new TestRequirementViewModel(); 
    return View(NewTestRequirement); 
} 

[HttpPost] 
public ActionResult TestRequirement(TestRequirementViewModel NewTestRequirement) 
{ 
    if(ModelState.IsValid) 
    { 
    ISession _session = FNHsessionFactory.GetSessionFactory();  
    _session.SaveOrUpdate(NewTestRequirement.TestRequirement);  

    ViewData["Message"] = "New Test Requirement has been created successfully"; 

    return View(); 
    } 

    return View(NewTestRequirement); 
} 

Antwort

0

ich nicht mit Fluent Validierung helfen können, aber als Du hast dies als fluent-nhibernate getaggt. Ich dachte, ich sollte deine Nutzung von NHibernate kommentieren.

Ihr Ansichtsmodell sollte nicht NHibernate in seinem Konstruktor verwenden; Tatsächlich sollte Ihr Ansichtsmodell nur eine Datenstruktur sein, die von einem externen Dienst aufgefüllt wird. Ähnlich möchten Sie vielleicht dasselbe mit Ihrem Controller machen; es ist üblich, dass Menschen den Datenzugriff in eine repository extrahieren, um ihre Controller zu isolieren (und das Testen einfacher zu machen, testen Sie nicht?).

Wenn Sie ein Repository verwenden, können Sie Ihr Ansichtsmodell dann von Ihrer Entität projizieren. Sie können dies entweder mit NHibernate projections and transformers oder mit einem Tool wie AutoMapper tun.

Verwandte Themen