パフォーマンスを偽る隠されたAJAXリクエストはどれほど安全ですか?


48

隠されたAJAXリクエストとは何ですか?

ユーザーのアクションがすぐに発生するように見えるように設計された非表示のAJAXリクエストの使用が増加していることに気付きました。このタイプのAJAXリクエストを非ブロッキングと呼びます。これは、ユーザーに発生を認識せずに行われたAJAXリクエストであり、バックグラウンドで実行され、操作はサイレントです(AJAX呼び出しが正常に完了したことを示す詳細はありません)。目標は、操作が実際に終了していないときにすぐに発生したように見えるようにすることです。

ノンブロッキングAJAXリクエストの例を次に示します。

  • ユーザーがメールのコレクションで[削除]をクリックします。アイテムは受信トレイからすぐに消え、他の操作を続行できます。一方、AJAXリクエストはバックグラウンドでアイテムの削除を処理しています。
  • ユーザーが新しいレコードのフォームに入力します。保存をクリックします。新しいアイテムがリストにすぐに表示されます。ユーザーは引き続き新しいレコードを追加できます。

明確にするために、AJAX要求をブロックする例を次に示します。

  • ユーザーがメールのコレクションで[削除]をクリックします。砂時計カーソルが表示されます。AJAX要求が行われ、応答すると砂時計カーソルがオフになります。ユーザーは、操作が完了するまで1秒待つ必要があります。
  • ユーザーが新しいレコードのフォームに入力します。保存をクリックします。AJAXローダーをアニメーション化すると、フォームが灰色に変わります。「データが保存されました」というメッセージが表示され、新しいレコードがリストに表示されます。

上記の2つのシナリオの違いは、非ブロッキングAJAXセットアップでは動作のフィードバックが提供されないことと、ブロッキングAJAXセットアップでは提供されることです。

隠されたAJAXリクエストのリスク

このスタイルのAJAX要求の最大のリスクは、AJAX要求が失敗したときにWebアプリケーションがまったく異なる状態になる可能性があることです。

たとえば、非ブロッキングの例。

  • ユーザーは多数のメールを選択します。削除ボタンをクリックします。操作はすぐに行われるように見えます(項目はリストから消えます)。次に、ユーザーは[作成]ボタンをクリックして、新しいメールの入力を開始します。この時点で、JavaScriptコードがAJAXリクエストが失敗したことを発見します。スクリプトはエラーメッセージを表示する可能性がありますが、現時点では本当に意味がありません。

または、ブロッキングの例。

  • ユーザーは多数のメールを選択します。削除ボタンをクリックします。砂時計が見えますが、操作は失敗します。「error。blah blah blah」というエラーメッセージが表示されます。それらは電子メールのリストに戻り、削除したい電子メールが選択されたままです。彼らは再びそれらを削除しようとする可能性があります。

ノンブロッキングAJAXリクエストを実行するための他の技術的リスクもあります。ユーザーはブラウザを閉じ、別のWebサイトに移動し、現在のWebの別の場所に移動して、エラー応答のコンテキストを無意味にすることができます。

それで、なぜそんなに人気が出るのでしょうか?

Facebook、Google、Microsoftなど。これらの大規模なドメインはすべて、非ブロッキングAJAXリクエストを使用して、操作即座に実行されているように見せるようになっています。また、保存ボタンや送信ボタンのないフォームエディタが増えています。フィールドを出るかEnterキーを押すとすぐに。値が保存されます。プロフィールが更新されたというメッセージや保存手順はありません。

AJAXリクエストは確実ではなく、完了するまで成功として扱われるべきではありませんが、多くの主要なWebアプリケーションはそのように動作しています。

ノンブロッキングAJAX呼び出しを使用するこれらのWebサイトは、レスポンシブアプリケーションをシミュレートし、高速に表示されるという犠牲を払って不要なリスクを冒していますか?

これは、競争力を維持するために私たち全員が従うべき設計パターンですか?


20
これは、操作が成功する可能性がはるかに高いという事実によって正当化されるため、過度に楽観的なフィードバックのまれなケースを避けるためだけに遅くすることは悪いトレードオフです。個人的な関係に転じて、あなたはむしろ穏やかで日当たりの良い人や、うまく行かないものはすべてうまく行かず、それに応じて行動することを断固として想定している人と対話しますか?
キリアンフォス

1
私にとって苦労しているのは、デスクトップアプリケーションの操作とエラーの両方がすぐに発生することです。Webアプリケーションでは、操作はすぐに行われますが、エラーは遅れます。それでも、サイトはデスクトップアプリケーションの設計で動作します。
-Reactgular

7
また、デスクトップアプリケーションがディスクに書き込み、実際にOSバッファーに書き込まれ、ディスクがプラッターに書き込まれる前に障害が発生した場合に何が起こるかを検討しましたか?または、バイトがプラッターに書き込まれた後、ディスクが故障します。どちらの場合でも、ユーザー、実際に発生していないときに何かが発生したと考えます。
kdgregory

