HTTP/2 は、HTTP/1.1 の複雑なインフラストラクチャの維持によって生じる苦痛を軽減することを目的としており、優れたパフォーマンスを備えています。 HTTP/2 は依然として HTTP/1.1 との下位互換性がありますが、テキストベースのプロトコルではなくなりました。
HTTP/2 多重化により、単一の接続で複数の双方向ストリームを処理できるようになり、クライアントは単一の接続で複数のリソースを同時にダウンロードできるようになります。
HTTP 1.x プロトコルはテキストベースであるため、メッセージは非常に長くなります。場合によっては、同じ HTTP ヘッダーのセットが何度も交換されることがあります。 HTTP/2 はリクエスト全体で HTTP ヘッダーを維持するため、データの繰り返し交換が不要になり、データのやり取りに必要な帯域幅が大幅に削減されます。
HTTP/2 のサーバー側データ プッシュは、WebSocket への継続またはアップグレードであると思われるかもしれませんが、そうではありません。 WebSocket は、TCP 接続が確立された後にサーバーがクライアントにデータを送信する、クライアントとサーバー間の全二重通信の方法ですが、HTTP/2 は異なるソリューションを提供します。
HTTP/2 プッシュは、クライアントの観点からリソース要求を開始せずに、リソースをクライアントにアクティブに送信することです。これは、サーバーが、Web サイトがさらに必要とする他のリソースをリクエストから認識し、クライアントが再度リクエストするずっと前に、それらをすべてまとめて (事前に) 送信できることを意味します。
#現在 HTTP/2 をサポートしている Java HTTP クライアントOkHttp
##Vert.xx
Firefly
ただし、この記事では、これらの Java クライアント ソフトウェアを導入しますが、Java9 によって提供される HTTP/2 サポートも導入します。
最初に Java 9 構文を使用してモジュールをインポートします。
jdk.incubator.httpclientmodule com.springui.echo.client { requires jdk.incubator.httpclient; }
Java 9 の新しい HTTP Cient API はビルダー パターンに従います。 HttpClient は、HTTP リクエストを操作するために使用されるエントリ ポイントであり、最初に構築されてから使用されます。 <pre class="brush:java;">HttpClient client = HttpClient
.newBuilder()
.version(Version.HTTP_2) //支持HTTP2
.build();</pre>
ブロッキング モードでのリクエストの送信
HttpClient インスタンスを取得したら、それを使用して HttpRequest を送信できます。HttpRequest インスタンスは、コンストラクターを使用して作成することもできます。
HttpResponse<String> response = client.send( HttpRequest .newBuilder(TEST_URI) //请求地址 .POST(BodyProcessor.fromString("Hello world")) //POST报文数据 .build(), BodyHandler.asString() //请求响应数据处理,接收字符串 );
ノンブロッキング モードでのリクエストの送信 (Java 9)
次の例では、10 個のランダムな整数が非同期に送信されます。
List<CompletableFuture<String>> responseFutures = IntStream.of(1,2,3,4,5,6,7,8,9,10) //10个整数形成IntStream,Java 8的语法 .mapToObj(String::valueOf) //10个整数转换成字符串,Java 8的语法 .map(message -> client.sendAsync( //将10个整数字符串作为内容,发送10个异步请求 HttpRequest.newBuilder(TEST_URI) .POST(HttpRequest.BodyProcessor.fromString(message)) .build(), HttpResponse.BodyHandler.asString() ).thenApply(HttpResponse::body) //以CompletableFuture<HttpResponse.body()>作为流处理的返回值 ) .collect(Collectors.toList()); //将Stream转成List
sendAsync メソッドの戻り値 CompletableFuture721c5bd4f0360fdcda122bb99928a389> は、thenApply(HttpResponse::body) を使用してさらに処理され、最終的な戻り値は CompletableFuturef7e83be87db5cd2d9a8a0b8117b38cd4 になります。
CompletableFuture は、同時非同期処理の結果を出力する Java 非同期プログラミングの知識です。
responseFutures.stream().forEach(future -> { LOGGER.info("Async response: " + future.getNow(null)); });
すべてのリクエストが非同期で送信されるため、最終的な印刷ログは 1、2、3、4、5、6、7、8、9、10 の順序で処理されない可能性があることがわかります。返される結果は、非同期処理に使用される CompletableFuture の結果です。
3. HTTP2 をサポートする Push-Promise フレーム
上記の例はすべて HTTP/1.1 プロトコルで完了できますが、新しいノンブロッキング非同期 API が追加され、HTTP/2特徴。心配しないでください。Java 9 クライアント API は HTTP/2 と最も緊密に統合されています。HTTP2 を使用してリクエストを送信し、複数の非同期データ結果を取得できます。 (一部のデータは事前にプッシュされます。もちろん、これにはサーバーが連携のために HTTP/2 もサポートしている必要があります)
Map<HttpRequest,CompletableFuture<HttpResponse<String>>> responses = client.sendAsync( //注意这里只发送一次请求 HttpRequest.newBuilder(TEST_URI) .POST(HttpRequest.BodyProcessor.fromString(TEST_MESSAGE)) .build(), HttpResponse.MultiProcessor.asMap( //多个资源的响应结果 request -> Optional.of(HttpResponse.BodyHandler.asString()) ) ).join(); responses.forEach((request, responseFuture) -> { LOGGER.info("Async response: " + responseFuture.getNow(null)); });
以上がJava 9 の HTTP2 プロトコルのサポートとノンブロッキング HTTP API 分析の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。