|
7 | 7 | */ |
8 | 8 | package org.seedstack.seed.core.internal.configuration; |
9 | 9 |
|
| 10 | +import org.seedstack.coffig.spi.ConfigFunction; |
| 11 | +import org.seedstack.coffig.spi.ConfigFunctionHolder; |
| 12 | + |
| 13 | +import javax.net.ServerSocketFactory; |
10 | 14 | import java.io.IOException; |
11 | 15 | import java.net.DatagramSocket; |
12 | 16 | import java.net.InetAddress; |
13 | 17 | import java.net.ServerSocket; |
14 | | -import javax.net.ServerSocketFactory; |
15 | | -import org.seedstack.coffig.spi.ConfigFunction; |
16 | | -import org.seedstack.coffig.spi.ConfigFunctionHolder; |
| 18 | +import java.util.concurrent.ConcurrentHashMap; |
| 19 | +import java.util.concurrent.ConcurrentMap; |
17 | 20 |
|
18 | 21 | public class AvailablePortFunctionHolder implements ConfigFunctionHolder { |
| 22 | + private static final ConcurrentMap<String, Integer> TCP_PORTS = new ConcurrentHashMap<>(); |
| 23 | + private static final ConcurrentMap<String, Integer> UDP_PORTS = new ConcurrentHashMap<>(); |
19 | 24 | private static final int PORT_RANGE_MIN = 49152; |
20 | 25 | private static final int PORT_RANGE_MAX = 65535; |
21 | | - private static final Object TCP_SYNC = new Object(); |
22 | | - private static final Object UDP_SYNC = new Object(); |
23 | 26 |
|
24 | 27 | @ConfigFunction |
25 | | - int availableTcpPort() { |
26 | | - synchronized (TCP_SYNC) { |
27 | | - for (int i = PORT_RANGE_MIN; i <= PORT_RANGE_MAX; i++) { |
28 | | - if (isTcpPortAvailable(i)) { |
29 | | - return i; |
| 28 | + int availableTcpPort(String name) { |
| 29 | + return TCP_PORTS.computeIfAbsent(name, n -> { |
| 30 | + synchronized (TCP_PORTS) { |
| 31 | + for (int i = PORT_RANGE_MIN; i <= PORT_RANGE_MAX; i++) { |
| 32 | + if (isTcpPortAvailable(i)) { |
| 33 | + return i; |
| 34 | + } |
30 | 35 | } |
| 36 | + throw new IllegalStateException("Unable to find an available TCP port in range " + PORT_RANGE_MIN + "-" + PORT_RANGE_MAX); |
31 | 37 | } |
32 | | - } |
33 | | - throw new IllegalStateException("Unable to find an available TCP port in range " + PORT_RANGE_MIN + "-" + |
34 | | - PORT_RANGE_MAX); |
| 38 | + }); |
35 | 39 | } |
36 | 40 |
|
37 | 41 | @ConfigFunction |
38 | | - int availableUdpPort() { |
39 | | - synchronized (UDP_SYNC) { |
40 | | - for (int i = PORT_RANGE_MIN; i <= PORT_RANGE_MAX; i++) { |
41 | | - if (isUdpPortAvailable(i)) { |
42 | | - return i; |
| 42 | + int availableUdpPort(String name) { |
| 43 | + return UDP_PORTS.computeIfAbsent(name, n -> { |
| 44 | + synchronized (UDP_PORTS) { |
| 45 | + for (int i = PORT_RANGE_MIN; i <= PORT_RANGE_MAX; i++) { |
| 46 | + if (isUdpPortAvailable(i)) { |
| 47 | + return i; |
| 48 | + } |
43 | 49 | } |
44 | 50 | } |
45 | | - } |
46 | | - throw new IllegalStateException("Unable to find an available UDP port in range " + PORT_RANGE_MIN + "-" + |
47 | | - PORT_RANGE_MAX); |
| 51 | + throw new IllegalStateException("Unable to find an available UDP port in range " + PORT_RANGE_MIN + "-" + PORT_RANGE_MAX); |
| 52 | + }); |
48 | 53 | } |
49 | 54 |
|
50 | 55 | private boolean isTcpPortAvailable(int port) { |
|
0 commit comments