2012-05-11 13 views
2

SQLデータベースに行を挿入できません。私は、オブジェクトの配列をJavaScriptのSQLテーブルに変換したい。ループ内の非同期SQL挿入

次のコードは、配列の最初のオブジェクトのみを追加します。私はstackoverflowや他の場所で見つけることができたすべてを試してきたし、それを動作させることはできません。

ご協力いただければ幸いです。ありがとう。

 for (var i = 0; i < arr.length; i++) { 
      db.save({key:i+"", value:arr[i]}, function(e){ 

      }); 
     } 

UPDATE 1:私はの例をmathecするためにそれを変更して、問題を少し絞り込まれてきました 。

挿入される行の数は、挿入されるオブジェクトのサイズによって異なります。だから、それは各オブジェクトを処理するのにかかる時間と関係があります。

この問題を回避するにはどうすればよいですか?ありがとう。

アップデート2:

私は以下のロバート・ヤングの提案を取り、自己完結型の例を含めました。

以下の例では、最初の5つの要素のみが挿入されています。テストキーの単語テキストの一部を削除して「単語」を1回だけ表示すると、10個の要素が挿入されます。だから、私はそれがそれぞれのオブジェクトを処理するのにかかる時間と関係があると確信しています。

<html> 
    <head> 
     <script src="jquery.js"></script> 
     <script src="lawnchair.js"></script> 
     <script type='text/javascript'> 


      var db = ""; 
      var arr = []; 

      arr.push({name:"a1", test:"word word word word word word word word word word word word word word "}); 
      arr.push({name:"a2", test:"word word word word word word word word word word word word word word "}); 
      arr.push({name:"a3", test:"word word word word word word word word word word word word word word "}); 
      arr.push({name:"a4", test:"word word word word word word word word word word word word word word "}); 
      arr.push({name:"a5", test:"word word word word word word word word word word word word word word "}); 
      arr.push({name:"a6", test:"word word word word word word word word word word word word word word "}); 
      arr.push({name:"a7", test:"word word word word word word word word word word word word word word "}); 
      arr.push({name:"a8", test:"word word word word word word word word word word word word word word "}); 
      arr.push({name:"a9", test:"word word word word word word word word word word word word word word "}); 
      arr.push({name:"a10", test:"word word word word word word word word word word word word word word "}); 
      arr.push({name:"a11", test:"word word word word word word word word word word word word word word "}); 

      $(function() { 
       db = new Lawnchair({table:'t50'}, function(e){ 
        for (i = 0; i < arr.length; i++) { 
         (function(i) { 
          add_row(i); 
         }(i)); 
        } 
       }); 
      }); 

      function add_row(i) { 
       db.save({key:i+"", value:arr[i]}, function(e){ 

       }); 
      } 

     </script> 
    </head> 
    <body> 

    </body> 
</html> 

UPDATE 3: 私はロバートの提案コードを使用し、三つの小さな要素と協力し、次のを思い付きました。だから私は最初の要素を変更し、他の要素よりも大きくしてテストしました。最初の要素は追加されず、最後の要素は追加されました。配列の処理に時間がかかりますか?

<html> 
    <head> 
     <script src="jquery.js"></script> 
     <script src="lawnchair.js"></script> 
     <script type='text/javascript'> 

      var arr = []; 
      var db = ""; 

      $(function() { 
       db = new Lawnchair({table:'t51'}, function(e){ 
        arr=[{key:"k1", value:"v1. Because the contents of this element are larger than the others it will not be added for some reason. Lorem ipsum dolor sit amet, consectetur adipisicing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum. Lorem ipsum dolor sit amet, consectetur adipisicing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum. "} 
        ,{key:"k2", value:"v2"} 
        ,{key:"k3", value:"v3"}] 

        db.batch(arr, function() { 
         db.all(function (recs) { for (r in recs) {console.log(recs[r].key +"| "+ recs[r].value) } }); 
        }); 
       }); 

      }); 

     </script> 
    </head> 
    <body> 
    </body> 
</html> 
+0

