web-dev-qa-db-de.com

Die unauffällige Validierung funktioniert nicht mit Ajax.BeginForm

Ich habe View mit Model1, wo ich Ajax.BeginForm() stelle, und in dieser View habe ich PartialView mit Model2, wo ich Ajax.BeginForm() stelle. Also nur in der ersten Form, die unobtrusive validation arbeitet. Warum nur in erster Form eine Arbeitsbestätigung?

Erster Blick  

@model Model1

@using (Ajax.BeginForm("Action1","Controller",null,new AjaxOption(){ onSuccess = "alert('=)')"},null)
{

   <intput type="submit" value="Save" />
}


Model2 model2 = new Model2();
@Html.EditorFor(m=>model2)

** In der Model2-Ansicht habe ich. ** 

@model Model2 
@using (Ajax.BeginForm("AddStreet","Controller",new AjaxOption(){onSuccess = "alert('=)'")},option,null)
{

        @Html.LabelFor(m => Model.Name):
        @Html.TextBoxFor(m => Model.Name)
        @Html.ValidationMessageFor(m => Model.Name)

       <intput type="submit" value="Save" />
}

Danke an @Darin Dimitrov für die Antwort.  

31
Sasha Fentsyk

Dies liegt daran, dass die zweite Ansicht zu einem späteren Zeitpunkt mit AJAX geladen wird und Sie $.validator.unobtrusive.parse(...).__ aufrufen müssen. unmittelbar nachdem der Inhalt in das DOM injiziert wurde, um eine unauffällige Validierung zu ermöglichen. Schauen Sie sich den folgenden Blogpost an für weitere Details.

Abonnieren Sie in Ihrem Fall anstelle von alerting im OnSuccess-Callback des ersten AJAX - Aufrufs eine Javascript-Funktion, die diese Methode aufruft:

@using (Ajax.BeginForm(
    "Action1",
    "Controller",
    null,
    new AjaxOptions { 
        OnSuccess = "onSuccess",
        UpdateTargetId = "result"
    },
    null)
)
{
    <input type="submit" value="Save" />
}

und dann in Ihrer Javascript-Datei:

var onSuccess = function(result) {
    // enable unobtrusive validation for the contents
    // that was injected into the <div id="result"></div> node
    $.validator.unobtrusive.parse($(result));
};
52
Darin Dimitrov

Sie müssen diese 2 Dateien in Ihrer Teilansicht hinzufügen, auch wenn sie sich bereits in Shared/_Layout.cshtml befindet:

<script src="@Url.Content("~/Scripts/jquery.validate.min.js")" type="text/javascript"></script>
<script src="@Url.Content("~/Scripts/jquery.validate.unobtrusive.js")" type="text/javascript"></script>

Oder platzieren Sie dies in Ihrem Partial :

<script type="text/javascript" language=javascript>
    $.validator.unobtrusive.parse(document);
</script>
24
dperez

Sie müssen einen Verweis auf jquery.unobtrusive-ajax.js hinzufügen, um die Validierung in Ajax Form zu aktivieren.

Etwas wie das:

<script type="text/javascript" src="/Scripts/jquery.unobtrusive-ajax.js"></script>
2
gdoron

Die Antwort von Darin Dimitrov funktioniert nur, wenn validate() des jquery validate plugin nicht aufgerufen wurde, bis der Ajax-Erfolgshandler aufgerufen wird. Ich kann mir kein Szenario vorstellen, in dem dies der Fall sein könnte. Daher wundere ich mich, warum die Antwort als richtig akzeptiert wurde.

Möglicherweise führt eine Änderung des Jquery-Validierungscodes in der Vergangenheit zu folgendem Problem:

Das Problem ist, dass validate() zuerst die folgende Zeile ausführt

// Check if a validator for this form was already created
var validator = $.data( this[ 0 ], "validator" );
if ( validator ) {
  return validator;

was bedeutet, dass das validator-Objekt) zurückgegeben wird, wenn validate () ohne weitere Behandlung der Optionen aufgerufen wird.

Dies bedeutet auch, dass ein späterer Aufruf von $.validator.unobtrusive.parse(...) oder $.validator.unobtrusive.parseElement(...) a ausführt

$form.validate(this.options) <- this.options holds the new rules parsed from HTML

das Aktualisieren der Optionen des Validators hat keine Auswirkung, da die Optionen überhaupt nicht verarbeitet werden.

Die Lösung hier ist, den Validator manuell zu aktualisieren

var $htmlCode = $("your html");

$.validator.unobtrusive.parse($htmlCode, true); // true means no validate() call

// now get the validation info collected in parse()
var validationInfo = $form.data("unobtrusiveValidation"); 

var $validator = $form.validate(); // get validator and ...
$validator.settings.rules = validationInfo.options.rules; // ... update its rules
$validator.settings.messages = validationInfo.options.messages; // ... update its messages

Die erneute Validierung des Formulars (z. B. durch Klicken auf "Senden") sollte jetzt zu den erwarteten Ergebnissen führen.

Hier ist ein vollständiges Beispiel, das auch Code aus der bereits akzeptierten Antwort enthält:

Rasierer

@using (Ajax.BeginForm(
    "Action1",
    "Controller",
    null,
    new AjaxOptions { 
        OnSuccess = "onSuccess",
        UpdateTargetId = "result"
    },
    null)
)
{
    <input type="submit" value="Save" />
}

Javascript

var onSuccess = function(result) {
    var $htmlCode = $(result);

    $.validator.unobtrusive.parse($htmlCode, true); // true means no validate() call

    // now get the validation info collected in parse()
    var validationInfo = $form.data("unobtrusiveValidation"); 

    var $validator = $form.validate(); // get validator and ...
    $validator.settings.rules = validationInfo.options.rules; // ... update its rules
    $validator.settings.messages = validationInfo.options.messages; // ... update its messages
};

-

Als Randbemerkung ist auch ein manuelles Aktualisieren des Validators mithilfe der rules()-Methode möglich

$yourHtmlField.rules( "add", {
  required: true,
  messages: {
    required: "Required input"
  }
});

da dies direkt die Regeln des Validators ohne das unauffällige Zeug aktualisiert. Dann werden die Datenwertattribute jedoch unbrauchbar.

1
ViRuSTriNiTy

Diese Lösung hat für mich am besten funktioniert.

$.validator.unobtrusive.parse(document);
1