Skip to content

Commit

Permalink
[Enhancement] Use ThreadLocalRandom and try-with-resource (#3239)
Browse files Browse the repository at this point in the history
* polish

* fix code reviews

* empty
  • Loading branch information
kun-song authored and beiwei30 committed Jan 31, 2019
1 parent ea45921 commit dbab8c5
Show file tree
Hide file tree
Showing 4 changed files with 48 additions and 65 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -32,47 +32,41 @@
import java.net.UnknownHostException;
import java.util.Enumeration;
import java.util.Map;
import java.util.Random;
import java.util.Optional;
import java.util.concurrent.ThreadLocalRandom;
import java.util.regex.Pattern;

/**
* IP and Port Helper for RPC
*/
public class NetUtils {

private static final Logger logger = LoggerFactory.getLogger(NetUtils.class);
private static final int RND_PORT_START = 30000;

// returned port range is [30000, 39999]
private static final int RND_PORT_START = 30000;
private static final int RND_PORT_RANGE = 10000;

private static final Random RANDOM = new Random(System.currentTimeMillis());
// valid port range is (0, 65535]
private static final int MIN_PORT = 0;
private static final int MAX_PORT = 65535;

private static final Pattern ADDRESS_PATTERN = Pattern.compile("^\\d{1,3}(\\.\\d{1,3}){3}\\:\\d{1,5}$");
private static final Pattern LOCAL_IP_PATTERN = Pattern.compile("127(\\.\\d{1,3}){3}$");
private static final Pattern IP_PATTERN = Pattern.compile("\\d{1,3}(\\.\\d{1,3}){3,5}$");
private static final Map<String, String> hostNameCache = new LRUCache<String, String>(1000);

private static final Map<String, String> hostNameCache = new LRUCache<>(1000);
private static volatile InetAddress LOCAL_ADDRESS = null;

public static int getRandomPort() {
return RND_PORT_START + RANDOM.nextInt(RND_PORT_RANGE);
return RND_PORT_START + ThreadLocalRandom.current().nextInt(RND_PORT_RANGE);
}

public static int getAvailablePort() {
ServerSocket ss = null;
try {
ss = new ServerSocket();
try (ServerSocket ss = new ServerSocket()) {
ss.bind(null);
return ss.getLocalPort();
} catch (IOException e) {
return getRandomPort();
} finally {
if (ss != null) {
try {
ss.close();
} catch (IOException e) {
}
}
}
}

Expand All @@ -81,19 +75,10 @@ public static int getAvailablePort(int port) {
return getAvailablePort();
}
for (int i = port; i < MAX_PORT; i++) {
ServerSocket ss = null;
try {
ss = new ServerSocket(i);
try (ServerSocket ss = new ServerSocket(i)) {
return i;
} catch (IOException e) {
// continue
} finally {
if (ss != null) {
try {
ss.close();
} catch (IOException e) {
}
}
}
}
return port;
Expand Down Expand Up @@ -134,7 +119,7 @@ public static InetSocketAddress getLocalSocketAddress(String host, int port) {
new InetSocketAddress(port) : new InetSocketAddress(host, port);
}

static boolean isValidAddress(InetAddress address) {
static boolean isValidV4Address(InetAddress address) {
if (address == null || address.isLoopbackAddress()) {
return false;
}
Expand Down Expand Up @@ -233,21 +218,31 @@ public static InetAddress getLocalAddress() {
return localAddress;
}

private static Optional<InetAddress> toValidAddress(InetAddress address) {
if (address instanceof Inet6Address) {
Inet6Address v6Address = (Inet6Address) address;
if (isValidV6Address(v6Address)) {
return Optional.ofNullable(normalizeV6Address(v6Address));
}
}
if (isValidV4Address(address)) {
return Optional.of(address);
}
return Optional.empty();
}

private static InetAddress getLocalAddress0() {
InetAddress localAddress = null;
try {
localAddress = InetAddress.getLocalHost();
if (localAddress instanceof Inet6Address) {
Inet6Address address = (Inet6Address) localAddress;
if (isValidV6Address(address)) {
return normalizeV6Address(address);
}
} else if (isValidAddress(localAddress)) {
return localAddress;
Optional<InetAddress> addressOp = toValidAddress(localAddress);
if (addressOp.isPresent()) {
return addressOp.get();
}
} catch (Throwable e) {
logger.warn(e);
}

try {
Enumeration<NetworkInterface> interfaces = NetworkInterface.getNetworkInterfaces();
if (null == interfaces) {
Expand All @@ -259,14 +254,9 @@ private static InetAddress getLocalAddress0() {
Enumeration<InetAddress> addresses = network.getInetAddresses();
while (addresses.hasMoreElements()) {
try {
InetAddress address = addresses.nextElement();
if (address instanceof Inet6Address) {
Inet6Address v6Address = (Inet6Address) address;
if (isValidV6Address(v6Address)) {
return normalizeV6Address(v6Address);
}
} else if (isValidAddress(address)) {
return address;
Optional<InetAddress> addressOp = toValidAddress(addresses.nextElement());
if (addressOp.isPresent()) {
return addressOp.get();
}
} catch (Throwable e) {
logger.warn(e);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -104,22 +104,22 @@ public void testGetLocalSocketAddress() throws Exception {

@Test
public void testIsValidAddress() throws Exception {
assertFalse(NetUtils.isValidAddress((InetAddress) null));
assertFalse(NetUtils.isValidV4Address((InetAddress) null));
InetAddress address = mock(InetAddress.class);
when(address.isLoopbackAddress()).thenReturn(true);
assertFalse(NetUtils.isValidAddress(address));
assertFalse(NetUtils.isValidV4Address(address));
address = mock(InetAddress.class);
when(address.getHostAddress()).thenReturn("localhost");
assertFalse(NetUtils.isValidAddress(address));
assertFalse(NetUtils.isValidV4Address(address));
address = mock(InetAddress.class);
when(address.getHostAddress()).thenReturn("0.0.0.0");
assertFalse(NetUtils.isValidAddress(address));
assertFalse(NetUtils.isValidV4Address(address));
address = mock(InetAddress.class);
when(address.getHostAddress()).thenReturn("127.0.0.1");
assertFalse(NetUtils.isValidAddress(address));
assertFalse(NetUtils.isValidV4Address(address));
address = mock(InetAddress.class);
when(address.getHostAddress()).thenReturn("1.2.3.4");
assertTrue(NetUtils.isValidAddress(address));
assertTrue(NetUtils.isValidV4Address(address));
}

@Test
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -40,12 +40,12 @@
import java.util.Iterator;
import java.util.Map;
import java.util.Properties;
import java.util.Random;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.ScheduledExecutorService;
import java.util.concurrent.ScheduledFuture;
import java.util.concurrent.ThreadLocalRandom;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.atomic.AtomicBoolean;
import java.util.concurrent.atomic.AtomicInteger;
Expand All @@ -62,13 +62,13 @@ public abstract class AbstractMetadataReport implements MetadataReport {
// Log output
protected final Logger logger = LoggerFactory.getLogger(getClass());

// Local disk cache, where the special key value.registies records the list of registry centers, and the others are the list of notified service providers
// Local disk cache, where the special key value.registries records the list of registry centers, and the others are the list of notified service providers
final Properties properties = new Properties();
private final ExecutorService reportCacheExecutor = Executors.newFixedThreadPool(1, new NamedThreadFactory("DubboSaveMetadataReport", true));
final Map<MetadataIdentifier, Object> allMetadataReports = new ConcurrentHashMap<MetadataIdentifier, Object>(4);
final Map<MetadataIdentifier, Object> allMetadataReports = new ConcurrentHashMap<>(4);

private final AtomicLong lastCacheChanged = new AtomicLong();
final Map<MetadataIdentifier, Object> failedReports = new ConcurrentHashMap<MetadataIdentifier, Object>(4);
final Map<MetadataIdentifier, Object> failedReports = new ConcurrentHashMap<>(4);
private URL reportURL;
boolean syncReport;
// Local disk cache file
Expand Down Expand Up @@ -101,12 +101,7 @@ public AbstractMetadataReport(URL reportServerURL) {
// cycle report the data switch
if (reportServerURL.getParameter(Constants.CYCLE_REPORT_KEY, Constants.DEFAULT_METADATA_REPORT_CYCLE_REPORT)) {
ScheduledExecutorService scheduler = Executors.newSingleThreadScheduledExecutor(new NamedThreadFactory("DubboMetadataReportTimer", true));
scheduler.scheduleAtFixedRate(new Runnable() {
@Override
public void run() {
publishAll();
}
}, calculateStartTime(), ONE_DAY_IN_MIll, TimeUnit.MILLISECONDS);
scheduler.scheduleAtFixedRate(this::publishAll, calculateStartTime(), ONE_DAY_IN_MIll, TimeUnit.MILLISECONDS);
}
}

Expand Down Expand Up @@ -335,8 +330,7 @@ long calculateStartTime() {
calendar.set(Calendar.SECOND, 0);
calendar.set(Calendar.MILLISECOND, 0);
long subtract = calendar.getTimeInMillis() + ONE_DAY_IN_MIll - nowMill;
Random r = new Random();
return subtract + (FOUR_HOURS_IN_MIll / 2) + r.nextInt(FOUR_HOURS_IN_MIll);
return subtract + (FOUR_HOURS_IN_MIll / 2) + ThreadLocalRandom.current().nextInt(FOUR_HOURS_IN_MIll);
}

class MetadataReportRetry {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -43,13 +43,13 @@
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Random;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentMap;
import java.util.concurrent.Executors;
import java.util.concurrent.ScheduledExecutorService;
import java.util.concurrent.ScheduledFuture;
import java.util.concurrent.ThreadLocalRandom;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.atomic.AtomicInteger;

Expand All @@ -72,7 +72,7 @@ public class RedisRegistry extends FailbackRegistry {

private final Map<String, JedisPool> jedisPools = new ConcurrentHashMap<>();

private final ConcurrentMap<String, Notifier> notifiers = new ConcurrentHashMap<String, Notifier>();
private final ConcurrentMap<String, Notifier> notifiers = new ConcurrentHashMap<>();

private final int reconnectPeriod;

Expand Down Expand Up @@ -122,7 +122,7 @@ public RedisRegistry(URL url) {
}
replicate = "replicate".equals(cluster);

List<String> addresses = new ArrayList<String>();
List<String> addresses = new ArrayList<>();
addresses.add(url.getAddress());
String[] backups = url.getParameter(Constants.BACKUP_KEY, new String[0]);
if (ArrayUtils.isNotEmpty(backups)) {
Expand Down Expand Up @@ -518,7 +518,6 @@ private class Notifier extends Thread {
private final String service;
private final AtomicInteger connectSkip = new AtomicInteger();
private final AtomicInteger connectSkipped = new AtomicInteger();
private final Random random = new Random();
private volatile Jedis jedis;
private volatile boolean first = true;
private volatile boolean running = true;
Expand All @@ -540,7 +539,7 @@ private boolean isSkip() {
int skip = connectSkip.get(); // Growth of skipping times
if (skip >= 10) { // If the number of skipping times increases by more than 10, take the random number
if (connectRandom == 0) {
connectRandom = random.nextInt(10);
connectRandom = ThreadLocalRandom.current().nextInt(10);
}
skip = 10 + connectRandom;
}
Expand Down

0 comments on commit dbab8c5

Please sign in to comment.