All Downloads are FREE. Search and download functionalities are using the official Maven repository.

reactor.netty.http.server.ConnectionInfo Maven / Gradle / Ivy

There is a newer version: 1.2.1
Show newest version
/*
 * Copyright (c) 2018-2024 VMware, Inc. or its affiliates, All Rights Reserved.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *   https://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
package reactor.netty.http.server;

import java.net.InetSocketAddress;
import java.net.SocketAddress;
import java.util.function.BiFunction;

import io.netty.handler.codec.http.HttpHeaderNames;
import io.netty.handler.codec.http.HttpRequest;
import reactor.util.annotation.Nullable;

import static java.util.Objects.requireNonNull;

/**
 * Resolve information about the current connection, including the
 * host (server) address, the remote (client) address and the scheme.
 *
 * 

Depending on the chosen factory method, the information * can be retrieved directly from the channel or additionally * using the {@code "Forwarded"}, or {@code "X-Forwarded-*"} * HTTP request headers. * * @author Brian Clozel * @author Andrey Shlykov * @since 0.8 * @see rfc7239 */ public final class ConnectionInfo { static final int DEFAULT_HTTP_PORT = 80; static final int DEFAULT_HTTPS_PORT = 443; static final String DEFAULT_HOST_NAME = "localhost"; final SocketAddress hostAddress; final SocketAddress remoteAddress; final String scheme; final String hostName; final int hostPort; final boolean isInetAddress; @Nullable final String forwardedPrefix; static ConnectionInfo from(HttpRequest request, boolean secured, SocketAddress localAddress, SocketAddress remoteAddress, @Nullable BiFunction forwardedHeaderHandler) { String hostName = DEFAULT_HOST_NAME; int hostPort = -1; String scheme = secured ? "https" : "http"; String header = request.headers().get(HttpHeaderNames.HOST); if (header != null) { hostName = header; if (!header.isEmpty()) { int portIndex = header.charAt(0) == '[' ? header.indexOf(':', header.indexOf(']')) : header.indexOf(':'); if (portIndex != -1) { hostName = header.substring(0, portIndex); hostPort = Integer.parseInt(header.substring(portIndex + 1)); } } } if (!(remoteAddress instanceof InetSocketAddress)) { return new ConnectionInfo(localAddress, hostName, hostPort, remoteAddress, scheme, false); } else { ConnectionInfo connectionInfo = new ConnectionInfo(localAddress, hostName, hostPort, remoteAddress, scheme, true); if (forwardedHeaderHandler != null) { return forwardedHeaderHandler.apply(connectionInfo, request); } return connectionInfo; } } ConnectionInfo(SocketAddress hostAddress, SocketAddress remoteAddress, boolean secured) { this(hostAddress, DEFAULT_HOST_NAME, -1, remoteAddress, secured ? "https" : "http", remoteAddress instanceof InetSocketAddress); } ConnectionInfo(SocketAddress hostAddress, String hostName, int hostPort, SocketAddress remoteAddress, String scheme, boolean isInetAddress) { this(hostAddress, hostName, hostPort, remoteAddress, scheme, isInetAddress, null); } ConnectionInfo(SocketAddress hostAddress, String hostName, int hostPort, SocketAddress remoteAddress, String scheme, boolean isInetAddress, @Nullable String forwardedPrefix) { this.hostAddress = hostAddress; this.hostName = hostName; this.hostPort = hostPort; this.isInetAddress = isInetAddress; this.remoteAddress = remoteAddress; this.scheme = scheme; this.forwardedPrefix = forwardedPrefix; } /** * Return the host address of the connection. * @return the host address */ @Nullable public InetSocketAddress getHostAddress() { return isInetAddress ? (InetSocketAddress) hostAddress : null; } /** * Return the remote address of the connection. * @return the remote address */ @Nullable public InetSocketAddress getRemoteAddress() { return isInetAddress ? (InetSocketAddress) remoteAddress : null; } /** * Return the connection scheme. * @return the connection scheme */ public String getScheme() { return scheme; } /** * Return a new {@link ConnectionInfo} with the updated host address. * @param hostAddress the host address * @return a new {@link ConnectionInfo} */ public ConnectionInfo withHostAddress(InetSocketAddress hostAddress) { requireNonNull(hostAddress, "hostAddress"); return new ConnectionInfo(hostAddress, hostAddress.getHostString(), hostAddress.getPort(), this.remoteAddress, this.scheme, true); } /** * Return a new {@link ConnectionInfo} with updated host address, host name, and host port information. * @param hostAddress the updated host address * @param hostName the updated host name * @param hostPort the updated host port * @return a new {@link ConnectionInfo} * @since 1.0.32 */ public ConnectionInfo withHostAddress(InetSocketAddress hostAddress, String hostName, int hostPort) { requireNonNull(hostAddress, "hostAddress"); requireNonNull(hostName, "hostName"); return new ConnectionInfo(hostAddress, hostName, hostPort, this.remoteAddress, this.scheme, true); } /** * Return a new {@link ConnectionInfo} with the updated remote address. * @param remoteAddress the remote address * @return a new {@link ConnectionInfo} */ public ConnectionInfo withRemoteAddress(InetSocketAddress remoteAddress) { requireNonNull(remoteAddress, "remoteAddress"); return new ConnectionInfo(this.hostAddress, this.hostName, this.hostPort, remoteAddress, this.scheme, true); } /** * Return a new {@link ConnectionInfo} with the updated scheme. * @param scheme the connection scheme * @return a new {@link ConnectionInfo} */ public ConnectionInfo withScheme(String scheme) { requireNonNull(scheme, "scheme"); return new ConnectionInfo(this.hostAddress, this.hostName, this.hostPort, this.remoteAddress, scheme, this.isInetAddress); } /** * Return a new {@link ConnectionInfo} with the forwardedPrefix set. * @param forwardedPrefix the prefix provided via X-Forwarded-Prefix header * @return a new {@link ConnectionInfo} * @since 1.1.23 */ public ConnectionInfo withForwardedPrefix(String forwardedPrefix) { requireNonNull(forwardedPrefix, "forwardedPrefix"); return new ConnectionInfo(this.hostAddress, this.hostName, this.hostPort, this.remoteAddress, this.scheme, this.isInetAddress, forwardedPrefix); } /** * Returns the connection host name. * @return the connection host name * @since 1.0.32 */ public String getHostName() { return hostName; } /** * Returns the connection host port. * @return the connection host port * @since 1.0.32 */ public int getHostPort() { return hostPort != -1 ? hostPort : getDefaultHostPort(scheme); } /** * Returns the X-Forwarded-Prefix if it was part of the request headers. * @return the X-Forwarded-Prefix * @since 1.1.23 */ @Nullable public String getForwardedPrefix() { return forwardedPrefix; } /** * Returns the default host port number based on scheme. * @param scheme a connection scheme like "http", "https", or "wss" * @return the default host port number based on scheme * @since 1.0.32 */ public static int getDefaultHostPort(String scheme) { return scheme.equalsIgnoreCase("https") || scheme.equalsIgnoreCase("wss") ? DEFAULT_HTTPS_PORT : DEFAULT_HTTP_PORT; } }





© 2015 - 2025 Weber Informatics LLC | Privacy Policy