Skip to content

Commit dbc9065

Browse files
author
Andrey Ershov
committed
transport.publish_address should contain CNAME (#45626)
This commit adds CNAME reporting for transport.publish_address same way it's done for http.publish_address. Relates #32806 Relates #39970 (cherry picked from commit e0a2558)
1 parent 59d378f commit dbc9065

File tree

6 files changed

+162
-3
lines changed

6 files changed

+162
-3
lines changed

buildSrc/src/main/groovy/org/elasticsearch/gradle/BuildPlugin.groovy

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -894,6 +894,9 @@ class BuildPlugin implements Plugin<Project> {
894894
// TODO: remove this once ctx isn't added to update script params in 7.0
895895
test.systemProperty 'es.scripting.update.ctx_in_params', 'false'
896896

897+
// TODO: remove this once cname is prepended to transport.publish_address by default in 8.0
898+
test.systemProperty 'es.transport.cname_in_publish_address', 'true'
899+
897900
test.testLogging { TestLoggingContainer logging ->
898901
logging.showExceptions = true
899902
logging.showCauses = true

docs/build.gradle

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -59,6 +59,9 @@ testClusters.integTest {
5959
extraConfigFile 'hunspell/en_US/en_US.dic', project(":server").file('src/test/resources/indices/analyze/conf_dir/hunspell/en_US/en_US.dic')
6060
// Whitelist reindexing from the local node so we can test it.
6161
setting 'reindex.remote.whitelist', '127.0.0.1:*'
62+
63+
// TODO: remove this once cname is prepended to transport.publish_address by default in 8.0
64+
systemProperty 'es.transport.cname_in_publish_address', 'true'
6265
}
6366

6467
// build the cluster with all plugins

modules/lang-painless/build.gradle

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,8 @@ esplugin {
2828
testClusters.integTest {
2929
module file(project(':modules:mapper-extras').tasks.bundlePlugin.archiveFile)
3030
systemProperty 'es.scripting.update.ctx_in_params', 'false'
31+
// TODO: remove this once cname is prepended to transport.publish_address by default in 8.0
32+
systemProperty 'es.transport.cname_in_publish_address', 'true'
3133
}
3234

3335
dependencies {

server/src/main/java/org/elasticsearch/common/transport/BoundTransportAddress.java

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@
2222
import org.elasticsearch.common.io.stream.StreamInput;
2323
import org.elasticsearch.common.io.stream.StreamOutput;
2424
import org.elasticsearch.common.io.stream.Writeable;
25+
import org.elasticsearch.common.network.InetAddresses;
2526

2627
import java.io.IOException;
2728

@@ -75,7 +76,12 @@ public void writeTo(StreamOutput out) throws IOException {
7576
@Override
7677
public String toString() {
7778
StringBuilder builder = new StringBuilder("publish_address {");
78-
builder.append(publishAddress);
79+
String hostString = publishAddress.address().getHostString();
80+
String publishAddressString = publishAddress.toString();
81+
if (InetAddresses.isInetAddress(hostString) == false) {
82+
publishAddressString = hostString + '/' + publishAddress.toString();
83+
}
84+
builder.append(publishAddressString);
7985
builder.append("}, bound_addresses ");
8086
boolean firstAdded = false;
8187
for (TransportAddress address : boundAddresses) {

server/src/main/java/org/elasticsearch/transport/TransportInfo.java

Lines changed: 40 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -19,26 +19,45 @@
1919

2020
package org.elasticsearch.transport;
2121

22+
import org.apache.logging.log4j.LogManager;
2223
import org.elasticsearch.common.Nullable;
2324
import org.elasticsearch.common.io.stream.StreamInput;
2425
import org.elasticsearch.common.io.stream.StreamOutput;
2526
import org.elasticsearch.common.io.stream.Writeable;
27+
import org.elasticsearch.common.logging.DeprecationLogger;
28+
import org.elasticsearch.common.network.InetAddresses;
2629
import org.elasticsearch.common.transport.BoundTransportAddress;
30+
import org.elasticsearch.common.transport.TransportAddress;
2731
import org.elasticsearch.common.xcontent.ToXContentFragment;
2832
import org.elasticsearch.common.xcontent.XContentBuilder;
2933

3034
import java.io.IOException;
3135
import java.util.HashMap;
3236
import java.util.Map;
3337

38+
import static org.elasticsearch.common.Booleans.parseBoolean;
39+
3440
public class TransportInfo implements Writeable, ToXContentFragment {
3541

42+
private static final DeprecationLogger deprecationLogger = new DeprecationLogger(LogManager.getLogger(TransportInfo.class));
43+
44+
/** Whether to add hostname to publish host field when serializing. */
45+
private static final boolean CNAME_IN_PUBLISH_ADDRESS =
46+
parseBoolean(System.getProperty("es.transport.cname_in_publish_address"), false);
47+
3648
private BoundTransportAddress address;
3749
private Map<String, BoundTransportAddress> profileAddresses;
50+
private final boolean cnameInPublishAddress;
3851

3952
public TransportInfo(BoundTransportAddress address, @Nullable Map<String, BoundTransportAddress> profileAddresses) {
53+
this(address, profileAddresses, CNAME_IN_PUBLISH_ADDRESS);
54+
}
55+
56+
public TransportInfo(BoundTransportAddress address, @Nullable Map<String, BoundTransportAddress> profileAddresses,
57+
boolean cnameInPublishAddress) {
4058
this.address = address;
4159
this.profileAddresses = profileAddresses;
60+
this.cnameInPublishAddress = cnameInPublishAddress;
4261
}
4362

4463
public TransportInfo(StreamInput in) throws IOException {
@@ -52,6 +71,7 @@ public TransportInfo(StreamInput in) throws IOException {
5271
profileAddresses.put(key, value);
5372
}
5473
}
74+
this.cnameInPublishAddress = CNAME_IN_PUBLISH_ADDRESS;
5575
}
5676

5777
@Override
@@ -77,17 +97,35 @@ static final class Fields {
7797
static final String PROFILES = "profiles";
7898
}
7999

100+
private String formatPublishAddressString(String propertyName, TransportAddress publishAddress){
101+
String publishAddressString = publishAddress.toString();
102+
String hostString = publishAddress.address().getHostString();
103+
if (InetAddresses.isInetAddress(hostString) == false) {
104+
if (cnameInPublishAddress) {
105+
publishAddressString = hostString + '/' + publishAddress.toString();
106+
} else {
107+
deprecationLogger.deprecated(
108+
propertyName + " was printed as [ip:port] instead of [hostname/ip:port]. "
109+
+ "This format is deprecated and will change to [hostname/ip:port] in a future version. "
110+
+ "Use -Des.transport.cname_in_publish_address=true to enforce non-deprecated formatting."
111+
);
112+
}
113+
}
114+
return publishAddressString;
115+
}
116+
80117
@Override
81118
public XContentBuilder toXContent(XContentBuilder builder, Params params) throws IOException {
82119
builder.startObject(Fields.TRANSPORT);
83120
builder.array(Fields.BOUND_ADDRESS, (Object[]) address.boundAddresses());
84-
builder.field(Fields.PUBLISH_ADDRESS, address.publishAddress().toString());
121+
builder.field(Fields.PUBLISH_ADDRESS, formatPublishAddressString("transport.publish_address", address.publishAddress()));
85122
builder.startObject(Fields.PROFILES);
86123
if (profileAddresses != null && profileAddresses.size() > 0) {
87124
for (Map.Entry<String, BoundTransportAddress> entry : profileAddresses.entrySet()) {
88125
builder.startObject(entry.getKey());
89126
builder.array(Fields.BOUND_ADDRESS, (Object[]) entry.getValue().boundAddresses());
90-
builder.field(Fields.PUBLISH_ADDRESS, entry.getValue().publishAddress().toString());
127+
String propertyName = "transport." + entry.getKey() + ".publish_address";
128+
builder.field(Fields.PUBLISH_ADDRESS, formatPublishAddressString(propertyName, entry.getValue().publishAddress()));
91129
builder.endObject();
92130
}
93131
}
Lines changed: 107 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,107 @@
1+
/*
2+
* Licensed to Elasticsearch under one or more contributor
3+
* license agreements. See the NOTICE file distributed with
4+
* this work for additional information regarding copyright
5+
* ownership. Elasticsearch licenses this file to you under
6+
* the Apache License, Version 2.0 (the "License"); you may
7+
* not use this file except in compliance with the License.
8+
* You may obtain a copy of the License at
9+
*
10+
* http://www.apache.org/licenses/LICENSE-2.0
11+
*
12+
* Unless required by applicable law or agreed to in writing,
13+
* software distributed under the License is distributed on an
14+
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15+
* KIND, either express or implied. See the License for the
16+
* specific language governing permissions and limitations
17+
* under the License.
18+
*/
19+
20+
package org.elasticsearch.transport;
21+
22+
import org.elasticsearch.common.network.NetworkAddress;
23+
import org.elasticsearch.common.transport.BoundTransportAddress;
24+
import org.elasticsearch.common.transport.TransportAddress;
25+
import org.elasticsearch.common.xcontent.ToXContent;
26+
import org.elasticsearch.common.xcontent.XContentBuilder;
27+
import org.elasticsearch.common.xcontent.XContentFactory;
28+
import org.elasticsearch.test.ESTestCase;
29+
30+
import java.io.IOException;
31+
import java.net.InetAddress;
32+
import java.util.Collections;
33+
import java.util.Map;
34+
35+
public class TransportInfoTests extends ESTestCase {
36+
37+
private TransportInfo createTransportInfo(InetAddress address, int port, boolean cnameInPublishAddress) {
38+
BoundTransportAddress boundAddress = new BoundTransportAddress(
39+
new TransportAddress[]{new TransportAddress(address, port)},
40+
new TransportAddress(address, port)
41+
);
42+
Map<String, BoundTransportAddress> profiles = Collections.singletonMap("test_profile", boundAddress);
43+
return new TransportInfo(boundAddress, profiles, cnameInPublishAddress);
44+
}
45+
46+
public void testCorrectlyDisplayPublishedCname() throws Exception {
47+
InetAddress address = InetAddress.getByName("localhost");
48+
int port = 9200;
49+
assertPublishAddress(
50+
createTransportInfo(address, port,true),
51+
"localhost/" + NetworkAddress.format(address) + ':' + port
52+
);
53+
}
54+
55+
public void testHideCnameIfDeprecatedFormat() throws Exception {
56+
InetAddress address = InetAddress.getByName("localhost");
57+
int port = 9200;
58+
assertPublishAddress(
59+
createTransportInfo(address, port,false),
60+
NetworkAddress.format(address) + ':' + port
61+
);
62+
assertWarnings("transport.publish_address was printed as [ip:port] instead of [hostname/ip:port]. " +
63+
"This format is deprecated and will change to [hostname/ip:port] in a future version. " +
64+
"Use -Des.transport.cname_in_publish_address=true to enforce non-deprecated formatting.",
65+
66+
"transport.test_profile.publish_address was printed as [ip:port] instead of [hostname/ip:port]. " +
67+
"This format is deprecated and will change to [hostname/ip:port] in a future version. " +
68+
"Use -Des.transport.cname_in_publish_address=true to enforce non-deprecated formatting.");
69+
}
70+
71+
public void testCorrectDisplayPublishedIp() throws Exception {
72+
InetAddress address = InetAddress.getByName(NetworkAddress.format(InetAddress.getByName("localhost")));
73+
int port = 9200;
74+
assertPublishAddress(
75+
createTransportInfo(address, port,true),
76+
NetworkAddress.format(address) + ':' + port
77+
);
78+
}
79+
80+
public void testCorrectDisplayPublishedIpv6() throws Exception {
81+
InetAddress address = InetAddress.getByName(NetworkAddress.format(InetAddress.getByName("0:0:0:0:0:0:0:1")));
82+
int port = 9200;
83+
assertPublishAddress(
84+
createTransportInfo(address, port,true),
85+
new TransportAddress(address, port).toString()
86+
);
87+
}
88+
89+
@SuppressWarnings("unchecked")
90+
private void assertPublishAddress(TransportInfo httpInfo, String expected) throws IOException {
91+
XContentBuilder builder = XContentFactory.jsonBuilder();
92+
builder.startObject();
93+
httpInfo.toXContent(builder, ToXContent.EMPTY_PARAMS);
94+
builder.endObject();
95+
96+
Map<String, Object> transportMap = (Map<String, Object>) createParser(builder).map().get(TransportInfo.Fields.TRANSPORT);
97+
Map<String, Object> profilesMap = (Map<String, Object>) transportMap.get("profiles");
98+
assertEquals(
99+
expected,
100+
transportMap.get(TransportInfo.Fields.PUBLISH_ADDRESS)
101+
);
102+
assertEquals(
103+
expected,
104+
((Map<String, Object>)profilesMap.get("test_profile")).get(TransportInfo.Fields.PUBLISH_ADDRESS)
105+
);
106+
}
107+
}

0 commit comments

Comments
 (0)