Refactor ProcessWrapper to conditionally, based on System property, to forcibly destroy a forked JVM (child) process on shutdown.
This commit is contained in:
@@ -40,6 +40,7 @@ import org.springframework.data.gemfire.tests.util.IOUtils;
|
||||
import org.springframework.data.gemfire.tests.util.ThreadUtils;
|
||||
import org.springframework.data.gemfire.tests.util.ThrowableUtils;
|
||||
import org.springframework.lang.NonNull;
|
||||
import org.springframework.lang.Nullable;
|
||||
import org.springframework.util.Assert;
|
||||
import org.springframework.util.StringUtils;
|
||||
|
||||
@@ -59,6 +60,7 @@ import org.springframework.util.StringUtils;
|
||||
* @see java.util.concurrent.Future
|
||||
* @see org.springframework.data.gemfire.tests.process.ProcessConfiguration
|
||||
* @see org.springframework.data.gemfire.tests.process.ProcessInputStreamListener
|
||||
* @see org.springframework.data.gemfire.tests.process.ProcessUtils
|
||||
* @since 0.0.1
|
||||
*/
|
||||
@SuppressWarnings("unused")
|
||||
@@ -72,6 +74,8 @@ public class ProcessWrapper {
|
||||
|
||||
protected static final String DEFAULT_HOST = "localhost";
|
||||
|
||||
protected static final String PROCESS_DESTROY_FORCIBLY_PROPERTY = "spring.data.gemfire.test.process.destroy-forcibly";
|
||||
|
||||
private final List<ProcessInputStreamListener> listeners = new CopyOnWriteArrayList<>();
|
||||
|
||||
protected final Logger log = Logger.getLogger(getClass().getName());
|
||||
@@ -220,12 +224,12 @@ public class ProcessWrapper {
|
||||
}
|
||||
}
|
||||
|
||||
public ProcessWrapper listeningOn(int port) {
|
||||
public @NonNull ProcessWrapper listeningOn(int port) {
|
||||
this.port = Math.max(port, DEFAULT_PORT);
|
||||
return this;
|
||||
}
|
||||
|
||||
public String readLogFile() throws IOException {
|
||||
public @NonNull String readLogFile() throws IOException {
|
||||
|
||||
File[] logFiles = FileSystemUtils.listFiles(getWorkingDirectory(),
|
||||
path -> (path != null && (path.isDirectory() || path.getAbsolutePath().endsWith(".log"))));
|
||||
@@ -239,20 +243,20 @@ public class ProcessWrapper {
|
||||
}
|
||||
}
|
||||
|
||||
public String readLogFile(File log) throws IOException {
|
||||
public @NonNull String readLogFile(@NonNull File log) throws IOException {
|
||||
return FileUtils.read(log);
|
||||
}
|
||||
|
||||
public boolean register(ProcessInputStreamListener listener) {
|
||||
public boolean register(@Nullable ProcessInputStreamListener listener) {
|
||||
return listener != null && listeners.add(listener);
|
||||
}
|
||||
|
||||
public ProcessWrapper registerShutdownHook() {
|
||||
public @NonNull ProcessWrapper registerShutdownHook() {
|
||||
Runtime.getRuntime().addShutdownHook(new Thread(this::shutdown));
|
||||
return this;
|
||||
}
|
||||
|
||||
public ProcessWrapper runningOn(String host) {
|
||||
public @NonNull ProcessWrapper runningOn(@Nullable String host) {
|
||||
this.host = StringUtils.hasText(host) ? host : DEFAULT_HOST;
|
||||
return this;
|
||||
}
|
||||
@@ -331,6 +335,7 @@ public class ProcessWrapper {
|
||||
interrupted = true;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
catch (TimeoutException cause) {
|
||||
exitValue = -1;
|
||||
@@ -361,7 +366,7 @@ public class ProcessWrapper {
|
||||
|
||||
if (isRunning()) {
|
||||
stop();
|
||||
if (isRunning()) {
|
||||
if (isRunning() && isShutdownForciblyEnabled()) {
|
||||
this.process.destroyForcibly();
|
||||
}
|
||||
}
|
||||
@@ -369,6 +374,10 @@ public class ProcessWrapper {
|
||||
return safeExitValue();
|
||||
}
|
||||
|
||||
private boolean isShutdownForciblyEnabled() {
|
||||
return Boolean.getBoolean(PROCESS_DESTROY_FORCIBLY_PROPERTY);
|
||||
}
|
||||
|
||||
public boolean unregister(ProcessInputStreamListener listener) {
|
||||
return this.listeners.remove(listener);
|
||||
}
|
||||
|
||||
@@ -30,8 +30,7 @@ import org.springframework.lang.Nullable;
|
||||
import org.springframework.util.Assert;
|
||||
|
||||
/**
|
||||
* The {@link FileSystemUtils} class is a utility class encapsulating functionality to process
|
||||
* file system directories and files collectively.
|
||||
* Abstract utility class encapsulating functionality to process file system directories and files collectively.
|
||||
*
|
||||
* @author John Blum
|
||||
* @see java.io.File
|
||||
@@ -51,11 +50,11 @@ public abstract class FileSystemUtils extends FileUtils {
|
||||
|
||||
public static final File[] NO_FILES = new File[0];
|
||||
|
||||
public static boolean deleteRecursive(File path) {
|
||||
public static boolean deleteRecursive(@Nullable File path) {
|
||||
return deleteRecursive(path, AllFilesFilter.INSTANCE);
|
||||
}
|
||||
|
||||
public static boolean deleteRecursive(File path, FileFilter fileFilter) {
|
||||
public static boolean deleteRecursive(@Nullable File path, @Nullable FileFilter fileFilter) {
|
||||
|
||||
boolean success = true;
|
||||
|
||||
@@ -72,7 +71,7 @@ public abstract class FileSystemUtils extends FileUtils {
|
||||
return path != null && path.exists();
|
||||
}
|
||||
|
||||
// returns sub-directory just below working directory
|
||||
// returns subdirectory just below working directory
|
||||
public static @Nullable File getRootRelativeToWorkingDirectoryOrPath(@Nullable File path) {
|
||||
|
||||
File localPath = path;
|
||||
@@ -83,12 +82,10 @@ public abstract class FileSystemUtils extends FileUtils {
|
||||
}
|
||||
}
|
||||
|
||||
return localPath != null
|
||||
? localPath
|
||||
: path;
|
||||
return localPath != null ? localPath : path;
|
||||
}
|
||||
|
||||
public static boolean isEmpty(File path) {
|
||||
public static boolean isEmpty(@Nullable File path) {
|
||||
|
||||
return isDirectory(path)
|
||||
? ArrayUtils.isEmpty(path.listFiles())
|
||||
@@ -120,13 +117,9 @@ public abstract class FileSystemUtils extends FileUtils {
|
||||
|
||||
public static @NonNull File[] safeListFiles(@Nullable File directory, @Nullable FileFilter fileFilter) {
|
||||
|
||||
FileFilter resolvedFileFilter = fileFilter != null
|
||||
? fileFilter
|
||||
: AllFilesFilter.INSTANCE;
|
||||
FileFilter resolvedFileFilter = fileFilter != null ? fileFilter : AllFilesFilter.INSTANCE;
|
||||
|
||||
File[] files = isDirectory(directory)
|
||||
? directory.listFiles(resolvedFileFilter)
|
||||
: null;
|
||||
File[] files = isDirectory(directory) ? directory.listFiles(resolvedFileFilter) : null;
|
||||
|
||||
return files != null
|
||||
? files
|
||||
|
||||
@@ -22,17 +22,15 @@ import java.io.FileReader;
|
||||
import java.io.FileWriter;
|
||||
import java.io.IOException;
|
||||
|
||||
import org.springframework.lang.NonNull;
|
||||
import org.springframework.util.Assert;
|
||||
import org.springframework.util.StringUtils;
|
||||
|
||||
/**
|
||||
* The {@link FileUtils} class is an abstract utility class for processing file system files
|
||||
* by working with {@link File} objects.
|
||||
* Abstract utility class for processing file system files by using {@link File} objects.
|
||||
*
|
||||
* @author John Blum
|
||||
* @see java.io.File
|
||||
* @see java.io.FileReader
|
||||
* @see java.io.FileWriter
|
||||
* @see org.springframework.data.gemfire.tests.util.IOUtils
|
||||
* @since 0.0.1
|
||||
*/
|
||||
@@ -50,11 +48,11 @@ public abstract class FileUtils extends IOUtils {
|
||||
return path != null && path.isFile();
|
||||
}
|
||||
|
||||
public static File newFile(String pathname) {
|
||||
public static @NonNull File newFile(String pathname) {
|
||||
return new File(pathname);
|
||||
}
|
||||
|
||||
public static File newFile(File parent, String pathname) {
|
||||
public static @NonNull File newFile(File parent, String pathname) {
|
||||
return new File(parent, pathname);
|
||||
}
|
||||
|
||||
@@ -62,13 +60,11 @@ public abstract class FileUtils extends IOUtils {
|
||||
return path != null ? path.length() : 0L;
|
||||
}
|
||||
|
||||
public static String read(File file) throws IOException {
|
||||
public static @NonNull String read(@NonNull File file) throws IOException {
|
||||
|
||||
Assert.isTrue(isFile(file), String.format("The File [%s] to read the contents from is not a valid file", file));
|
||||
|
||||
BufferedReader fileReader = new BufferedReader(new FileReader(file));
|
||||
|
||||
try {
|
||||
try (BufferedReader fileReader = new BufferedReader(new FileReader(file))) {
|
||||
|
||||
StringBuilder buffer = new StringBuilder();
|
||||
|
||||
@@ -79,12 +75,9 @@ public abstract class FileUtils extends IOUtils {
|
||||
|
||||
return buffer.toString().trim();
|
||||
}
|
||||
finally {
|
||||
close(fileReader);
|
||||
}
|
||||
}
|
||||
|
||||
public static void write(File file, String contents) throws IOException {
|
||||
public static void write(@NonNull File file, @NonNull String contents) throws IOException {
|
||||
|
||||
Assert.notNull(file, "File is required");
|
||||
|
||||
|
||||
@@ -13,7 +13,6 @@
|
||||
* or implied. See the License for the specific language governing
|
||||
* permissions and limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.data.gemfire.tests.util;
|
||||
|
||||
import java.io.ByteArrayInputStream;
|
||||
@@ -26,8 +25,11 @@ import java.io.Serializable;
|
||||
import java.util.logging.Level;
|
||||
import java.util.logging.Logger;
|
||||
|
||||
import org.springframework.lang.NonNull;
|
||||
import org.springframework.lang.Nullable;
|
||||
|
||||
/**
|
||||
* The {@link IOUtils} class is an abstract utility class for working with IO operations.
|
||||
* Abstract utility class used to process IO operations.
|
||||
*
|
||||
* @author John Blum
|
||||
* @see java.io.Closeable
|
||||
@@ -39,7 +41,7 @@ public abstract class IOUtils {
|
||||
|
||||
protected static final Logger log = Logger.getLogger(IOUtils.class.getName());
|
||||
|
||||
public static boolean close(Closeable closeable) {
|
||||
public static boolean close(@Nullable Closeable closeable) {
|
||||
|
||||
if (closeable != null) {
|
||||
try {
|
||||
@@ -67,7 +69,7 @@ public abstract class IOUtils {
|
||||
* threw an {@link IOException}.
|
||||
* @see IOException
|
||||
*/
|
||||
public static boolean doSafeIo(IoExceptionThrowingOperation operation) {
|
||||
public static boolean doSafeIo(@NonNull IoExceptionThrowingOperation operation) {
|
||||
|
||||
try {
|
||||
operation.doIo();
|
||||
@@ -87,7 +89,6 @@ public abstract class IOUtils {
|
||||
|
||||
try {
|
||||
objectInputStream = new ObjectInputStream(byteArrayInputStream);
|
||||
|
||||
return (T) objectInputStream.readObject();
|
||||
}
|
||||
finally {
|
||||
@@ -105,7 +106,6 @@ public abstract class IOUtils {
|
||||
objectOutputStream = new ObjectOutputStream(byteArrayOutputStream);
|
||||
objectOutputStream.writeObject(obj);
|
||||
objectOutputStream.flush();
|
||||
|
||||
return byteArrayOutputStream.toByteArray();
|
||||
}
|
||||
finally {
|
||||
|
||||
Reference in New Issue
Block a user