
package de.ivu.elect.dokumente.wahlvorschlag;

import static de.ivu.elect.business.dokumente.entity.DokumentKonverterResult.openOfficeFromList;

import java.util.ArrayList;
import java.util.List;

import javax.inject.Inject;

import de.ivu.elect.business.dokumente.control.DokumentExtraFileOutput;
import de.ivu.elect.business.dokumente.control.ProgressMonitor;
import de.ivu.elect.business.dokumente.entity.DokumentGenerierenProgress;
import de.ivu.elect.business.dokumente.entity.DokumentKonverterResult;
import de.ivu.elect.business.gebietsbaum.boundary.GebietDAO;
import de.ivu.elect.business.gebietsbaum.entity.Gebiet;
import de.ivu.elect.business.stimmzettel.boundary.EntityAufStimmzettelDatenDAOFactory;
import de.ivu.elect.business.wahlausschuss.boundary.WahlausschussmitgliedDAO;
import de.ivu.elect.business.wahlvorschlag.boundary.WahlvorschlaegeDokumentContext;
import de.ivu.elect.business.wahlvorschlag.boundary.WahlvorschlagDAO;
import de.ivu.elect.business.wahlvorschlag.control.WahlvorschlaegeDokumentGeneratorWahlrechtspruefungenFinder;
import de.ivu.elect.business.wahlvorschlagsperson.boundary.WahlvorschlagsPersonDAO;
import de.ivu.elect.dokumente.CoreElectContext;
import de.ivu.elect.dokumente.CoreElectContextBuilder;
import de.ivu.elect.dokumente.ElectDocument;
import de.ivu.elect.dokumente.kandidatur.KandidaturCoreDaten;
import de.ivu.elect.dokumente.konverter.AbstractDokumentKonverter;
import de.ivu.elect.jee.entity.Entity;

public abstract class AbstractWahlvorschlaegeDokumentKonverter<E extends Entity< ? , ? >, C extends WahlvorschlaegeDokumentContext> extends AbstractDokumentKonverter<C> {

  @Inject
  private transient GebietDAO gebietDAO;

  @Inject
  private transient WahlvorschlagDAO wahlvorschlagDAO;

  @Inject
  private transient WahlvorschlagsPersonDAO wahlvorschlagsPersonDAO;

  @Inject
  private transient WahlausschussmitgliedDAO wahlausschussmitgliedDAO;

  @Inject
  private transient CoreElectContextBuilder coreElectContextBuilder;

  @Inject
  private transient EntityAufStimmzettelDatenDAOFactory entityAufStimmzettelDatenDAOFactory;

  @Inject
  private transient WahlvorschlaegeDokumentGeneratorWahlrechtspruefungenFinder wahlvorschlaegeDokumentGeneratorWahlrechtspruefungenFinder;

  protected AbstractWahlvorschlaegeDokumentKonverter() {
    super();
  }

  public DokumentKonverterResult konvertiereInDokumentEingabe(List<List<E>> groupsOfEntities, C context, DokumentExtraFileOutput dokumentExtraFileOutput, ProgressMonitor monitor) {
    List<Object> result = new ArrayList<>(groupsOfEntities.size());

    CoreElectContext coreElectContext = coreElectContextBuilder.create(createBaseElectContext(context, dokumentExtraFileOutput));

    KandidaturCoreDaten kandidaturCoreDaten = new KandidaturCoreDaten(coreElectContext, entityAufStimmzettelDatenDAOFactory.getEntityAufStimmzettelDaten(), context.getKandidaturFormatDarstellung());

    WahlvorschlagCoreDaten wahlvorschlagCoreDaten = new WahlvorschlagCoreDaten(attach(context.getWahl()), wahlvorschlagDAO, kandidaturCoreDaten, wahlvorschlagsPersonDAO, wahlausschussmitgliedDAO,
        wahlvorschlaegeDokumentGeneratorWahlrechtspruefungenFinder, context);

    Gebiet auswertungsgebiet = gebietDAO.attach(context.getGebiet());

    int count = 0;
    int size = groupsOfEntities.size();

    for (List<E> entities : groupsOfEntities) {
      if (monitor.isCanceled()) {
        return openOfficeFromList(result);
      }

      count++;

      result.add(createDokumentEingabe(coreElectContext, auswertungsgebiet, wahlvorschlagCoreDaten, entities));

      monitor.progress(DokumentGenerierenProgress.MAPPE_ENTITY, count, size);
    }

    return openOfficeFromList(result);
  }

  protected abstract ElectDocument createDokumentEingabe(CoreElectContext coreElectContext, Gebiet auswertungsgebiet, WahlvorschlagCoreDaten wahlvorschlagCoreDaten, List<E> entities);
}