2
@KilianFoth「晴れた」人があなたをpunchり、トラブルの最初の兆候であなたの財布を盗もうとするなら、私はすべてがうまくいかないことを想定している人を好むでしょう。そのため、失敗時のページの反応の規模に依存します。
イズカタ

1
@ButtleButkus保存メッセージは新しいものだと思います。私が質問したとき、彼らはそこにいませんでした。グーグルが最近フィードバックを追加していることに気づきました。それはバックグラウンドで何かをしているということです。
Reactgular 14年

回答:


62

実際の応答性ほど「偽」のパフォーマンスではありません。人気がある理由はいくつかあります。

  • 現在、インターネット接続はかなり信頼できます。AJAXリクエストが失敗するリスクは非常に低いです。
  • 実行される操作は、実際には安全上重要ではありません。サーバーでメールが削除されない場合、最悪の事態は、次にページにアクセスしたときに再度削除する必要があることです。
  • 要求が失敗した場合にアクションを取り消すようにページを設計できますが、サーバーへの接続が切断されることを意味するため、それほど微妙である必要はありません。「接続が失われました。最近の変更を保存できません。しばらくしてからもう一度お試しください」と言う方が簡単です。
  • 保留中のAJAXリクエストを1つだけ許可するようにページを設計することができるため、サーバーから状態が同期しなくなることはありません。
  • AJAXリクエストが保留中のときにページを閉じたり、ページから移動しようとすると、ブラウザは警告を表示します。

AJAX保留中の警告


8
最後のポイントは、すべてのブラウザがデフォルトでそれを行うのですか?
スビッシュ

知りません。IE9と最新のchromeでのみテストしました。
カールBielefeldt

3
あなたは明らか...移動中の車両にも、モバイル、場所をない発展、貧困層に言及し、オーストラリアのインターネットに精通し、絶縁されていません
ヒッピー・トレイル

2
@hippietrailさて、あなたはいつもみんなを幸せにすることはできません。
コビコ

1
ユーザーがリクエストを送信するとき、常に新しいページを要求するわけではありません。適切に設計されたAJAXアプリケーションは、それらをより楽しくし、リロードよりも効率的に何が起こっているかをユーザーに知らせることができると思います。
Frederik.L

32

何かが機能すると仮定し、リモート側で失敗した場合にエラーを表示することは、サーバーからの応答があるまでユーザーが他の操作をブロックするよりもはるかにユーザーフレンドリーです。

実際には、電子メールクライアントはこれの優れた例です。5つの電子メールを含むリストがあり、一番上の電子メールを選択すると、DEL3回ヒットすると最初の3つの電子メールが削除されます。「ノンブロッキングAJAX」では、これは正常に機能します。キーを押すたびに、選択した電子メールがすぐに削除されます。何か問題が発生した場合、エラーが表示され、正しく削除されていない電子メールが再び表示されるか、ページが再ロードされて一貫性のないローカル状態が取り除かれます。

そのため、最も一般的なケース -成功-では、使いやすさが向上します。では珍しいケース -故障-ユーザビリティが低下している(再び要素ショーを削除したり、アプリケーションを「再起動」される)がありますが、通常は一般的なケースのために、ないエラーが発生した場合の最高の使いやすさを持つようにしたいアプリケーションを作成するとき。


1
+1これは問題の中心にあるスポットです。デフォルトでは人々が非常に安全であるため、最悪の場合でも本当のユーザーのミスをリスクにさらすことはありません。メールクライアントが削除に失敗し、ローカル状態が悪いと想像してください。サーバーでは、大部分のバックエンド開発者がそこに安全なキャッチがあり、ユーザーが絶対に望むものだけを削除することを保証するため、この不整合は誤った削除を引き起こしません(エラーで失敗するかもしれませんが、削除しません) 。
ジミー・ホッファ

@JimmyHoffaでは、削除リクエストで一意のメールIDを使用します。受信ボックス内の電子メールの任意の表示順序に基づいて削除要求を送信するのは本当に悪いでしょう。
バトルビュータス14年

14

ユーザーは、あなたのソフトウェアが舞台裏で何をしているのか気にしません。彼らは自分の行動に目に見える影響を与え、自分のペースで作業できるようにしたいのです。

メールの削除など、クライアント側でアクションが成功した場合、サーバー側でも同様に成功させるのはあなたの仕事です。削除が失敗したのはなぜですか?何らかの制限が原因である場合(たとえば、アーカイブされたメールを削除することはできません)、ユーザーはアクションが失敗する前にそのことを認識しておく必要があります。

エラーの原因がより重大なもの(データベースのクラッシュなど)である場合は、操作を保存して、システムが再起動したときに再試行する方法が必要です。

これを管理する良い例は、Facebookがチャットを処理する方法です。ユーザーが突然切断することを止める方法はありません。つまり、ユーザーが送信する前に送信したメッセージを読むことができなくなります。エラーを表示する代わりに、システムはそれらすべてのメッセージを保存し、ユーザーが戻ってきたときにそれらを利用できるようにします。データは失われません。