投稿したコードの最初のスニペットに問題はありません。ただし、コールバック引数を使用していない場合は不要です。奇妙なことが起こっているようです。問題の[短い、自己完結型の例](http://sscce.org/)を投稿できますか? –

+0

こんにちはロバート、あなたが提案した完全な例を加えました。何か案は?ありがとう。 – user1389968

答えて

1

これは永続ストレージであるため、これを何度も実行すると、永続ストアを初期化しないため、毎回異なる結果になることがあります。 db.nuke()を追加して、少なくともあなたがバグを解決するまでは空白のスレートで始めることをお勧めします。

非同期ストレージについて知っておくべき主なことは、関数が返されるということは、データが実際にはまだ格納されていないということだけです。あなたがdb.getを呼び出すときに、値が格納されているか、されない場合がありますので、あなたが

db = new Lawnchair(function(db){ 
    db.save({key:"value"}) 
    db.get("foo", function (rec) { console.log(rec.value) }); 
}); 

を実行する場合には、あるいは、動作しない場合があります。

これが機能するには、db.getを呼び出す前に値が格納されていることを確認する必要があります。これを行う方法は、コールバックを使用することです.db.saveに2つの引数を渡すと、値が格納されると2番目の引数がコールされます。したがって

db = new Lawnchair(function(db){ 
    db.save({key:"foo", value:"bar"}, function() { 
     db.get("foo", function (rec) { console.log(rec.value) }); 
    }); 
}); 

が問題ありません。

複数の値を格納しようとすると、すべてが格納されていることを確認したいので、これは難しくなります。幸いなことに、この関数はbatchは、このためにあります:

db = new Lawnchair(function(db){ 
    arr=[{key:"k1", value:"v1"},{key:"k2", value:"v2"},{key:"k3", value:"v3"}]; 
    db.batch(arr, function() { 
     db.all(function (recs) { for (r in recs) {console.log(recs[r].key) } }); 
    }); 
}); 

出力

k1 
k2 
k3 

はそれを試してみて、何が起こるか見なければなりません。

+0

こんにちはロバート、私はあなたの例を試してみましたが、私のように非常に少量のデータでしか動作しません。あなたの例の 'k1'をより多くのテキスト(段落など)に置き換えると、最後の2つの要素だけが追加されます。 – user1389968

+0

別の興味深いのは、最初の要素のキーまたは値のテキストのサイズを大きくし、最後の2つの要素がデータベースに追加されますが、console.debugは呼び出されません。これは非常に奇妙な問題です。 – user1389968

+0

このような問題はないので、ブラウザ固有の問題かもしれません。どのブラウザ(バージョン、OS)、どのLawnchairアダプタを使用していますか?使用しているブラウザで大量のデータを保存できない可能性はありますか? –

2

私は数回自分自身を作ったトリッキーなミス:-)。ループ内でコールバック関数が呼び出された場合、コールバック関数は非同期で呼び出されます。したがって、ループは最後まで実行され続けます。この問題を解決する方法は、現在のi値の周りにクロージャを作成して、コールバック関数が実行されたときに右のiにバインドされるようにすることです。

function doSomething(i) { 
    console.log(i) 
} 

var i, len; 

for (i = 0; i < 10; i++) { 
    (function(i) { 
    doSomething(i); 
    }(i)); 
} 

ループ内の関数はすぐに実行されますが、i値は有効範囲内に保持されます。

+0

こんにちは、私はちょうどそれを試みて、再び最初の行を追加します。 – user1389968

+0

この時点で可能性を絞り込む必要があります。たぶん、配列の値をログに記録して、反復が機能していることを確認してください。それが確認されたら、DBログを調べて何らかの理由で行が拒否されていないことを確認します。 – cmather

+0

こんにちはmathec、私は問題を絞りました。オブジェクトが大きいほど、挿入される行が少なくなります。そうすれば、オブジェクトを処理するのにかかる時間と何か関係があります。しかし、何が分かりません。 – user1389968

0

DBにデータを保存する方法がわからないため、AJAXリクエストが問題になることはありませんが、問題は解決するのが難しいですか?問題は、各行を保存するロジック全体にあると思いますある行が別の行を開始するために保存されるのを待たず、何らかの種類の競合状態が発生していて、いくつかの行が同じ "id"(自動インクリメントフィールド)に保存されていて、いくつかの行が保存されます。

私の提案は、サーバーにアレイ全体を送信し、各行を次に保存します。

もちろん、idをロックしてからデータを保存することもできますが、サーバーとDBに往復する必要があり、各行にDBを必要とするため、IDの要求を2倍にする必要があります。サーバ。

希望すると助かります!

P.D.コールバックの問題でループ変数を指摘するために@mathecに+1する!

+0

こんにちはJuanはローカルに保存されているので、サーバーに送信される心配はありません。私はあなたのID仮説を試してみるつもりですが、ちょっと大きな行(キー内のテキストの単なる段落)だけを追加しても何も追加されません。だから私はその要素の大きさと関係があると思う。 – user1389968

関連する問題