Merge branch 'jetty-9.4.x'
This commit is contained in:
commit
bfeedc6f5e
|
@ -17,15 +17,6 @@
|
|||
[[alpn]]
|
||||
=== Introducing ALPN
|
||||
|
||||
The development of new web protocols such as HTTP/2 raised the need of protocol negotiation within a Transport Layer Security (TLS) handshake.
|
||||
A protocol negotiation called https://tools.ietf.org/html/rfc7301[ALPN] (Application Layer Protocol Negotiation) RFC7301 has been defined to accomplish this.
|
||||
|
||||
ALPN has now replaced the older (and now fully deprecated) NPN in the general Web of 2016.
|
||||
|
||||
For those browsers that support HTTP/2, they all now support the ALPN negotiation layers for TLS.
|
||||
|
||||
Starting with Jetty 9.3.0, only ALPN is supported by Jetty.
|
||||
|
||||
The Jetty project provides an implementation of the TLS extension for ALPN for OpenJDK 7 and OpenJDK 8.
|
||||
ALPN allows the application layer to negotiate which protocol to use over the secure connection.
|
||||
|
||||
|
@ -35,7 +26,7 @@ The ALPN implementation is therefore not HTTP/2 or SPDY specific in any way.
|
|||
Jetty's ALPN implementation, although hosted under the umbrella of the Jetty project, is independent of Jetty (the Servlet Container); you can use the ALPN implementation in any other Java network server.
|
||||
|
||||
The Jetty distribution will automatically enable ALPN when it is needed to by a HTTP/2 connector, so for the most part ALPN is transparent to the average deployer.
|
||||
This section provides the detail required for unusual deployments or developing to the ALPN API.
|
||||
This section provides the detail required for non-standard deployments or developing to the ALPN API.
|
||||
|
||||
[[alpn-starting]]
|
||||
==== Starting the JVM
|
||||
|
@ -47,14 +38,14 @@ To enable ALPN support, start the JVM as follows:
|
|||
java -Xbootclasspath/p:<path_to_alpn_boot_jar> ...
|
||||
----
|
||||
|
||||
where `path_to_alpn_boot_jar` is the path on the file system for the ALPN Boot Jar file, for example, one at the Maven coordinates `org.mortbay.jetty.alpn:alpn-boot`.
|
||||
Where `path_to_alpn_boot_jar` is the path on the file system for the ALPN Boot Jar file,such as the one at the Maven coordinates `org.mortbay.jetty.alpn:alpn-boot`.
|
||||
|
||||
Be certain link:#alpn-versions[to get the ALPN Boot Jar version which matches the version of your JRE].
|
||||
|
||||
[[alpn-osgi]]
|
||||
===== Starting in OSGi
|
||||
|
||||
To use ALPN in an OSGi environment, in addition to putting the ALPN jar on the boot classpath for the container, you will also need to deploy the jetty-osgi-alpn jar.
|
||||
To use ALPN in an OSGi environment, in addition to putting the ALPN jar on the boot classpath for the container, you will also need to deploy the `jetty-osgi-alpn` jar.
|
||||
This jar contains a Fragment-Host directive that ensures the ALPN classes will be available from the system bundle.
|
||||
|
||||
You can download the http://central.maven.org/maven2/org/eclipse/jetty/osgi/jetty-osgi-alpn/[jetty-osgi-alpn jar] from Maven Central.
|
||||
|
@ -67,7 +58,7 @@ For example, server applications need to know whether the client supports ALPN,
|
|||
|
||||
To implement this interaction, Jetty's ALPN implementation provides an API to applications, hosted at Maven coordinates
|
||||
`org.eclipse.jetty.alpn:alpn-api`.
|
||||
You need to declare this dependency as provided, because the `alpn-boot` Jar already includes it (see the previous section), and it is therefore available from the boot classpath.
|
||||
You need to declare this dependency as provided, because the `alpn-boot` jar already includes it (see the previous section), and it is therefore available from the boot classpath.
|
||||
|
||||
The API consists of a single class, `org.eclipse.jetty.alpn.ALPN`, and applications need to register instances of `SSLSocket` or `SSLEngine` with a `ClientProvider` or `ServerProvider` (depending on whether the application is a client application or server application).
|
||||
Refer to `ALPN` Javadocs and to the examples below for further details about client and server provider methods.
|
||||
|
@ -111,10 +102,10 @@ ALPN.put(sslSocket, new ALPN.ClientProvider()
|
|||
|
||||
The ALPN implementation calls `ALPN.ClientProvider` methods `supports()`, `protocols()`, `unsupported()` and `selected(String)`, so that the client application can:
|
||||
|
||||
* decide whether to support ALPN.
|
||||
* provide the protocols supported.
|
||||
* know whether the server supports ALPN.
|
||||
* know the protocol chosen by the server.
|
||||
* Decide whether to support ALPN
|
||||
* Provide the protocols supported
|
||||
* Know whether the server supports ALPN
|
||||
* Know the protocol chosen by the server
|
||||
|
||||
[[alpn-server-example]]
|
||||
==== Server Example
|
||||
|
@ -197,7 +188,7 @@ You can enable debug logging for the ALPN implementation in this way:
|
|||
ALPN.debug = true;
|
||||
....
|
||||
|
||||
Since the ALPN class is in the boot classpath, we chose not to use logging libraries because we do not want to override application logging library choices; therefore the logging is performed directly on `System.err.`
|
||||
Since the ALPN class is in the boot classpath, we chose not to use logging libraries because we do not want to override application logging library choices; therefore the logging is performed directly on `System.err`.
|
||||
|
||||
[[alpn-license-details]]
|
||||
==== License Details
|
||||
|
@ -265,7 +256,6 @@ $ hg clone http://hg.openjdk.java.net/jdk7u/jdk7u jdk7u # OpenJDK 7
|
|||
$ hg clone http://hg.openjdk.java.net/jdk8u/jdk8u jdk8u # OpenJDK 8
|
||||
$ cd !$
|
||||
$ ./get_source.sh
|
||||
|
||||
....
|
||||
|
||||
To update the source to a specific tag, use the following command:
|
||||
|
@ -276,8 +266,6 @@ $ ./make/scripts/hgforest.sh update <tag-name>
|
|||
|
||||
....
|
||||
|
||||
The list of OpenJDK tags can be obtained from these pages:
|
||||
http://hg.openjdk.java.net/jdk7u/jdk7u/tags[OpenJDK 7] /
|
||||
http://hg.openjdk.java.net/jdk8u/jdk8u/tags[OpenJDK 8].
|
||||
The list of OpenJDK tags can be obtained from these pages: http://hg.openjdk.java.net/jdk7u/jdk7u/tags[OpenJDK 7] / http://hg.openjdk.java.net/jdk8u/jdk8u/tags[OpenJDK 8].
|
||||
|
||||
Then you need to compare and incorporate the OpenJDK source changes into the modified OpenJDK classes at the https://github.com/jetty-project/jetty-alpn[ALPN GitHub Repository], branch `openjdk7` for OpenJDK 7 and branch `master` for OpenJDK 8.
|
||||
You will then need to compare and incorporate the OpenJDK source changes into the modified OpenJDK classes at the https://github.com/jetty-project/jetty-alpn[ALPN GitHub Repository], branch `openjdk7` for OpenJDK 7 and branch `master` for OpenJDK 8.
|
||||
|
|
|
@ -15,6 +15,14 @@
|
|||
// ========================================================================
|
||||
|
||||
[[alpn-chapter]]
|
||||
== ALPN
|
||||
== Application Layer Protocol Negotiation (ALPN)
|
||||
|
||||
The development of new web protocols such as HTTP/2 raised the need of protocol negotiation within a Transport Layer Security (TLS) handshake.
|
||||
A protocol negotiation called https://tools.ietf.org/html/rfc7301[ALPN] (Application Layer Protocol Negotiation) RFC7301 has been defined to accomplish this.
|
||||
|
||||
ALPN has now replaced the older (and now fully deprecated) NPN in the general Web of 2016.
|
||||
|
||||
For those browsers that support HTTP/2, they all now support the ALPN negotiation layers for TLS.
|
||||
Starting with Jetty 9.3.0, only ALPN is supported by Jetty.
|
||||
|
||||
include::alpn.adoc[]
|
||||
|
|
|
@ -17,13 +17,13 @@
|
|||
[[http2-configuring-haproxy]]
|
||||
=== Configuring HAProxy and Jetty
|
||||
|
||||
Typical website deployments have Apache (or Nginx) configured as reverse proxy to talk to one or more backend Jetty instances.
|
||||
Typical website deployments have Apache (or Nginx) configured as reverse proxy to talk to one or more backend Jetty instances.
|
||||
This configuration cannot be used for HTTP/2 because Apache does not yet support HTTP/2 (nor does Nginx).
|
||||
|
||||
http://haproxy.org[HAProxy] is an open source solution that offers load balancing and proxying for TCP and HTTP based application, and can be used as a replacement for Apache (or Nginx) when these are used as reverse proxies, and has the major benefit that supports HTTP/2.
|
||||
It also offers load balancing and a ton of other features, so you can probably use it as a replacement for Apache (or Nginx).
|
||||
http://haproxy.org[HAProxy] is an open source solution that offers load balancing and proxying for TCP and HTTP based application, and can be used as a replacement for Apache or Nginx when these are used as reverse proxies and has the major benefit that supports HTTP/2.
|
||||
It also offers load balancing and several other features which can position it as a complete replacement for Apache or Nginx.
|
||||
|
||||
The deployment proposed here will have HAProxy play the role that Apache (or Nginx) usually do: to perform the TLS offloading (that is, decrypt and encrypt TLS) and then forwarding the now clear-text traffic to a backend Jetty server, speaking either HTTP/1.1 or HTTP/2.
|
||||
The deployment proposed here will have HAProxy play the role that Apache and Nginx usually do: to perform the TLS offloading (that is, decrypt and encrypt TLS) and then forwarding the now clear-text traffic to a backend Jetty server, speaking either HTTP/1.1 or HTTP/2.
|
||||
|
||||
The instructions that follow are for Linux.
|
||||
|
||||
|
@ -32,20 +32,18 @@ The instructions that follow are for Linux.
|
|||
|
||||
You will need HAProxy 1.5 or later, because it provides support for SSL and ALPN, both required by HTTP/2. Most Linux distributions have the HAProxy package available to be installed out of the box. For example on Ubuntu 15.04:
|
||||
|
||||
[source,shell]
|
||||
----
|
||||
[source,screen, subs="{sub-order}"]
|
||||
....
|
||||
$ sudo apt-get install haproxy
|
||||
|
||||
----
|
||||
....
|
||||
|
||||
Alternatively you can download the HAProxy source code and build it on your environment, by following the README bundled with the HAProxy source code tarball.
|
||||
Alternatively you can download the HAProxy source code and build it on your environment by following the README bundled with the HAProxy source code tarball.
|
||||
|
||||
____
|
||||
[NOTE]
|
||||
HAProxy supports ALPN only if built with OpenSSL 1.0.2 or greater.
|
||||
Alternatively, HAProxy supports NPN when built with OpenSSL 1.0.1 or greater.
|
||||
HAProxy supports ALPN only if built with OpenSSL 1.0.2 or greater.
|
||||
Alternatively, HAProxy supports NPN when built with OpenSSL 1.0.1 or greater.
|
||||
You must upgrade OpenSSL if you have a version earlier than 1.0.1.
|
||||
|
||||
Use `haproxy -vv` to know with which OpenSSL version HAProxy has been built.
|
||||
____
|
||||
|
||||
|
@ -56,7 +54,7 @@ HAProxy will perform the TLS decryption and encryption much more efficiently tha
|
|||
|
||||
HAProxy will need a single file containing the X509 certificates and the private key, all in https://en.wikipedia.org/wiki/X.509[PEM format], with the following order:
|
||||
|
||||
1. The site certificate; this certificate's Common Name refers to the site domain (for example: CN=*.webtide.com) and it's signed by Certificate Authority #1.
|
||||
1. The site certificate; this certificate's Common Name refers to the site domain (for example: CN=*.webtide.com) and is signed by Certificate Authority #1.
|
||||
2. The Certificate Authority #1 certificate; this certificate may be signed by Certificate Authority #2.
|
||||
3. The Certificate Authority #2 certificate; this certificate may be signed by Certificate Authority #3; and so on until the Root Certificate Authority.
|
||||
4. The Root Certificate Authority certificate.
|
||||
|
@ -64,8 +62,8 @@ HAProxy will need a single file containing the X509 certificates and the private
|
|||
|
||||
Let's use `keytool` to generate a self signed certificate:
|
||||
|
||||
[source,shell]
|
||||
----
|
||||
[source,screen, subs="{sub-order}"]
|
||||
....
|
||||
$ keytool -genkeypair -keyalg RSA -keystore keystore.p12 -storetype pkcs12 -storepass storepwd -ext SAN=DNS:domain.com
|
||||
What is your first and last name?
|
||||
[Unknown]: *.domain.com
|
||||
|
@ -81,44 +79,41 @@ What is the two-letter country code for this unit?
|
|||
[Unknown]: IT
|
||||
Is CN=*.domain.com, OU=Unit, O=Domain, L=Torino, ST=TO, C=IT correct?
|
||||
[no]: yes
|
||||
|
||||
----
|
||||
....
|
||||
|
||||
The above command will generate a self signed certificate and private key for `domain.com` and subdomains, stored in the `keystore.p12` file in PKCS#12 format.
|
||||
The above command will generate a self signed certificate and private key for `domain.com` and subdomains, stored in the `keystore.p12` file in PKCS#12 format.
|
||||
We need to extract the certificate and the private key in PEM format.
|
||||
|
||||
To extract the certificate into `certificate.pem`:
|
||||
|
||||
[source,shell]
|
||||
----
|
||||
[source,screen, subs="{sub-order}"]
|
||||
....
|
||||
$ keytool -exportcert -keystore keystore.p12 -storetype pkcs12 -storepass storepwd -rfc -file certificate.pem
|
||||
|
||||
----
|
||||
....
|
||||
|
||||
To export the private key into `private_key.pem`:
|
||||
|
||||
[source,shell]
|
||||
----
|
||||
[source,screen, subs="{sub-order}"]
|
||||
....
|
||||
$ openssl pkcs12 -in keystore.p12 -nodes -nocerts -out private_key.pem -passin pass:storepwd
|
||||
|
||||
----
|
||||
....
|
||||
|
||||
At this point you just need to concatenate the two files into one, in the correct order:
|
||||
|
||||
[source,shell]
|
||||
----
|
||||
[source,screen, subs="{sub-order}"]
|
||||
....
|
||||
$ cat certificate.pem private_key.pem > domain.pem
|
||||
|
||||
----
|
||||
....
|
||||
|
||||
The `domain.pem` file will be used later by HAProxy.
|
||||
|
||||
[[http2-haproxy-cfg]]
|
||||
==== HAProxy Configuration File
|
||||
|
||||
Now we can setup `haproxy.cfg` to configure HAProxy.
|
||||
Now we can setup `haproxy.cfg` to configure HAProxy.
|
||||
This is a minimal configuration:
|
||||
|
||||
[source, ,subs="{sub-order}"]
|
||||
....
|
||||
global
|
||||
tune.ssl.default-dh-param 1024
|
||||
|
@ -142,56 +137,53 @@ default_backend be_http
|
|||
backend be_http
|
||||
mode tcp
|
||||
server domain 127.0.0.1:8282
|
||||
|
||||
....
|
||||
|
||||
The HAProxy configuration file works in the following way.
|
||||
The HAProxy configuration file works in the following way.
|
||||
The `fe_http` front-end accepts connections on port 80 and redirects them to use the `https` scheme.
|
||||
|
||||
The `fe_https` front-end accepts connections on port 443 and it is where the TLS decryption/encryption happens.
|
||||
You must specify the path to the PEM file containing the TLS key material (the `crt domain.pem` part), the ciphers that are suitable for HTTP/2 (the `ciphers TLSv1.2` part), and the ALPN (or NPN if you are using old OpenSSL versions) protocols supported (the `alpn h2,http/1.1` part).
|
||||
This front-end then forwards the now decrypted bytes to the back-end in `mode tcp`. The `mode tcp`) means that HAProxy will not try to interpret the bytes as HTTP/1.1 but just opaquely forward them to the back-end.
|
||||
The `fe_https` front-end accepts connections on port 443 and it is where the TLS decryption/encryption happens.
|
||||
You must specify the path to the PEM file containing the TLS key material (the `crt domain.pem` part), the ciphers that are suitable for HTTP/2 (the `ciphers TLSv1.2`), and the ALPN protocols supported (the `alpn h2,http/1.1` ).
|
||||
This front-end then forwards the now decrypted bytes to the back-end in `mode tcp`. The `mode tcp` says that HAProxy will not try to interpret the bytes as HTTP/1.1 but instead opaquely forward them to the back-end.
|
||||
|
||||
The `be_http` back-end will forward (again in `mode tcp`) the clear-text bytes to a Jetty connector that talks clear-text HTTP/2 and HTTP/1.1 on port 8282.
|
||||
|
||||
[[http2-haproxy-jetty]]
|
||||
==== Setup Jetty for HTTP/2 and HTTP/1.1
|
||||
|
||||
The Jetty setup follows the usual steps of having Jetty installed in the `JETTY_HOME` directory, creating a `JETTY_BASE` directory and initializing it using Jetty's command line tools.
|
||||
You must enable the `http2c` module, that is the module that speaks clear-text HTTP/2.
|
||||
The Jetty setup follows the steps of having Jetty installed in the `JETTY_HOME` directory, creating a `JETTY_BASE` directory and initializing it using Jetty's command line tools.
|
||||
You must enable the `http2c` module, that is the module that speaks clear-text HTTP/2.
|
||||
Since the `http2c` module depends on the `http` module, the `http` module will be enabled transitively, and the final setup will therefore support both HTTP/2 and HTTP/1.1 in clear text.
|
||||
|
||||
Additionally, you will also enable the `deploy` module to be able to deploy a sample web application:
|
||||
|
||||
[source,shell]
|
||||
----
|
||||
[source,screen, subs="{sub-order}"]
|
||||
....
|
||||
$ JETTY_BASE=haproxy-jetty-http2
|
||||
$ mkdir $JETTY_BASE
|
||||
$ cd $JETTY_BASE
|
||||
$ java -jar $JETTY_HOME/start.jar --add-to-start=http2c,deploy
|
||||
|
||||
----
|
||||
....
|
||||
|
||||
Now let's deploy a demo web application and start Jetty:
|
||||
|
||||
[source,shell]
|
||||
----
|
||||
[source,screen, subs="{sub-order}"]
|
||||
....
|
||||
$ cd $JETTY_BASE
|
||||
$ cp $JETTY_HOME/demo-base/webapps/async-rest.war $JETTY_BASE/webapps/
|
||||
$ java -jar $JETTY_HOME/start.jar jetty.http.host=127.0.0.1 jetty.http.port=8282
|
||||
|
||||
----
|
||||
....
|
||||
|
||||
Now you can browse https://domain.com/async-rest (replace `domain.com` with your own domain, or with `localhost`, to make this example work).
|
||||
|
||||
____
|
||||
[NOTE]
|
||||
You want the Jetty connector that listens on port 8282 to be available only to HAProxy, and not to remote clients.
|
||||
For this reason, you want to specify the `jetty.http.host` property on the command line (or in `start.ini` to make this setting persistent) to bind the Jetty connector only on the loopback interface (127.0.0.1), making it available to HAProxy but not to remote clients.
|
||||
For this reason, you want to specify the `jetty.http.host` property on the command line (or in `start.ini`/ `start.d/http.ini` to make this setting persistent) to bind the Jetty connector only on the loopback interface (127.0.0.1), making it available to HAProxy but not to remote clients.
|
||||
If your Jetty instance runs on a different machine and/or on a different (sub)network, you may want to adjust both the back-end section of the HAProxy configuration file and the `jetty.http.host` property to match accordingly.
|
||||
____
|
||||
|
||||
Browsers supporting HTTP/2 will connect to HAProxy, which will decrypt the traffic and send it to Jetty.
|
||||
Browsers supporting HTTP/2 will connect to HAProxy, which will decrypt the traffic and send it to Jetty.
|
||||
Likewise, HTTP/1.1 clients will connect to HAProxy, which will decrypt the traffic and send it to Jetty.
|
||||
|
||||
The Jetty connector, configured with the `http2c` module (and therefore transitively with the `http` module) is able to distinguish whether the incoming bytes are HTTP/2 or HTTP/1.1 and will handle the request accordingly.
|
||||
|
|
|
@ -17,16 +17,16 @@
|
|||
[[http2-configuring]]
|
||||
=== Configuring HTTP/2
|
||||
|
||||
Enabling the HTTP/2 module in the jetty server does not create a HTTP/2 specific connector, but rather it adds a HTTP/2 Connection factory to an
|
||||
existing connector.
|
||||
Thus configuring HTTP/2 is a combination of configuring common properties on the connector and HTTP/2 specific properties on the connection factory.
|
||||
Enabling the HTTP/2 module in the Jetty server does not create a HTTP/2 specific connector, but rather it adds a HTTP/2 Connection factory to an
|
||||
existing connector.
|
||||
Thus configuring HTTP/2 is a combination of configuring common properties on the connector and HTTP/2 specific properties on the connection factory.
|
||||
The modules and XML files involved can be seen with the following commands:
|
||||
|
||||
[source,shell]
|
||||
----
|
||||
[source,screen, subs="{sub-order}"]
|
||||
....
|
||||
$ java -jar $JETTY_HOME/start.jar --list-modules
|
||||
...
|
||||
1) protonego-boot <transitive>
|
||||
1) protonego-boot <transitive>
|
||||
...
|
||||
2) http ${jetty.base}/start.d/http.ini
|
||||
2) ssl ${jetty.base}/start.d/ssl.ini
|
||||
|
@ -46,13 +46,17 @@ $ java -jar $JETTY_HOME/start.jar --list-config
|
|||
...
|
||||
${jetty.home}/etc/jetty-http2.xml
|
||||
${jetty.home}/etc/jetty-https.xml
|
||||
|
||||
----
|
||||
....
|
||||
|
||||
The common properties associated with connectors (host,port, timeouts, etc.) can be set in the module ini files (or start.ini if --add-to-start was used): `${jetty.base}/start.d/http.ini` `${jetty.base}/start.d/ssl.ini`.
|
||||
The common properties associated with connectors (host,port, timeouts, etc.) can be set in the module ini files (or `start.ini` if `--add-to-start` was used): `${jetty.base}/start.d/http.ini` and `${jetty.base}/start.d/ssl.ini`.
|
||||
These properties are instantiated in the associated XML files: `${jetty.home}/etc/jetty-http.xml`; `${jetty.home}/etc/jetty-ssl.xml`, plus the SSL keystore is instantiated in `${jetty.home}/etc/jetty-ssl-context.xml`.
|
||||
|
||||
HTTP/2 specific properties can be set in the module ini files: `${jetty.base}/start.d/http2.ini`; `${jetty.base}/start.d/http2c.ini`, which are instantiated in the associated XML files: `${jetty.home}/etc/jetty-http2.xml`; `${jetty.home}/etc/jetty-http2c.xml`.
|
||||
[NOTE]
|
||||
If you are planning to edit XML files, make sure to copy them to your `{$jetty.base}/etc/` directory before doing so.
|
||||
The XML files that come with the Jetty distribution should *not* be modified directly.
|
||||
----
|
||||
|
||||
HTTP/2 specific properties can be set in the module ini files: `${jetty.base}/start.d/http2.ini` and `${jetty.base}/start.d/http2c.ini`, which are instantiated in the associated XML files: `${jetty.home}/etc/jetty-http2.xml`; `${jetty.home}/etc/jetty-http2c.xml`, respectively.
|
||||
Currently there are very few HTTP/2 configuration properties and the default values are reasonable:
|
||||
|
||||
.HTTP/2 Configuration Properties
|
||||
|
|
|
@ -17,14 +17,13 @@
|
|||
[[http2-configuring-push]]
|
||||
=== Configuring HTTP/2 Push
|
||||
|
||||
HTTP/2 Push is a mechanism that allows the server to send multiple resources to the client for a single client request.
|
||||
This will reduce the amount of round-trips necessary to retrieve all the resources that make up a web page, and can significantly improve the page load time.
|
||||
HTTP/2 Push is a mechanism that allows the server to send multiple resources to the client for a single client request.
|
||||
This will reduce the amount of round-trips necessary to retrieve all the resources that make up a web page and can significantly improve the page load time.
|
||||
|
||||
HTTP/2 Push can be automated in your application by simply configuring a link:{JDURL}/org/eclipse/jetty/servlets/PushCacheFilter.html[`PushCacheFilter`] in your `web.xml`, in this way:
|
||||
HTTP/2 Push can be automated in your application by configuring a link:{JDURL}/org/eclipse/jetty/servlets/PushCacheFilter.html[`PushCacheFilter`] in the `web.xml`, in this way:
|
||||
|
||||
[source, xml, subs="{sub-order}"]
|
||||
----
|
||||
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<web-app
|
||||
xmlns="http://xmlns.jcp.org/xml/ns/javaee"
|
||||
|
@ -34,7 +33,6 @@ HTTP/2 Push can be automated in your application by simply configuring a link:{J
|
|||
version="3.1">
|
||||
|
||||
...
|
||||
|
||||
<filter>
|
||||
<filter-name>PushFilter</filter-name>
|
||||
<filter-class>org.eclipse.jetty.servlets.PushCacheFilter</filter-class>
|
||||
|
@ -44,17 +42,14 @@ HTTP/2 Push can be automated in your application by simply configuring a link:{J
|
|||
<filter-name>PushFilter</filter-name>
|
||||
<url-pattern>/*</url-pattern>
|
||||
</filter-mapping>
|
||||
|
||||
...
|
||||
|
||||
</web-app>
|
||||
|
||||
|
||||
----
|
||||
|
||||
`PushCacheFilter` analyzes the HTTP requests for resources that arrive to your web application.
|
||||
Some of these requests contain the HTTP `Referrer` header that points to a resource that has been requested previously.
|
||||
This allows the `PushCacheFilter` to organize resources in _primary_ resources (those referenced by the `Referrer` header) and _secondary_ resources (those that have the `Referer` header).
|
||||
`PushCacheFilter` analyzes the HTTP requests for resources that arrive to your web application.
|
||||
Some of these requests contain the HTTP `Referrer` header that points to a resource that has been requested previously.
|
||||
This allows the `PushCacheFilter` to organize resources in to two categories: _primary_ resources (those referenced by the `Referrer` header) and _secondary_ resources (those that have the `Referer` header).
|
||||
|
||||
`PushCacheFilter` associates secondary resources to primary resources.
|
||||
Only secondary resources that have been requested within a time window from the request of the primary resource are associated with the primary resource.
|
||||
|
@ -62,4 +57,3 @@ Only secondary resources that have been requested within a time window from the
|
|||
`PushCacheFilter` can be configured with the following `init-params`::
|
||||
* `associatePeriod`: the time window, in milliseconds, within which a request for a secondary resource will be associated to a primary resource.
|
||||
* `maxAssociations`: the max number of secondary resources that may be associated to a primary resource.
|
||||
|
||||
|
|
|
@ -17,7 +17,8 @@
|
|||
[[http2-enabling]]
|
||||
=== Enabling HTTP/2
|
||||
|
||||
This section is written assuming that a jetty base directory is being used and a demo jetty base that support HTTP/1, HTTPS/1 and deployment from a webapps directory can be created with the commands:
|
||||
This section is written assuming that a link:#startup-base-and-home[Jetty base directory] is being used.
|
||||
A demo Jetty base that supports HTTP/1, HTTPS/1 and deployment from a webapps directory can be created with the commands:
|
||||
|
||||
[source, screen, subs="{sub-order}"]
|
||||
....
|
||||
|
@ -27,21 +28,21 @@ $ cd $JETTY_BASE
|
|||
$ java -jar $JETTY_HOME/start.jar --add-to-startd=http,https,deploy
|
||||
....
|
||||
|
||||
The commands above create a `$JETTY_BASE` directory called `http2-demo`, and initializes the `http,` `https` and `deploy` modules (and their dependencies) to run a typical Jetty Server on port 8080 (for HTTP/1) and 8443 (for HTTPS/1).
|
||||
Note that the https module downloads a demo keystore file with a self signed certificate, which needs to be replaced by a Certificate Authority issued certificate for real deployment.
|
||||
The commands above create a `$JETTY_BASE` directory called `http2-demo`, and initializes the `http,` `https` and `deploy` modules (and their dependencies) to run a typical Jetty Server on port 8080 (for HTTP/1) and 8443 (for HTTPS/1).
|
||||
Note that the HTTPS module downloads a demo keystore file with a self signed certificate, which needs to be replaced by a Certificate Authority issued certificate for real deployment.
|
||||
|
||||
To add HTTP/2 to this demo base, it is just a matter of enabling the http2 module with the following command:
|
||||
To add HTTP/2 to this demo base, it is just a matter of enabling the `http2` module with the following command:
|
||||
|
||||
[source,shell]
|
||||
----
|
||||
[source, screen, subs="{sub-order}"]
|
||||
....
|
||||
$ java -jar $JETTY_HOME/start.jar --add-to-startd=http2
|
||||
----
|
||||
....
|
||||
|
||||
This command does not create a new connector, but instead simply adds the HTTP/2 protocol to the existing HTTPS/1 connector, so that it now supports both protocols on port 8443.
|
||||
To do this, it also transitively enables the ALPN module for protocol negotiation.
|
||||
This command does not create a new connector, but instead simply adds the HTTP/2 protocol to the existing HTTPS/1 connector, so that it now supports both protocols on port 8443.
|
||||
To do this, it also transitively enables the ALPN module for protocol negotiation.
|
||||
The support for each protocol can be seen in the info logging when the server is started:
|
||||
|
||||
[source,shell]
|
||||
[source,screen, subs="{sub-order}"]
|
||||
----
|
||||
$ java -jar $JETTY_HOME/start.jar
|
||||
...
|
||||
|
@ -50,22 +51,22 @@ $ java -jar $JETTY_HOME/start.jar
|
|||
...
|
||||
----
|
||||
|
||||
This log shows that port 8080 supports only HTTP/1.1 (which by specification includes HTTP/1.0 support), while port 8443 supports the SSL protocol, with ALPN negotiation to select between several versions of HTTP/2 (h2 & the draft h2-17) and HTTP/1.1.
|
||||
What is not shown, is that http/1.1 is the default ALPN protocol, so that if a client connects that does not speak ALPN, then HTTP/1.1 will be assumed.
|
||||
This log shows that port 8080 supports only HTTP/1.1 (which by specification includes HTTP/1.0 support), while port 8443 supports the SSL protocol, with ALPN negotiation to select between several versions of HTTP/2 (h2 & the draft h2-17) and HTTP/1.1.
|
||||
What is not shown is that HTTP/1.1 is the default ALPN protocol, so that if a client connects that does not speak ALPN, then HTTP/1.1 will be assumed.
|
||||
|
||||
A browser can now be pointed at `https://localhost:8443/` and if it supports HTTP/2 then it will be used (often indicated by a lightening bolt icon in the address bar).
|
||||
A browser can now be pointed at `https://localhost:8443/` and if it supports HTTP/2 then it will be used (often indicated by a lightening bolt icon in the address bar).
|
||||
Note that a browser pointed at this server with URL starting with `http://localhost:8080/` will still talk HTTP/1.1, as HTTP/2 has not been enabled on the plain text connector.
|
||||
|
||||
HTTP/2 can be enabled on the plain text connector and the server restarted with the following command:
|
||||
|
||||
[source,shell]
|
||||
----
|
||||
[source,screen]
|
||||
....
|
||||
$ java -jar $JETTY_HOME/start.jar --add-to-startd=http2c
|
||||
$ java -jar $JETTY_HOME/start.jar
|
||||
...
|
||||
..
|
||||
2015-06-17 14:16:12.549:INFO:oejs.ServerConnector:main: Started ServerConnector@6f32cd1e{HTTP/1.1,[http/1.1, h2c, h2c-17]}{0.0.0.0:8080}
|
||||
2015-06-17 14:16:12.782:INFO:oejs.ServerConnector:main: Started ServerConnector@711f39f9{SSL,[ssl, alpn, h2, h2-17, http/1.1]}{0.0.0.0:8443}
|
||||
...
|
||||
----
|
||||
..
|
||||
....
|
||||
|
||||
However, no major browser currently supports plain text HTTP/2, so the 8080 port will only be able to use HTTP/2 with specific clients (eg curl) that use the upgrade mechanism or assume HTTP/2
|
||||
No major browser currently supports plain text HTTP/2, so the 8080 port will only be able to use HTTP/2 with specific clients (eg `curl`) that use the upgrade mechanism or assume HTTP/2.
|
||||
|
|
|
@ -25,18 +25,18 @@ A server deployed over TLS (SSL) normally advertises the HTTP/2 protocol via the
|
|||
|
||||
____
|
||||
[IMPORTANT]
|
||||
To use HTTP/2 in Jetty via a TLS connector you need to add the link:#alpn-starting[ALPN boot Jar in the boot classpath.]
|
||||
This is done automatically when using the jetty distributions start.jar module system, but must be configured directly otherwise.
|
||||
To use HTTP/2 in Jetty via a TLS connector you need to add the link:#alpn-starting[ALPN boot jar] in the boot classpath.
|
||||
This is done automatically when using the Jetty distribution's start.jar link:#startup-modules[module system], but must be configured directly otherwise.
|
||||
____
|
||||
|
||||
[[http2-modules]]
|
||||
==== Jetty HTTP/2 Sub Projects
|
||||
=== Jetty HTTP/2 Sub Projects
|
||||
|
||||
The Jetty HTTP/2 implementation consists of the following sub-projects (each producing a jar):
|
||||
The Jetty HTTP/2 implementation consists of the following sub-projects (each producing a jar file):
|
||||
|
||||
1. `http2-common`: contains the HTTP/2 API and a partial implementation shared across other modules.
|
||||
2. `http2-hpack`: contains the HTTP/2 HPACK implementation for HTTP header compression.
|
||||
3. `http2-server`: provides the server-side implementation of HTTP/2.
|
||||
4. `http2-client`: provides the implementation of HTTP/2 client with a low level HTTP/2 API, dealing with HTTP/2 streams, frames, etc.
|
||||
5. `http2-http-client-transport`: provides the implementation of the HTTP/2 transport for `HttpClient` (see xref:http-client[]).
|
||||
Applications can use the higher level API provided by `HttpClient` to send HTTP requests and receive HTTP responses, and the HTTP/2 transport will take care of converting them in HTTP/2 format (see also https://webtide.com/http2-support-for-httpclient/[this blog entry]).
|
||||
1. `http2-common`: Contains the HTTP/2 API and a partial implementation shared across other modules.
|
||||
2. `http2-hpack`: Contains the HTTP/2 HPACK implementation for HTTP header compression.
|
||||
3. `http2-server`: Provides the server-side implementation of HTTP/2.
|
||||
4. `http2-client`: Provides the implementation of HTTP/2 client with a low level HTTP/2 API, dealing with HTTP/2 streams, frames, etc.
|
||||
5. `http2-http-client-transport`: Provides the implementation of the HTTP/2 transport for `HttpClient` (see xref:http-client[]).
|
||||
Applications can use the higher level API provided by `HttpClient` to send HTTP requests and receive HTTP responses, and the HTTP/2 transport will take care of converting them in HTTP/2 format (see also https://webtide.com/http2-support-for-httpclient/[this blog entry]).
|
||||
|
|
|
@ -106,7 +106,7 @@ public class HTTP2ServerConnectionFactory extends AbstractHTTP2ServerConnectionF
|
|||
HttpConfiguration httpConfig = getHttpConfiguration();
|
||||
Integer mhls = frame.getSettings().get(SettingsFrame.MAX_HEADER_LIST_SIZE);
|
||||
if (mhls != null && mhls < httpConfig.getResponseHeaderSize())
|
||||
httpConfig.setResponseHeaderSize(mhls);
|
||||
LOG.warn("MAX_HEADER_LIST_SIZE<{} for {}",getHttpConfiguration().getResponseHeaderSize(),session);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
Loading…
Reference in New Issue