4

ページ上のテキストフィールドのリストを反復処理する以下のJavaScriptコードがあります。テキストフィールドのテキストを価格として受け取り、AJAX GETを介してサーバーに送信し、解析されたdoubleをサーバーから取得します。返品された価格のいずれかが既存の価格よりも低い場合、フォームは送信しないでください。

問題は、Ajax呼び出しの非ブロッキング即時応答の性質のために、すべてのAJAX要求が終了する前にフォームが送信していることです。wait()関数(またはすべてのAjaxメソッドが完了したときのコールバック)を設定する必要がありますが、jQueryでそれを行う方法がわかりません。

助言がありますか?

// .submitForm is a simple button type="button", not type="submit"
$(".submitForm").click(function(e){
   var submittable = validatePrices();
   if (submittable) {
     $("#myForm").submit();
   }
});

function validatePrices() {
    var submittable = true; 

    $(".productPrice").each(function(){
        var $el = $(this);

        $.ajax({
            type: "POST",
            url: "/get_price.jsp", 
            async: false,
            dataType: "html",
            data: "price=" + $el.val(), 
            success: function(data)
            {                  
               var price = new Number(data.split("|")[1]);
               var minPrice = new Number($el.data("min-price")); 
               if (price < minPrice) 
               {
                  $el.addClass("error");
                  $(".dynamicMessage").show().addClass("error").append("<p>ERROR</p>");
                  submittable = false;
               }
            }
        });
        return submittable;
    });
}
4

2 に答える 2

4

すでに同期AJAX(ユーザーエクスペリエンスにとって非常に悪い考え)を使用しているので、それは問題ではありません。問題は、「送信」ハンドラーのデフォルトのアクションをキャンセルする必要があることです。

$(".submitForm").click(function(e){
   var submittable = validatePrices();
   e.preventDefault(); // this line
   if (submittable) {
     $("#myForm").submit();
   }
 });

個別のフィールドごとにサーバーに同期HTTPリクエストを使用すると、サイトの速度が大幅に低下します。とにかくフォームを送信するときは、サーバーでパラメーターを再度確認する必要があるため、確認してエラーを返す方がはるかに良いでしょう。

編集—状況がより明確になったので、先に進む方法は、AJAX検証チェックの実行を完全に停止することだと思います。なんで?そうですね、これらのテストを実行したとしても、フォームが実際に送信されるときに、基本的に同じ妥当性テストを行う必要があります。他のフォーム検証シナリオのように、実際に実行されているJavaScript検証コードに依存することはできません。とにかくフォームの送信時に検証を行う場合は、すべてを同時に行うために大量のHTTPリクエストを節約できます。

于 2013-03-07T17:18:57.577 に答える
1

フォームの送信をキャンセルするわけではありません。ajaxコールバックを厳密に操作する必要があります(非同期で使用したい場合は、これが便利です)。

$(".submitForm").click(function(e){
   e.preventDefault();
   validatePrices().done(function () { /* ajax success function here */
       if (submittable) {
           $("#myform").trigger('submit');
       }
   }
});

function validatePrices() {
    var checks = [];

    $(".productPrice").each(function(){
        var $el = $(this);
        checks.push($.ajax({
            /* snip */
    });
    return $.when.apply(null, checks);

}
于 2013-03-07T17:21:08.393 に答える