/*
 * Copyright 2018 Scytl Secure Electronic Voting SA
 *
 * All rights reserved
 *
 * See our extended copyright notice in *file 'Copyright.txt' which is part of this source code package
 */
package com.scytl.products.ov.config.webapp.mvc.commands.ballotbox;

import java.nio.file.Path;
import java.nio.file.Paths;
import java.time.Instant;
import java.time.ZoneOffset;
import java.time.ZonedDateTime;
import java.util.Properties;

import com.scytl.products.ov.config.commands.ballotbox.BallotBoxParametersHolder;
import com.scytl.products.ov.config.commands.electionevent.datapacks.beans.ElectionInputDataPack;
import com.scytl.products.ov.config.webapp.mvc.dto.input.CreateBallotBoxesInput;
import com.scytl.products.ov.constants.Constants;

public class BallotBoxWebappAdapter {

    public BallotBoxParametersHolder adapt(final CreateBallotBoxesInput input) {
        final BallotBoxParametersHolder holder;

        final String ballotID = input.getBallotID();

        final String electoralAuthorityId = input.getElectoralAuthorityID();

        final String ballotBoxID = input.getBallotBoxID();

        final String alias = input.getAlias();

        final String isTest = input.getTest();

        final String gracePeriod = input.getGracePeriod();

        final String confirmationRequired = input.getConfirmationRequired();

        final String outputFolder = input.getOutputFolder();

        validateOutPutFolder(outputFolder);

        final Path absolutePath = Paths.get(outputFolder).toAbsolutePath();

        final String eeID = absolutePath.getFileName().toString();

        final ElectionInputDataPack electionInputDataPack = new ElectionInputDataPack();

        electionInputDataPack.setEeid(eeID);

        final Integer validityPeriod = input.getValidityPeriod();

        final ZonedDateTime startValidityPeriod = ZonedDateTime.now(ZoneOffset.UTC);

        final ZonedDateTime electionStartDate =
            ZonedDateTime.ofInstant(Instant.parse(input.getStart()), ZoneOffset.UTC);
        final ZonedDateTime electionEndDate = ZonedDateTime.ofInstant(Instant.parse(input.getEnd()), ZoneOffset.UTC);

        final ZonedDateTime endValidityPeriod = electionEndDate.plusYears(validityPeriod);

        if (electionEndDate.isAfter(endValidityPeriod)) {
            throw new IllegalArgumentException("End date cannot be after Start date plus validity period.");
        }

        electionInputDataPack.setStartDate(startValidityPeriod);
        electionInputDataPack.setEndDate(endValidityPeriod);
        electionInputDataPack.setElectionStartDate(electionStartDate);
        electionInputDataPack.setElectionEndDate(electionEndDate);

        final String writeInAlphabet = input.getWriteInAlphabet();
        final Properties certificateProperties = input.getBallotBoxCertificateProperties();

        holder = new BallotBoxParametersHolder(ballotID, electoralAuthorityId, ballotBoxID, alias, absolutePath, eeID,
            electionInputDataPack, isTest, gracePeriod, confirmationRequired, writeInAlphabet, certificateProperties);
        holder.setKeyForProtectingKeystorePassword(input.getKeyForProtectingKeystorePassword());

        return holder;
    }

    private void validateOutPutFolder(final String outputFolder) {

        final Path outputPath = Paths.get(outputFolder).toAbsolutePath();

        final String prefixErrorMessage = "The given output path: \"" + outputPath.toString();

        if (!outputPath.toFile().exists()) {
            throw new IllegalArgumentException(prefixErrorMessage + "\" does not exist.");
        }

        final String electionEventID = outputPath.getFileName().toString();

        if (!electionEventID.matches(Constants.HEX_ALPHABET)) {

            throw new IllegalArgumentException(prefixErrorMessage
                + "\" requires an election event id in UUID format (e.g. 17ccbe962cf341bc93208c26e911090c).");
        }

    }

}