2
+1。優れたチャット例。ほとんどのユーザーは、メッセージがすぐにすべての人に利用可能になることを期待しています。そのようなメッセージが失敗することはめったにないため、ユーザーはそのような錯覚を与えられます。
ニール

1
@Niphra、「なぜ削除に失敗したのですか?」ネットワークはさまざまな理由で失敗する可能性がありますが、アプリケーションとは関係ありません。それを止めるためにできることは何もありません。
パセリエ

5

2つのオプションの間で妥協することができます。たとえば、ユーザーがメールを削除した場合、サーバーから確認が返されるまで赤または灰色でマークしてから、リストから削除することができます。ユーザーは、1つのアクションが保留中に他のことを実行できるため、ブロックされませんが、アクションがまだコミットされていないことをユーザーに少し思い出させます。

Amazon AWSはこのアプローチを取ります:インスタンスを停止/開始すると、それを選択できるチェックボックスがスピナーに変わります(したがって、数秒間は何もできません)が、これはあなたをブロックしません他のインスタンスとの対話。


あなたの提案は、GmailがXHRの進行中に「保存中...」というテキストを表示し、終了後に「保存済み」と表示するのと似ています。常に「保存済み」と表示されている場合、誰がそれを信じますか?
バトルビュータス14年

3

これは、従来のサイトよりも、アプリケーションのように振る舞い、ブラウザでより多くの処理(フォームデータの検証など)を試みるWebサイトが増えてくると思います。あなたのコードが信頼でき、通常の条件下で成功することを期待できる限り、あまり問題はありません。

「この時点で、JavaScriptコードがAJAXリクエストが失敗したことを発見しました。スクリプトはエラーメッセージを表示する可能性がありますが、現時点では本当に意味がありません。」

なぜ無意味なのでしょうか?メールのリストに戻り、削除を再度実行できます。代わりに待つのはなぜですか?実際には「リスク」はあまりなく、高速に「見える」わけではなく、実際には高速に動作します。では、アクティビティが「クリティカル」でない場合、なぜ遅いのでしょうか?


1
無意味な言葉は正しい言葉ではないかもしれませんが、エラーメッセージには相対的なコンテキストが欠けているということです。ユーザーは今やまったく違うことをしているからです。私が言いたいのは、無知なウェブユーザーにとって、彼らはメールが正常に削除されたと思ったということです。なぜ今、後で、「見た」何かが削除されたというエラーメッセージが表示されます。プログラマーにとっては理解できますが、Gmailを使用するおじいちゃんにとっては理解できません。
-Reactgular

ほとんどの人は、物事がすぐに発生し、システムが応答し、値を変更するたびに1秒間フリーズするアプリケーションよりもエラーでUIが奇妙な方法で更新される可能性がある10,000分の1の確率でアプリケーションを使用します。
ロボット

1

私の2cは、「非ブロッキング」Ajaxオペレーションなど、設計の選択が不適切な場合があります。例:YouTubeビデオの投票。そこから始まる小さなアイコンをクリックする間、ページのどの部分もブロックされたくないのです。黙って失敗する方が良い。確認メッセージでさえも殺されてしまいます。ただし、電子メールを削除する場合の例は、ブロッキングタイプのAjaxリクエストに必須と見なされます。

Mongo DBはそのようなことをします(これはデスクトップアプリケーションの例と見なすことができます)。オペレーションにはさまざまな「懸念事項」があり、「すぐに戻って何も待たない」から「ネットワーク転送が成功したことを確認するまでブロックする」まで、オペレーションごとに異なる値に設定できます。その後、「戻る前に、コンテンツがリモートマシンのディスク書き込み用に適切にスケジュールされるまで待機する」に戻ります。明らかに、Mongoドライバーを使用してデスクトップシッククライアント(C ++など)を作成する場合、最小限の "重要度"(新しい電子メールのチェックなど)のdb操作に対して最も軽い書き込みの懸念を設定します。 。

ノンブロッキングAjaxの有用性はわかりますが、あまりにも多くのことが起こっていることに同意します。ある時点で、写真のアップロードのためにこれを行う少なくとも1つの有名な「ソーシャルネットワーキング」サイトがありました。アップロードする写真を選択してからバムし、すぐにそれが完了したことを伝え、さらに翌日あなたがいくつかの写真を追加したいとき(または既に追加したと思ったものを使用するとき)決して見つけられなかった。後で彼らはこれをあきらめ、実際に応答を待つ時間を取りました(そして、実際には「写真のアップロードに失敗しました。後で試してください」などのメッセージが表示されることがあります)。


私のやり方で物事を見るための+1 :)。写真のアップロードは失敗の良い例です。
Reactgular

1
ブロックするアップロードが望ましいのはなぜですか?Picasa(ウェブインターフェース)では、写真をドラッグして、バックグラウンドでアップロードしながら、さらにドラッグしたり、終了した写真にタグを付けたりできます。アップロード操作をブロックすると、恐ろしいUX
BLSully
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.