Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Allows configuring the initial HTTP/2 settings #33777

Merged
merged 1 commit into from
Jun 6, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions docs/src/main/asciidoc/http-reference.adoc
Original file line number Diff line number Diff line change
Expand Up @@ -292,6 +292,10 @@ If you want to disable HTTP/2 you can set:
quarkus.http.http2=false
----

Note that some configuration attributes are specific to HTTP/2.
For example, to configure the max header list size (~ header), you need to configure the `quarkus.http.limits.max-header-list-size` attribute.
You can also enable or disable HTTP/2 push using `quarkus.http.http2-push-enabled`.

== Listening on a Random Port

If you don't want to specify a port you can set `quarkus.http.port=0` or `quarkus.http.test-port=0`. A random open port
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -81,6 +81,14 @@ public class HttpConfiguration {
@ConfigItem(defaultValue = "true")
public boolean http2;

/**
* Enables or Disable the HTTP/2 Push feature.
* This setting can be used to disable server push. The server will not send a {@code PUSH_PROMISE} frame if it
* receives this parameter set to @{code false}.
*/
@ConfigItem(defaultValue = "true")
public boolean http2PushEnabled;

/**
* The CORS config
*/
Expand Down Expand Up @@ -179,6 +187,14 @@ public class HttpConfiguration {
@ConfigItem(defaultValue = "-1")
public int acceptBacklog;

/**
* Set the SETTINGS_INITIAL_WINDOW_SIZE HTTP/2 setting.
* Indicates the sender's initial window size (in octets) for stream-level flow control.
* The initial value is {@code 2^16-1} (65,535) octets.
*/
@ConfigItem
public OptionalInt initialWindowSize;

/**
* Path to a unix domain socket
*/
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@

import java.util.Optional;
import java.util.OptionalInt;
import java.util.OptionalLong;

import io.quarkus.runtime.annotations.ConfigGroup;
import io.quarkus.runtime.annotations.ConfigItem;
Expand Down Expand Up @@ -46,4 +47,43 @@ public class ServerLimitsConfig {
@ConfigItem
public OptionalInt maxConnections;

/**
* Set the SETTINGS_HEADER_TABLE_SIZE HTTP/2 setting.
* <p>
* Allows the sender to inform the remote endpoint of the maximum size of the header compression table used to decode
* header blocks, in octets. The encoder can select any size equal to or less than this value by using signaling
* specific to the header compression format inside a header block.
* The initial value is {@code 4,096} octets.
*/
@ConfigItem
public OptionalLong headerTableSize;

/**
* Set SETTINGS_MAX_CONCURRENT_STREAMS HTTP/2 setting.
* <p>
* Indicates the maximum number of concurrent streams that the sender will allow. This limit is directional: it
* applies to the number of streams that the sender permits the receiver to create. Initially, there is no limit to
* this value. It is recommended that this value be no smaller than 100, to not unnecessarily limit parallelism.
*/
@ConfigItem
public OptionalLong maxConcurrentStreams;

/**
* Set the SETTINGS_MAX_FRAME_SIZE HTTP/2 setting.
* Indicates the size of the largest frame payload that the sender is willing to receive, in octets.
* The initial value is {@code 2^14} (16,384) octets.
*/
@ConfigItem
public OptionalInt maxFrameSize;

/**
* Set the SETTINGS_MAX_HEADER_LIST_SIZE HTTP/2 setting.
* This advisory setting informs a peer of the maximum size of header list that the sender is prepared to accept,
* in octets. The value is based on the uncompressed size of header fields, including the length of the name and
* value in octets plus an overhead of 32 octets for each header field.
* The default value is {@code 8192}
*/
@ConfigItem
public OptionalLong maxHeaderListSize;
Comment on lines +50 to +87
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Just a thought: Should these be under a dedicated http2 group?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I was wondering the same, but because these are limits, it's a bit weird to have them separately like:

  • quarkus.http.limits for http/1 and http/1.1
  • quarkus.http.http2 for http/2

But I don't have a strong opinion.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

But I don't have a strong opinion.

Me neither, so let's just leave it as is


}
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@
import io.quarkus.vertx.http.runtime.management.ManagementInterfaceBuildTimeConfig;
import io.quarkus.vertx.http.runtime.management.ManagementInterfaceConfiguration;
import io.vertx.core.buffer.Buffer;
import io.vertx.core.http.Http2Settings;
import io.vertx.core.http.HttpServerOptions;
import io.vertx.core.http.HttpVersion;
import io.vertx.core.net.JdkSSLEngineOptions;
Expand Down Expand Up @@ -275,6 +276,27 @@ public static void applyCommonOptions(HttpServerOptions httpServerOptions,
httpServerOptions.setDecompressionSupported(buildTimeConfig.enableDecompression);
httpServerOptions.setMaxInitialLineLength(httpConfiguration.limits.maxInitialLineLength);
httpServerOptions.setHandle100ContinueAutomatically(httpConfiguration.handle100ContinueAutomatically);

if (httpConfiguration.http2) {
var settings = new Http2Settings();
if (httpConfiguration.limits.headerTableSize.isPresent()) {
settings.setHeaderTableSize(httpConfiguration.limits.headerTableSize.getAsLong());
}
settings.setPushEnabled(httpConfiguration.http2PushEnabled);
if (httpConfiguration.limits.maxConcurrentStreams.isPresent()) {
settings.setMaxConcurrentStreams(httpConfiguration.limits.maxConcurrentStreams.getAsLong());
}
if (httpConfiguration.initialWindowSize.isPresent()) {
settings.setInitialWindowSize(httpConfiguration.initialWindowSize.getAsInt());
}
if (httpConfiguration.limits.maxFrameSize.isPresent()) {
settings.setMaxFrameSize(httpConfiguration.limits.maxFrameSize.getAsInt());
}
if (httpConfiguration.limits.maxHeaderListSize.isPresent()) {
settings.setMaxHeaderListSize(httpConfiguration.limits.maxHeaderListSize.getAsLong());
}
httpServerOptions.setInitialSettings(settings);
}
}

public static void applyCommonOptionsForManagementInterface(HttpServerOptions options,
Expand Down