package ru.micord.ervu.account_applications.service.processor.impl;

import java.sql.Timestamp;
import java.time.Instant;
import java.util.Set;
import java.util.stream.Collectors;

import org.springframework.stereotype.Component;
import org.springframework.util.CollectionUtils;
import ru.micord.ervu.account_applications.dao.SolutionDao;
import ru.micord.ervu.account_applications.db_beans.public_.tables.records.SolutionRecord;
import ru.micord.ervu.account_applications.model.ReferenceEntity;
import ru.micord.ervu.account_applications.model.SolutionData;
import ru.micord.ervu.account_applications.service.processor.DataProcessor;

/**
 * @author Adel Kalimullin
 */
@Component
public class SolutionProcessor implements DataProcessor<SolutionData, SolutionRecord> {
  private final SolutionDao dao;
  private final SolutionRoleProcessor solutionRoleProcessor;

  public SolutionProcessor(SolutionDao solutionDao, SolutionRoleProcessor solutionRoleProcessor) {
    this.dao = solutionDao;
    this.solutionRoleProcessor = solutionRoleProcessor;
  }

  @Override
  public void upsertData(SolutionData data) {
    SolutionRecord solutionRecord = mapToRecord(data);
    if (!CollectionUtils.isEmpty(data.getRoles())) {
      Set<String> rolesIds = data.getRoles().stream()
          .map(ReferenceEntity::getId)
          .collect(Collectors.toSet());
      solutionRoleProcessor.upsertSolutionRoles(data.getId(), rolesIds);
    }

    dao.upsertData(solutionRecord);
  }

  @Override
  public void changeActiveStatus(String id, boolean active) {
    dao.setActiveStatus(id, active);
  }

  @Override
  public Class<SolutionData> getType() {
    return SolutionData.class;
  }

  @Override
  public SolutionRecord mapToRecord(SolutionData data) {
    Timestamp updatedAt = Timestamp.from(Instant.ofEpochMilli(data.getModified()));
    Timestamp createdAt = Timestamp.from(Instant.ofEpochMilli(data.getCreated()));
    Timestamp deletedAt = Timestamp.from(Instant.ofEpochMilli(data.getDeleted()));
    SolutionRecord record = dao.newRecord();
    record.setId(data.getId());
    record.setDisplayName(data.getDisplayName());
    record.setActive(data.getActive());
    record.setDescription(data.getDescription());
    record.setName(data.getName());
    record.setCreated(createdAt);
    record.setDeleted(deletedAt);
    record.setModified(updatedAt);
    record.setVersion(data.getVersion());
    return record;
  }
}
