package de.duehl.basics.io.lock;

/*
 * Copyright 2017 Christian Dühl. All rights reserved.
 *
 * This program is free software. You can redistribute it and/or
 * modify it under the same terms as perl:
 *
 * general:  http://dev.perl.org/licenses/
 * GPL:      http://dev.perl.org/licenses/gpl1.html
 * artistic: http://dev.perl.org/licenses/artistic.html
 */

import java.io.File;

import de.duehl.basics.io.FileHelper;

/**
 * Diese Klasse kümmert sich um eine Lockdatei, welche verhindert, dass mehrere Programmaufrufe zur
 * gleichen Zeit stattfinden.
 *
 * @version 1.01     2017-03-27
 * @author Christian Dühl
 */

public class MultipleStartLock extends LockBase {

    /**
     * Konstruktor.
     *
     * @param filename
     *            Name der Sperrdatei, die einen mehrfachen Start verhindert.
     */
    public MultipleStartLock(String filename) {
        super(filename);
    }

    /**
     * Erstellt die Lockdatei.
     *
     * @return Gibt an, ob der Lock erhalten wurde: Der Wert false bedeutet, die Lockdatei ist
     *         bereits vorhanden, also läuft ein anderer Prozess. Falls es die Lockdatei noch nicht
     *         gab und diese angelegt werden konnte, wird true zurückgeliefert. Gab es den Lock
     *         nicht, aber konnte er auch nicht angelegt werden, so wird eine Ausnahme geworfen.
     * @throws IORuntimeException
     *             Wenn die Datei nicht vorhanden ist und trotzdem nicht angelegt werden konnte.
     */
    @Override
    public boolean lock() {
        if (FileHelper.exists(filename)) {
            return false;
        }
        else {
            FileHelper.createEmptyFile(filename);
            return true;
        }

        /*
         * Dieses Vorgehen verhindert leider keine Race-Conditions.
         *
         * https://stackoverflow.com/questions/60016052/prevent-race-condition-with-files
         */
    }

    /** Entfernt die Lockdatei. */
    @Override
    public boolean unlock() {
        File lockFile = new File(filename);
        if (lockFile.exists()) {
            lockFile.delete();
            return true;
        }
        else {
            return false;
        }
    }

}
