package Common.Utils;
import java.util.concurrent.Semaphore;
import java.util.concurrent.TimeUnit;
public abstract class TimerTask {
    int maxtime;
    int attempts;
    boolean success;
    Semaphore semaphore = null;
    Thread actionThread = null;
    //--
    public TimerTask(int maxtime_in, int attempts_in) {
        maxtime = maxtime_in;
        attempts = attempts_in;
        semaphore = new Semaphore(1);
        actionThread = new Thread(new Runnable() {
            @Override
            public void run() {
                try {
                    Action();
                } catch (Exception ex) {
                    System.out.println("Thread occured exception!");
                    ex.printStackTrace();
                    System.out.println("-------------------------");
                } finally {
                    releaseSemaphore();
                }
            }
        });
    }
    //--
    public abstract void Action() throws Exception;
    public void finalizeThread() {
    }
    void acquireSemaphore() {
        try {
            semaphore.acquire();
            System.out.println("semaphore acquired");
        } catch (Exception ignore) {
        }
    }
    void releaseSemaphore() {
        semaphore.release();
        System.out.println("semaphore released");
    }
    void waitForThread() {
        int i = 0;
        success = false;
        while (true) {
            try {
                ++i;
                if (semaphore.tryAcquire(1, TimeUnit.SECONDS)) {
                    System.out.println("thread finished for " + i + " seconds");
                    success = true;
                    return;
                } else {
                    System.out.println("thread active " + i + " seconds");
                    if (i >= maxtime) {
                        System.out.println("maxtime reached: " + i + " seconds");
                        return;
                    }
                }
            } catch (Exception ex) {
                System.out.println("waiting exception");
                ex.printStackTrace();
                return;
            }
        }
    }
    public boolean Perform(int attempts) {
        int i = 0;
        while (i < attempts) {
            acquireSemaphore();
            actionThread.start();
            waitForThread();
            finalizeThread();
            ++i;
            System.out.println("task finished for " + i + " attempts");
            if (success) {
                return true;
            }
        }
        System.out.println("attempts overlimited");
        return false;
    }
}
