package com.capgemini.reports.periodicity;

import com.capgemini.framework.common.SettingsHelper;
import com.capgemini.framework.common.TeamcenterDateFormatter;
import com.capgemini.reports.database.javabean.enumeration.SchedulingEnum;
import com.capgemini.reports.database.manager.MngSchedulingCriteriaVal.SchedulingCriteriaValue;
import lombok.Getter;

import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;

/**
 * Represents a specific day for execution. Occurs only once.
 */
@Getter
public class SpecificDay implements SchedulingPeriod {

    private static final String LAUNCH_HOUR_STR = SettingsHelper.getDelayedLaunchHour();

    private final Date day;

    /**
     * Build a specific day.
     * 
     * @param day the day using format: "dd-MM-yyyy"
     * @throws ParseException if unable to parse the input date.
     */
    public SpecificDay(final String day) throws ParseException {
        this.day = getScheduledDate(day);
    }

    /**
     * Build a specific day.
     * 
     * @param day the {@link Date}
     * @throws ParseException
     */
    protected SpecificDay(final Date day) {
        this.day = day;
    }

    @Override
    public SchedulingEnum getPeriodicity() {
        return SchedulingEnum.DATE;
    }

    @Override
    public <T> T accept(final PeriodVisitor<T> visitor) {
        return visitor.visit(this);
    }

    @Override
    public List<SchedulingCriteriaValue> asCriteriaValues() {
        List<SchedulingCriteriaValue> list = new ArrayList<>(2);
        list.add(new SchedulingCriteriaValue(SchedulingEnum.PERIOD, SchedulingEnum.DATE.getCriteriaName()));
        list.add(new SchedulingCriteriaValue(SchedulingEnum.DATE, String.valueOf(dateToString())));
        return list;
    }

    /**
     * Get the scheduled date.
     * 
     * @param stringValue String - the date value to the TC format dd-MM-yyyy
     * 
     * @throws ParseException if the parse of the {@link SimpleDateFormat} doesn't work.
     * 
     * @return a {@link Date} pointing to the provided day, at the default hour & minute
     */
    private Date getScheduledDate(final String stringValue) throws ParseException {
        // Create a date with the appropriate value
        SimpleDateFormat curFormater = new SimpleDateFormat(TeamcenterDateFormatter.DD_MM_YYYY_HH_MM);
        return curFormater.parse(stringValue + " " + LAUNCH_HOUR_STR);
    }

    private String dateToString() {
        return new SimpleDateFormat(TeamcenterDateFormatter.DD_MM_YYYY).format(day);
    }

}
