はい、私が知る限り、デフォルトのプール制限は10で、デフォルトのリクエストタイムアウトはリクエストごとに30秒ですが、タイムアウトとポーリングの制限は制御でき、ブラウザごとに異なる制限が実装されています。
このGoogleの実装をチェックしてください。
これは、タイムアウトエラーをキャッチする素晴らしい実装です!
Firefoxの詳細はここにあります!
Internet Explorerの詳細は、Windowsレジストリ内から制御されます。
この質問もご覧ください。
基本的に、制御する方法は、ブラウザーの制限を変更することではなく、それらを順守することです。したがって、スロットルと呼ばれる手法を適用します。
関数のFIFO/優先キューを作成することと考えてください。xhrリクエストをメンバーとして受け取り、それらの間の遅延を強制するキュー構造体はXhrPollです。たとえば、私はJsonpを使用して、別のドメインにあるnode.jsサーバーからデータを取得していますが、もちろんブラウザーの制限のためにポーリングしています。それ以外の場合、サーバーからの応答はゼロになります。これは、ブラウザーの制限によるものです。
私は実際に送信されることになっているすべてのリクエストに対してコンソールログを作成していますが、すべてがログに記録されているわけではありません。したがって、ブラウザはそれらを制限します。
私はあなたを助けることでさらに具体的になります。私のウェブサイトには、数十または数百の記事のビューを表示することになっているページがあります。あなたはクールな水平スライダーを使用してそれらを通過します。
スライダーの現在の値は、現在の「ページ」と一致します。1ページに5つの記事しか表示しておらず、パフォーマンスに深刻な影響を与えずに何千もの記事を「オンロード」で正確にロードすることはできないため、現在のページの記事をロードします。クロスドメインリクエストをPythonスクリプトに送信することで、MongoDBからそれらを取得します。
スクリプトは、「ページ」のDOM要素を構築するために必要なすべての詳細を含む5つのオブジェクトの配列を返すことになっています。ただし、いくつかの問題があります。
まず、スライダーは多かれ少なかれ値の変化であるため、非常に高速に動作します。ドラッグドロップ機能、キーダウンイベントなどがある場合でも、実際の変更にはミリ秒かかります。ただし、スライダーのコードは次のようになります。
goog.events.listen(slider, goog.events.EventType.CHANGE, function() {
myProject.Articles.page(slider.getValue());
}
Slider.getValue()メソッドは、現在のページ番号を含むintを返すため、基本的に次の場所からロードする必要があります。
currentPage * articlesPerPage to (currentPage * articlesPerPage + 1) - 1
しかし、ロードするために、私は次のようなことをします:私はストレージエンジンを持っています(それを配列と考えてください):
- コンテンツがまだないか確認します
- そうである場合は、別のリクエストを行う意味がないため、作成済みのDOM要素を配置した配列からDOM要素を取得してください。
そうでない場合は、取得する必要があるため、言及したリクエストを送信する必要があります。これは、(ブラウザーの制限を考慮せずに)次のようになります。
JSONP.send({'action':'getMeSomeArticles'、'start':start、'length':itemsPerPage、function(callback){
//コールバックをすばやく解析して、一貫性があることを確認します// DOM要素を作成し、//クライアント側のストレージにデータを入力して//ユーザーのビューを更新します。}}
問題は、そのスライダーを変更できる速度にあります。すべての変更がリクエストをトリガーすると思われるため(通常のXhrリクエストでも同じことが起こります)、基本的にすべてのブラウザーの制限を超えています。したがって、スロットルがなければ、ほとんどのリクエストに対して「コールバック」はありません。「コールバック」は、JSONPリクエストによって返されるJSコードです(これは、他の何よりもリモートスクリプトの包含です)。
つまり、私が行うことは、POLLではなく優先キューにリクエストをプッシュすることです。これで、複数のリクエストを同時に送信する必要がなくなりました。キューが空の場合、最近追加されたメンバーが実行され、全員が満足します。そうでない場合は、進行中の未完了のリクエストがすべてキャンセルされ、最後のリクエストのみが実行されます。
ここで、私の特定のケースでは、バイナリ検索(0(log n))を実行して、ストレージエンジンに前の要求のデータがまだないかどうかを確認します。これにより、前の要求が完了したかどうかがわかります。ある場合はキューから削除され、現在のキューが処理されます。そうでない場合は、新しいキューが起動します。などなど。
繰り返しになりますが、速度を考慮し、Internet Explorerなどのブラウザを使いたい場合は、上記の手順を約3〜4ステップ先に実行します。したがって、すべてがクライアント側のストレージエンジンになるまで、20ページ先にプリロードします。このようにして、すべての制限が正常に処理されます。
クールダウン時間は、20ページをスライドするのにかかる最小時間でカバーされ、スロットルは、常に1つ以下のアクティブな要求があることを確認します(Internet Explorer 5までの下位互換性があります)。
私がこれをすべて書いた理由は、FIFO構造から直接遅延を強制できるとは限らないという例を示すためです。これは、呼び出しがユーザーに表示されるものに変わる必要があり、正確に作成したくないためです。ユーザーは、1つのページがレンダリングされるまで10〜15秒待ちます。
また、常にポーリングとポーリングの必要性を最小限に抑えます(すべてのブラウザーが実際にそれらを使用して良いことを行うわけではないため、同時に発生するAjaxイベント)。たとえば、コンテンツを取得するために1つのリクエストを送信し、アプリの指標で表示されるようにそのコンテンツを追跡するために別のリクエストを送信するようなことを行う代わりに、サーバーレベルで可能な限り多くのタスクを実行します。
もちろん、おそらくエラーを適切に追跡したいので、選択したライブラリのXhrオブジェクトはajaxのエラー処理を実装します。あなたは素晴らしい開発者なので、それらを利用したいと考えています。
したがって、try-catchブロックが適切に配置されているとします。シナリオは次のとおりです。Ajax呼び出しが終了し、JSONを返すことになっていますが、呼び出しが何らかの理由で失敗しました。ただし、JSONを解析して、必要な処理を実行しようとします。それで
function onAjaxSuccess (ajaxResponse) {
try {
var yourObj = JSON.parse(ajaxRespose);
} catch (err) {
// Now I've actually seen this on a number of occasions, to log that an error occur
// a lot of developers will attempt to send yet another ajax request to log the
// failure of the previous one.
// for these reasons, workers exist.
myProject.worker.message('preferrably a pre-determined error code should go here');
// Then only the worker should again throttle and poll the ajax requests that log the
//specific error.
};
};
ブラウザーの制限に遭遇するまで、可能な限り多くのXhrリクエストを同時に起動しようとするさまざまな実装を見てきましたが、ブラウザーのクールダウンを待って起動されなかったリクエストを停止するのに非常に優れています。 '、私があなたにアドバイスできることは、次のことについて考えることです:
- アプリの速度はどれほど重要ですか?
- I / Oはどれだけスケーラブルでどれほど集中的になりますか?
前者の答えが「非常に」で、後者の「OMFGモダンテクノロジー」の答えである場合は、コードとアーキテクチャを可能な限り最適化して、10個の同時Xhrリクエストを送信する必要がないようにしてください。また、大規模なアプリの場合は、プロセスをマルチスレッド化します。これを実現するJavaScriptの方法は、ワーカーを使用することです。または、ECMAボードを呼び出して、これをデフォルトにするように指示し、ここに投稿して、残りのJS開発者がJSでネイティブマルチスレッドを楽しむことができるようにすることもできます:)(dafuqはこれについてどう思いませんでしたか?! ?!)