diff --git a/core/src/main/java/org/elasticsearch/common/network/NetworkUtils.java b/core/src/main/java/org/elasticsearch/common/network/NetworkUtils.java index 8652d4c5c05..9e06c39b83e 100644 --- a/core/src/main/java/org/elasticsearch/common/network/NetworkUtils.java +++ b/core/src/main/java/org/elasticsearch/common/network/NetworkUtils.java @@ -32,6 +32,7 @@ import java.util.Arrays; import java.util.Collections; import java.util.Comparator; import java.util.List; +import java.util.Optional; /** * Utilities for network interfaces / addresses binding and publishing. @@ -227,14 +228,15 @@ public abstract class NetworkUtils { /** Returns addresses for the given interface (it must be marked up) */ static InetAddress[] getAddressesForInterface(String name) throws SocketException { - NetworkInterface intf = NetworkInterface.getByName(name); - if (intf == null) { + Optional networkInterface = getInterfaces().stream().filter((netIf) -> name.equals(netIf.getName())).findFirst(); + + if (networkInterface.isPresent() == false) { throw new IllegalArgumentException("No interface named '" + name + "' found, got " + getInterfaces()); } - if (!intf.isUp()) { + if (!networkInterface.get().isUp()) { throw new IllegalArgumentException("Interface '" + name + "' is not up and running"); } - List list = Collections.list(intf.getInetAddresses()); + List list = Collections.list(networkInterface.get().getInetAddresses()); if (list.isEmpty()) { throw new IllegalArgumentException("Interface '" + name + "' has no internet addresses"); } diff --git a/core/src/test/java/org/elasticsearch/common/network/NetworkUtilsTests.java b/core/src/test/java/org/elasticsearch/common/network/NetworkUtilsTests.java index e5b95f258a3..85a74724161 100644 --- a/core/src/test/java/org/elasticsearch/common/network/NetworkUtilsTests.java +++ b/core/src/test/java/org/elasticsearch/common/network/NetworkUtilsTests.java @@ -22,6 +22,10 @@ package org.elasticsearch.common.network; import org.elasticsearch.test.ESTestCase; import java.net.InetAddress; +import java.net.NetworkInterface; +import java.util.Collections; + +import static org.hamcrest.Matchers.containsString; /** * Tests for network utils. Please avoid using any methods that cause DNS lookups! @@ -74,4 +78,30 @@ public class NetworkUtilsTests extends ESTestCase { assertArrayEquals(new InetAddress[] { InetAddress.getByName("127.0.0.1") }, NetworkUtils.filterIPV4(addresses)); assertArrayEquals(new InetAddress[] { InetAddress.getByName("::1") }, NetworkUtils.filterIPV6(addresses)); } + + /** + * Test that selecting by name is possible and properly matches the addresses on all interfaces and virtual + * interfaces. + * + * Note that to avoid that this test fails when interfaces are down or they do not have addresses assigned to them, + * they are ignored. + */ + public void testAddressInterfaceLookup() throws Exception { + for (NetworkInterface netIf : NetworkUtils.getInterfaces()) { + if (!netIf.isUp() || Collections.list(netIf.getInetAddresses()).isEmpty()) { + continue; + } + + String name = netIf.getName(); + InetAddress[] expectedAddresses = Collections.list(netIf.getInetAddresses()).toArray(new InetAddress[0]); + InetAddress[] foundAddresses = NetworkUtils.getAddressesForInterface(name); + assertArrayEquals(expectedAddresses, foundAddresses); + } + } + + public void testNonExistingInterface() throws Exception { + IllegalArgumentException exception = expectThrows(IllegalArgumentException.class, + () -> NetworkUtils.getAddressesForInterface("non-existing")); + assertThat(exception.getMessage(), containsString("No interface named 'non-existing' found")); + } }