From 1b172c1d20ecf96839abc02a67ae2a763af2815e Mon Sep 17 00:00:00 2001 From: Rossen Stoyanchev Date: Tue, 10 Dec 2019 15:10:13 +0000 Subject: [PATCH] Expose localAddress in WebFlux server Closes gh-24174 --- .../reactive/MockServerHttpRequest.java | 33 ++++++++++++++--- .../function/server/MockServerRequest.java | 33 +++++++++++++---- .../DefaultServerHttpRequestBuilder.java | 14 ++++---- .../reactive/ReactorServerHttpRequest.java | 7 +++- .../server/reactive/ServerHttpRequest.java | 9 +++++ .../reactive/ServerHttpRequestDecorator.java | 7 +++- .../reactive/ServletServerHttpRequest.java | 7 +++- .../reactive/UndertowServerHttpRequest.java | 5 +++ .../reactive/test/MockServerHttpRequest.java | 35 +++++++++++++++--- .../function/server/DefaultServerRequest.java | 5 +++ .../function/server/RequestPredicates.java | 5 +++ .../function/server/ServerRequest.java | 6 ++++ .../server/support/ServerRequestWrapper.java | 5 +++ .../function/server/MockServerRequest.java | 36 +++++++++++++++---- 14 files changed, 176 insertions(+), 31 deletions(-) diff --git a/spring-test/src/main/java/org/springframework/mock/http/server/reactive/MockServerHttpRequest.java b/spring-test/src/main/java/org/springframework/mock/http/server/reactive/MockServerHttpRequest.java index f94bacde936f..66c741eb6b9f 100644 --- a/spring-test/src/main/java/org/springframework/mock/http/server/reactive/MockServerHttpRequest.java +++ b/spring-test/src/main/java/org/springframework/mock/http/server/reactive/MockServerHttpRequest.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2018 the original author or authors. + * Copyright 2002-2019 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -61,6 +61,9 @@ public final class MockServerHttpRequest extends AbstractServerHttpRequest { @Nullable private final InetSocketAddress remoteAddress; + @Nullable + private final InetSocketAddress localAddress; + @Nullable private final SslInfo sslInfo; @@ -69,13 +72,14 @@ public final class MockServerHttpRequest extends AbstractServerHttpRequest { private MockServerHttpRequest(HttpMethod httpMethod, URI uri, @Nullable String contextPath, HttpHeaders headers, MultiValueMap cookies, - @Nullable InetSocketAddress remoteAddress, @Nullable SslInfo sslInfo, - Publisher body) { + @Nullable InetSocketAddress remoteAddress, @Nullable InetSocketAddress localAddress, + @Nullable SslInfo sslInfo, Publisher body) { super(uri, contextPath, headers); this.httpMethod = httpMethod; this.cookies = cookies; this.remoteAddress = remoteAddress; + this.localAddress = localAddress; this.sslInfo = sslInfo; this.body = Flux.from(body); } @@ -97,6 +101,12 @@ public InetSocketAddress getRemoteAddress() { return this.remoteAddress; } + @Nullable + @Override + public InetSocketAddress getLocalAddress() { + return this.localAddress; + } + @Nullable @Override protected SslInfo initSslInfo() { @@ -254,6 +264,12 @@ public interface BaseBuilder> { */ B remoteAddress(InetSocketAddress remoteAddress); + /** + * Set the local address to return. + * @since 5.2.3 + */ + B localAddress(InetSocketAddress localAddress); + /** * Set SSL session information and certificates. */ @@ -408,6 +424,9 @@ private static class DefaultBodyBuilder implements BodyBuilder { @Nullable private InetSocketAddress remoteAddress; + @Nullable + private InetSocketAddress localAddress; + @Nullable private SslInfo sslInfo; @@ -441,6 +460,12 @@ public BodyBuilder remoteAddress(InetSocketAddress remoteAddress) { return this; } + @Override + public BodyBuilder localAddress(InetSocketAddress localAddress) { + this.localAddress = localAddress; + return this; + } + @Override public void sslInfo(SslInfo sslInfo) { this.sslInfo = sslInfo; @@ -545,7 +570,7 @@ private Charset getCharset() { public MockServerHttpRequest body(Publisher body) { applyCookiesIfNecessary(); return new MockServerHttpRequest(this.method, getUrlToUse(), this.contextPath, - this.headers, this.cookies, this.remoteAddress, this.sslInfo, body); + this.headers, this.cookies, this.remoteAddress, this.localAddress, this.sslInfo, body); } private void applyCookiesIfNecessary() { diff --git a/spring-test/src/main/java/org/springframework/mock/web/reactive/function/server/MockServerRequest.java b/spring-test/src/main/java/org/springframework/mock/web/reactive/function/server/MockServerRequest.java index 0ae85abbe176..d3dde94ada2e 100644 --- a/spring-test/src/main/java/org/springframework/mock/web/reactive/function/server/MockServerRequest.java +++ b/spring-test/src/main/java/org/springframework/mock/web/reactive/function/server/MockServerRequest.java @@ -93,6 +93,9 @@ public final class MockServerRequest implements ServerRequest { @Nullable private final InetSocketAddress remoteAddress; + @Nullable + private final InetSocketAddress localAddress; + private final List> messageReaders; @Nullable @@ -103,8 +106,8 @@ private MockServerRequest(HttpMethod method, URI uri, String contextPath, MockHe MultiValueMap cookies, @Nullable Object body, Map attributes, MultiValueMap queryParams, Map pathVariables, @Nullable WebSession session, @Nullable Principal principal, - @Nullable InetSocketAddress remoteAddress, List> messageReaders, - @Nullable ServerWebExchange exchange) { + @Nullable InetSocketAddress remoteAddress, @Nullable InetSocketAddress localAddress, + List> messageReaders, @Nullable ServerWebExchange exchange) { this.method = method; this.uri = uri; @@ -118,6 +121,7 @@ private MockServerRequest(HttpMethod method, URI uri, String contextPath, MockHe this.session = session; this.principal = principal; this.remoteAddress = remoteAddress; + this.localAddress = localAddress; this.messageReaders = messageReaders; this.exchange = exchange; } @@ -163,6 +167,11 @@ public Optional remoteAddress() { return Optional.ofNullable(this.remoteAddress); } + @Override + public Optional localAddress() { + return Optional.ofNullable(this.localAddress); + } + @Override public List> messageReaders() { return this.messageReaders; @@ -303,6 +312,8 @@ public interface Builder { Builder remoteAddress(InetSocketAddress remoteAddress); + Builder localAddress(InetSocketAddress localAddress); + Builder messageReaders(List> messageReaders); Builder exchange(ServerWebExchange exchange); @@ -343,6 +354,9 @@ private static class BuilderImpl implements Builder { @Nullable private InetSocketAddress remoteAddress; + @Nullable + private InetSocketAddress localAddress; + private List> messageReaders = HandlerStrategies.withDefaults().messageReaders(); @Nullable @@ -470,6 +484,13 @@ public Builder remoteAddress(InetSocketAddress remoteAddress) { return this; } + @Override + public Builder localAddress(InetSocketAddress localAddress) { + Assert.notNull(localAddress, "'localAddress' must not be null"); + this.localAddress = localAddress; + return this; + } + @Override public Builder messageReaders(List> messageReaders) { Assert.notNull(messageReaders, "'messageReaders' must not be null"); @@ -489,16 +510,16 @@ public MockServerRequest body(Object body) { this.body = body; return new MockServerRequest(this.method, this.uri, this.contextPath, this.headers, this.cookies, this.body, this.attributes, this.queryParams, this.pathVariables, - this.session, this.principal, this.remoteAddress, this.messageReaders, - this.exchange); + this.session, this.principal, this.remoteAddress, this.localAddress, + this.messageReaders, this.exchange); } @Override public MockServerRequest build() { return new MockServerRequest(this.method, this.uri, this.contextPath, this.headers, this.cookies, null, this.attributes, this.queryParams, this.pathVariables, - this.session, this.principal, this.remoteAddress, this.messageReaders, - this.exchange); + this.session, this.principal, this.remoteAddress, this.localAddress, + this.messageReaders, this.exchange); } } diff --git a/spring-web/src/main/java/org/springframework/http/server/reactive/DefaultServerHttpRequestBuilder.java b/spring-web/src/main/java/org/springframework/http/server/reactive/DefaultServerHttpRequestBuilder.java index 963f5356d614..ce5a3d2b3739 100644 --- a/spring-web/src/main/java/org/springframework/http/server/reactive/DefaultServerHttpRequestBuilder.java +++ b/spring-web/src/main/java/org/springframework/http/server/reactive/DefaultServerHttpRequestBuilder.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2018 the original author or authors. + * Copyright 2002-2019 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -181,9 +181,6 @@ private static class MutatedServerHttpRequest extends AbstractServerHttpRequest private final MultiValueMap cookies; - @Nullable - private final InetSocketAddress remoteAddress; - @Nullable private final SslInfo sslInfo; @@ -199,7 +196,6 @@ public MutatedServerHttpRequest(URI uri, @Nullable String contextPath, super(uri, contextPath, headers); this.methodValue = methodValue; this.cookies = cookies; - this.remoteAddress = originalRequest.getRemoteAddress(); this.sslInfo = sslInfo != null ? sslInfo : originalRequest.getSslInfo(); this.body = body; this.originalRequest = originalRequest; @@ -218,7 +214,13 @@ protected MultiValueMap initCookies() { @Nullable @Override public InetSocketAddress getRemoteAddress() { - return this.remoteAddress; + return this.originalRequest.getRemoteAddress(); + } + + @Nullable + @Override + public InetSocketAddress getLocalAddress() { + return this.originalRequest.getLocalAddress(); } @Nullable diff --git a/spring-web/src/main/java/org/springframework/http/server/reactive/ReactorServerHttpRequest.java b/spring-web/src/main/java/org/springframework/http/server/reactive/ReactorServerHttpRequest.java index c6d60c01ab47..e05f992c97df 100644 --- a/spring-web/src/main/java/org/springframework/http/server/reactive/ReactorServerHttpRequest.java +++ b/spring-web/src/main/java/org/springframework/http/server/reactive/ReactorServerHttpRequest.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2018 the original author or authors. + * Copyright 2002-2019 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -151,6 +151,11 @@ public InetSocketAddress getRemoteAddress() { return this.request.remoteAddress(); } + @Override + public InetSocketAddress getLocalAddress() { + return this.request.hostAddress(); + } + @Override @Nullable protected SslInfo initSslInfo() { diff --git a/spring-web/src/main/java/org/springframework/http/server/reactive/ServerHttpRequest.java b/spring-web/src/main/java/org/springframework/http/server/reactive/ServerHttpRequest.java index 47b2e4c128dc..fd866d13503c 100644 --- a/spring-web/src/main/java/org/springframework/http/server/reactive/ServerHttpRequest.java +++ b/spring-web/src/main/java/org/springframework/http/server/reactive/ServerHttpRequest.java @@ -72,6 +72,15 @@ default InetSocketAddress getRemoteAddress() { return null; } + /** + * Return the local address the request was accepted on, if available. + * 5.2.3 + */ + @Nullable + default InetSocketAddress getLocalAddress() { + return null; + } + /** * Return the SSL session information if the request has been transmitted * over a secure protocol including SSL certificates, if available. diff --git a/spring-web/src/main/java/org/springframework/http/server/reactive/ServerHttpRequestDecorator.java b/spring-web/src/main/java/org/springframework/http/server/reactive/ServerHttpRequestDecorator.java index c24f79ef4f65..a526108d4637 100644 --- a/spring-web/src/main/java/org/springframework/http/server/reactive/ServerHttpRequestDecorator.java +++ b/spring-web/src/main/java/org/springframework/http/server/reactive/ServerHttpRequestDecorator.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2018 the original author or authors. + * Copyright 2002-2019 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -101,6 +101,11 @@ public InetSocketAddress getRemoteAddress() { return getDelegate().getRemoteAddress(); } + @Override + public InetSocketAddress getLocalAddress() { + return getDelegate().getLocalAddress(); + } + @Nullable @Override public SslInfo getSslInfo() { diff --git a/spring-web/src/main/java/org/springframework/http/server/reactive/ServletServerHttpRequest.java b/spring-web/src/main/java/org/springframework/http/server/reactive/ServletServerHttpRequest.java index 9385b455f1d5..6ea6e9404d6b 100644 --- a/spring-web/src/main/java/org/springframework/http/server/reactive/ServletServerHttpRequest.java +++ b/spring-web/src/main/java/org/springframework/http/server/reactive/ServletServerHttpRequest.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2018 the original author or authors. + * Copyright 2002-2019 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -178,6 +178,11 @@ public InetSocketAddress getRemoteAddress() { return new InetSocketAddress(this.request.getRemoteHost(), this.request.getRemotePort()); } + @Override + public InetSocketAddress getLocalAddress() { + return new InetSocketAddress(this.request.getLocalAddr(), this.request.getLocalPort()); + } + @Override @Nullable protected SslInfo initSslInfo() { diff --git a/spring-web/src/main/java/org/springframework/http/server/reactive/UndertowServerHttpRequest.java b/spring-web/src/main/java/org/springframework/http/server/reactive/UndertowServerHttpRequest.java index 060804dfab8f..11b4418951f4 100644 --- a/spring-web/src/main/java/org/springframework/http/server/reactive/UndertowServerHttpRequest.java +++ b/spring-web/src/main/java/org/springframework/http/server/reactive/UndertowServerHttpRequest.java @@ -102,6 +102,11 @@ public InetSocketAddress getRemoteAddress() { return this.exchange.getSourceAddress(); } + @Override + public InetSocketAddress getLocalAddress() { + return this.exchange.getDestinationAddress(); + } + @Nullable @Override protected SslInfo initSslInfo() { diff --git a/spring-web/src/test/java/org/springframework/mock/http/server/reactive/test/MockServerHttpRequest.java b/spring-web/src/test/java/org/springframework/mock/http/server/reactive/test/MockServerHttpRequest.java index 1615258e464a..3b7ecb116510 100644 --- a/spring-web/src/test/java/org/springframework/mock/http/server/reactive/test/MockServerHttpRequest.java +++ b/spring-web/src/test/java/org/springframework/mock/http/server/reactive/test/MockServerHttpRequest.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2018 the original author or authors. + * Copyright 2002-2019 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -52,7 +52,7 @@ * @author Rossen Stoyanchev * @since 5.0 */ -public class MockServerHttpRequest extends AbstractServerHttpRequest { +public final class MockServerHttpRequest extends AbstractServerHttpRequest { private final HttpMethod httpMethod; @@ -61,6 +61,9 @@ public class MockServerHttpRequest extends AbstractServerHttpRequest { @Nullable private final InetSocketAddress remoteAddress; + @Nullable + private final InetSocketAddress localAddress; + @Nullable private final SslInfo sslInfo; @@ -69,13 +72,14 @@ public class MockServerHttpRequest extends AbstractServerHttpRequest { private MockServerHttpRequest(HttpMethod httpMethod, URI uri, @Nullable String contextPath, HttpHeaders headers, MultiValueMap cookies, - @Nullable InetSocketAddress remoteAddress, @Nullable SslInfo sslInfo, - Publisher body) { + @Nullable InetSocketAddress remoteAddress, @Nullable InetSocketAddress localAddress, + @Nullable SslInfo sslInfo, Publisher body) { super(uri, contextPath, headers); this.httpMethod = httpMethod; this.cookies = cookies; this.remoteAddress = remoteAddress; + this.localAddress = localAddress; this.sslInfo = sslInfo; this.body = Flux.from(body); } @@ -97,6 +101,12 @@ public InetSocketAddress getRemoteAddress() { return this.remoteAddress; } + @Nullable + @Override + public InetSocketAddress getLocalAddress() { + return this.localAddress; + } + @Nullable @Override protected SslInfo initSslInfo() { @@ -254,6 +264,12 @@ public interface BaseBuilder> { */ B remoteAddress(InetSocketAddress remoteAddress); + /** + * Set the local address to return. + * @since 5.2.3 + */ + B localAddress(InetSocketAddress localAddress); + /** * Set SSL session information and certificates. */ @@ -408,6 +424,9 @@ private static class DefaultBodyBuilder implements BodyBuilder { @Nullable private InetSocketAddress remoteAddress; + @Nullable + private InetSocketAddress localAddress; + @Nullable private SslInfo sslInfo; @@ -441,6 +460,12 @@ public BodyBuilder remoteAddress(InetSocketAddress remoteAddress) { return this; } + @Override + public BodyBuilder localAddress(InetSocketAddress localAddress) { + this.localAddress = localAddress; + return this; + } + @Override public void sslInfo(SslInfo sslInfo) { this.sslInfo = sslInfo; @@ -545,7 +570,7 @@ private Charset getCharset() { public MockServerHttpRequest body(Publisher body) { applyCookiesIfNecessary(); return new MockServerHttpRequest(this.method, getUrlToUse(), this.contextPath, - this.headers, this.cookies, this.remoteAddress, this.sslInfo, body); + this.headers, this.cookies, this.remoteAddress, this.localAddress, this.sslInfo, body); } private void applyCookiesIfNecessary() { diff --git a/spring-webflux/src/main/java/org/springframework/web/reactive/function/server/DefaultServerRequest.java b/spring-webflux/src/main/java/org/springframework/web/reactive/function/server/DefaultServerRequest.java index cdfa46cb324f..74a6a710936c 100644 --- a/spring-webflux/src/main/java/org/springframework/web/reactive/function/server/DefaultServerRequest.java +++ b/spring-webflux/src/main/java/org/springframework/web/reactive/function/server/DefaultServerRequest.java @@ -122,6 +122,11 @@ public Optional remoteAddress() { return Optional.ofNullable(request().getRemoteAddress()); } + @Override + public Optional localAddress() { + return Optional.ofNullable(request().getLocalAddress()); + } + @Override public List> messageReaders() { return this.messageReaders; diff --git a/spring-webflux/src/main/java/org/springframework/web/reactive/function/server/RequestPredicates.java b/spring-webflux/src/main/java/org/springframework/web/reactive/function/server/RequestPredicates.java index ee28004a90af..cbb3a1795dfa 100644 --- a/spring-webflux/src/main/java/org/springframework/web/reactive/function/server/RequestPredicates.java +++ b/spring-webflux/src/main/java/org/springframework/web/reactive/function/server/RequestPredicates.java @@ -947,6 +947,11 @@ public Optional remoteAddress() { return this.request.remoteAddress(); } + @Override + public Optional localAddress() { + return this.request.localAddress(); + } + @Override public List> messageReaders() { return this.request.messageReaders(); diff --git a/spring-webflux/src/main/java/org/springframework/web/reactive/function/server/ServerRequest.java b/spring-webflux/src/main/java/org/springframework/web/reactive/function/server/ServerRequest.java index 72147d68985e..4bca08b45443 100644 --- a/spring-webflux/src/main/java/org/springframework/web/reactive/function/server/ServerRequest.java +++ b/spring-webflux/src/main/java/org/springframework/web/reactive/function/server/ServerRequest.java @@ -124,6 +124,12 @@ default PathContainer pathContainer() { */ Optional remoteAddress(); + /** + * Get the remote address to which this request is connected, if available. + * @since 5.2.3 + */ + Optional localAddress(); + /** * Get the readers used to convert the body of this request. * @since 5.1 diff --git a/spring-webflux/src/main/java/org/springframework/web/reactive/function/server/support/ServerRequestWrapper.java b/spring-webflux/src/main/java/org/springframework/web/reactive/function/server/support/ServerRequestWrapper.java index 4ae5fea57b54..9b92d77cd1bc 100644 --- a/spring-webflux/src/main/java/org/springframework/web/reactive/function/server/support/ServerRequestWrapper.java +++ b/spring-webflux/src/main/java/org/springframework/web/reactive/function/server/support/ServerRequestWrapper.java @@ -123,6 +123,11 @@ public Optional remoteAddress() { return this.delegate.remoteAddress(); } + @Override + public Optional localAddress() { + return this.delegate.localAddress(); + } + @Override public List> messageReaders() { return this.delegate.messageReaders(); diff --git a/spring-webflux/src/test/java/org/springframework/web/reactive/function/server/MockServerRequest.java b/spring-webflux/src/test/java/org/springframework/web/reactive/function/server/MockServerRequest.java index 964140255832..4332dc4afa90 100644 --- a/spring-webflux/src/test/java/org/springframework/web/reactive/function/server/MockServerRequest.java +++ b/spring-webflux/src/test/java/org/springframework/web/reactive/function/server/MockServerRequest.java @@ -61,7 +61,7 @@ * @author Arjen Poutsma * @since 5.0 */ -public class MockServerRequest implements ServerRequest { +public final class MockServerRequest implements ServerRequest { private final HttpMethod method; @@ -91,6 +91,9 @@ public class MockServerRequest implements ServerRequest { @Nullable private final InetSocketAddress remoteAddress; + @Nullable + private final InetSocketAddress localAddress; + private final List> messageReaders; @Nullable @@ -101,8 +104,8 @@ private MockServerRequest(HttpMethod method, URI uri, String contextPath, MockHe MultiValueMap cookies, @Nullable Object body, Map attributes, MultiValueMap queryParams, Map pathVariables, @Nullable WebSession session, @Nullable Principal principal, - @Nullable InetSocketAddress remoteAddress, List> messageReaders, - @Nullable ServerWebExchange exchange) { + @Nullable InetSocketAddress remoteAddress, @Nullable InetSocketAddress localAddress, + List> messageReaders, @Nullable ServerWebExchange exchange) { this.method = method; this.uri = uri; @@ -116,6 +119,7 @@ private MockServerRequest(HttpMethod method, URI uri, String contextPath, MockHe this.session = session; this.principal = principal; this.remoteAddress = remoteAddress; + this.localAddress = localAddress; this.messageReaders = messageReaders; this.exchange = exchange; } @@ -161,6 +165,11 @@ public Optional remoteAddress() { return Optional.ofNullable(this.remoteAddress); } + @Override + public Optional localAddress() { + return Optional.ofNullable(this.localAddress); + } + @Override public List> messageReaders() { return this.messageReaders; @@ -291,6 +300,7 @@ public interface Builder { Builder session(WebSession session); /** + * Sets the request {@link Principal}. * @deprecated in favor of {@link #principal(Principal)} */ @Deprecated @@ -300,6 +310,8 @@ public interface Builder { Builder remoteAddress(InetSocketAddress remoteAddress); + Builder localAddress(InetSocketAddress localAddress); + Builder messageReaders(List> messageReaders); Builder exchange(ServerWebExchange exchange); @@ -340,6 +352,9 @@ private static class BuilderImpl implements Builder { @Nullable private InetSocketAddress remoteAddress; + @Nullable + private InetSocketAddress localAddress; + private List> messageReaders = HandlerStrategies.withDefaults().messageReaders(); @Nullable @@ -467,6 +482,13 @@ public Builder remoteAddress(InetSocketAddress remoteAddress) { return this; } + @Override + public Builder localAddress(InetSocketAddress localAddress) { + Assert.notNull(localAddress, "'localAddress' must not be null"); + this.localAddress = localAddress; + return this; + } + @Override public Builder messageReaders(List> messageReaders) { Assert.notNull(messageReaders, "'messageReaders' must not be null"); @@ -486,16 +508,16 @@ public MockServerRequest body(Object body) { this.body = body; return new MockServerRequest(this.method, this.uri, this.contextPath, this.headers, this.cookies, this.body, this.attributes, this.queryParams, this.pathVariables, - this.session, this.principal, this.remoteAddress, this.messageReaders, - this.exchange); + this.session, this.principal, this.remoteAddress, this.localAddress, + this.messageReaders, this.exchange); } @Override public MockServerRequest build() { return new MockServerRequest(this.method, this.uri, this.contextPath, this.headers, this.cookies, null, this.attributes, this.queryParams, this.pathVariables, - this.session, this.principal, this.remoteAddress, this.messageReaders, - this.exchange); + this.session, this.principal, this.remoteAddress, this.localAddress, + this.messageReaders, this.exchange); } }