All Downloads are FREE. Search and download functionalities are using the official Maven repository.

com.github.mike10004.nativehelper.subprocess.ScopedProcessTracker Maven / Gradle / Ivy

There is a newer version: 10.0.0
Show newest version
package com.github.mike10004.nativehelper.subprocess;

import java.util.Collections;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import java.util.concurrent.TimeUnit;
import java.util.stream.Collectors;

import static com.google.common.base.Preconditions.checkState;

/**
 * Implementation of a process tracker that can be used in a try-with-resources
 * block. When execution exits the block, all the processes are destroyed
 * using {@link #destroyAll()}.
 */
public class ScopedProcessTracker implements ProcessTracker, AutoCloseable {

    public static final long DEFAULT_DESTROY_TIMEOUT_MILLIS = 500;

    private final Set processes;
    private final long destroyTimeoutMillis;

    public ScopedProcessTracker() {
        this(DEFAULT_DESTROY_TIMEOUT_MILLIS);
    }

    ScopedProcessTracker(long destroyTimeoutMillis) {
        // we can probably remove this synchro wrapper because all our methods are synchronized
        this.processes = Collections.synchronizedSet(new HashSet<>());
        this.destroyTimeoutMillis = destroyTimeoutMillis;
    }

    @Override
    public synchronized void add(Process process) {
        processes.add(process);
        checkState(processes.contains(process), "failed to add %s", process);
    }

    @Override
    public synchronized boolean remove(Process process) {
        return processes.remove(process);
    }

    @Override
    public synchronized int activeCount() {
        return processes.size();
    }

    public List destroyAll() {
        return ProcessTracker.destroyAll(processes, destroyTimeoutMillis, TimeUnit.MILLISECONDS);
    }

    @Override
    public synchronized void close() throws ProcessStillAliveException {
        List undestroyed = destroyAll();
        List stillAlive = undestroyed.stream().filter(Process::isAlive).collect(Collectors.toList());
        processes.retainAll(stillAlive);
        int stillAliveCount = stillAlive.size();
        if (stillAliveCount > 0) {
            throw new ProcessStillAliveException(stillAliveCount + " processes still alive");
        }
    }


}




© 2015 - 2025 Weber Informatics LLC | Privacy Policy