diff --git a/sync/src/main/java/org/mvndaemon/mvnd/sync/IpcClient.java b/sync/src/main/java/org/mvndaemon/mvnd/sync/IpcClient.java index 56ac67eb..cf1a3f2b 100644 --- a/sync/src/main/java/org/mvndaemon/mvnd/sync/IpcClient.java +++ b/sync/src/main/java/org/mvndaemon/mvnd/sync/IpcClient.java @@ -132,6 +132,10 @@ public class IpcClient { } args.add("-cp"); args.add(classpath); + String timeout = System.getProperty(IpcServer.IDLE_TIMEOUT_PROP); + if (timeout != null) { + args.add("-D" + IpcServer.IDLE_TIMEOUT_PROP + "=" + timeout); + } args.add(IpcServer.class.getName()); args.add(Integer.toString(tmpport)); args.add(Integer.toString(rand)); diff --git a/sync/src/main/java/org/mvndaemon/mvnd/sync/IpcServer.java b/sync/src/main/java/org/mvndaemon/mvnd/sync/IpcServer.java index 07aa0e91..bc53064e 100644 --- a/sync/src/main/java/org/mvndaemon/mvnd/sync/IpcServer.java +++ b/sync/src/main/java/org/mvndaemon/mvnd/sync/IpcServer.java @@ -46,6 +46,8 @@ import static org.mvndaemon.mvnd.sync.IpcMessages.RESPONSE_CONTEXT; */ public class IpcServer { + public static final String IDLE_TIMEOUT_PROP = "ipcsync.idle.timeout"; + static final long IDLE_TIMEOUT = TimeUnit.SECONDS.toNanos(60); private final ServerSocket serverSocket; @@ -53,13 +55,24 @@ public class IpcServer { private final AtomicInteger counter = new AtomicInteger(); private final Map locks = new ConcurrentHashMap<>(); private final Map contexts = new ConcurrentHashMap<>(); - + private final long idleTimeout; private volatile long lastUsed; private volatile boolean closing; public IpcServer() throws IOException { serverSocket = new ServerSocket(); serverSocket.bind(new InetSocketAddress(InetAddress.getLoopbackAddress(), 0)); + long timeout = IDLE_TIMEOUT; + String str = System.getProperty(IDLE_TIMEOUT_PROP); + if (str != null) { + try { + long dur = Long.parseLong(str); + timeout = TimeUnit.SECONDS.toNanos(dur); + } catch (NumberFormatException e) { + error("Property " + IDLE_TIMEOUT_PROP + " specified with invalid value: " + str, e); + } + } + idleTimeout = timeout; } public static void main(String[] args) throws Exception { @@ -77,8 +90,7 @@ public class IpcServer { sun.misc.Signal.handle(new sun.misc.Signal("TSTP"), sun.misc.SignalHandler.SIG_IGN); } } catch (Throwable t) { - System.err.println("Unable to ignore INT and TSTP signals"); - t.printStackTrace(); + error("Unable to ignore INT and TSTP signals", t); } int tmpPort = Integer.parseInt(args[0]); @@ -251,7 +263,7 @@ public class IpcServer { private void expirationCheck() { while (true) { long current = System.nanoTime(); - if (current - lastUsed > IDLE_TIMEOUT) { + if (current - lastUsed > idleTimeout) { close(); break; } diff --git a/sync/src/test/java/org/mvndaemon/mvnd/sync/IpcSyncContextTest.java b/sync/src/test/java/org/mvndaemon/mvnd/sync/IpcSyncContextTest.java index 61472a4c..bead3937 100644 --- a/sync/src/test/java/org/mvndaemon/mvnd/sync/IpcSyncContextTest.java +++ b/sync/src/test/java/org/mvndaemon/mvnd/sync/IpcSyncContextTest.java @@ -25,10 +25,22 @@ import org.eclipse.aether.impl.SyncContextFactory; import org.eclipse.aether.internal.impl.SimpleLocalRepositoryManagerFactory; import org.eclipse.aether.repository.LocalRepository; import org.eclipse.aether.repository.LocalRepositoryManager; +import org.junit.jupiter.api.AfterAll; +import org.junit.jupiter.api.BeforeAll; import org.junit.jupiter.api.Test; public class IpcSyncContextTest { + @BeforeAll + static void setup() { + System.setProperty(IpcServer.IDLE_TIMEOUT_PROP, "5"); + } + + @AfterAll + static void tearDown() { + System.clearProperty(IpcServer.IDLE_TIMEOUT_PROP); + } + @Test public void testContextSimple() throws Exception { SyncContextFactory factory = new IpcSyncContextFactory();