package br.gov.servicos.legado;

import br.gov.servicos.busca.Busca;
import br.gov.servicos.servico.Servico;
import br.gov.servicos.servico.ServicoRepository;
import lombok.experimental.FieldDefaults;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.core.io.ClassPathResource;
import org.springframework.data.elasticsearch.core.ElasticsearchTemplate;
import org.springframework.jmx.export.annotation.ManagedOperation;
import org.springframework.jmx.export.annotation.ManagedResource;
import org.springframework.stereotype.Component;

import javax.xml.bind.JAXBContext;
import javax.xml.bind.JAXBElement;
import javax.xml.bind.JAXBException;
import javax.xml.bind.Unmarshaller;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.URL;
import java.util.UUID;
import java.util.stream.Stream;

import static java.util.stream.Collectors.joining;
import static java.util.stream.Collectors.toList;
import static lombok.AccessLevel.PRIVATE;

@Component
@FieldDefaults(level = PRIVATE, makeFinal = true)
@ManagedResource(
        objectName = "ServicosGovBr:type=Importador",
        description = "Importa XML do Guia legado para o ElasticSearch"
)
public class Importador {

    private static final String INDEX_NAME = "guia-de-servicos";
    private static final String XML_LEGADO = "guiadeservicos.xml";
    private static final String SETTINGS = "/elasticsearch/settings.json";

    ElasticsearchTemplate es;
    ServicoRepository servicos;

    @Autowired
    Importador(ElasticsearchTemplate es, ServicoRepository servicos) {
        this.es = es;
        this.servicos = servicos;
    }

    @ManagedOperation
    public Iterable<Servico> importar() throws IOException, JAXBException {
        recriarIndice();

        servicos.save(
                servicosLegados()
                        .map(Importador::servicoLegadoToServico)
                        .collect(toList()));

        return servicos.findAll();
    }

    private void recriarIndice() throws IOException {
        if (es.indexExists(INDEX_NAME)) {
            es.deleteIndex(INDEX_NAME);
        }

        es.createIndex(INDEX_NAME, readSettings());
        es.putMapping(Busca.class);
        es.putMapping(Servico.class);
    }

    private static String readSettings() throws IOException {
        ClassPathResource resource = new ClassPathResource(SETTINGS);
        InputStreamReader reader = new InputStreamReader(resource.getInputStream());

        try (BufferedReader br = new BufferedReader(reader)) {
            return br.lines().collect(joining("\n"));
        }
    }

    private static Stream<ServicoType> servicosLegados() throws IOException, JAXBException {
        return unmarshallDadosLegados()
                .getServicos()
                .getServico()
                .stream();
    }

    private static DadosType unmarshallDadosLegados() throws IOException, JAXBException {
        URL xmlLegado = new ClassPathResource(XML_LEGADO).getURL();
        JAXBElement element = (JAXBElement) unmarshaller().unmarshal(xmlLegado);

        return (DadosType) element.getValue();
    }

    private static Unmarshaller unmarshaller() throws JAXBException {
        JAXBContext contexto = JAXBContext.newInstance("br.gov.servicos.legado");
        return contexto.createUnmarshaller();
    }

    private static Servico servicoLegadoToServico(ServicoType legado) {
        return new Servico(
                UUID.randomUUID().toString(),
                legado.getTitulo(),
                legado.getDescricao(),
                legado.getUrl(),
                legado.getTaxa(),
                legado.getOrgaoPrestador2(),
                legado.getOrgaoResponsavel2(),
                legado.getAreasDeInteresse(),
                legado.getLinhasDaVida(),
                legado.getEventosDasLinhasDaVida(),
                0L,
                0L
        );
    }
}

@@ -152,16 +152,51 @@
 sitory;%0A
+import com.github.slugify.Slugify;%0A
 import l
@@ -864,31 +864,8 @@
 RL;%0A
-import java.util.UUID;%0A
 impo
@@ -1540,16 +1540,37 @@
 ervicos;
+%0A    Slugify slugify;
 %0A%0A    @A
@@ -1645,16 +1645,33 @@
 servicos
+, Slugify slugify
 ) %7B%0A    
@@ -1718,24 +1718,56 @@
 = servicos;%0A
+        this.slugify = slugify;%0A
     %7D%0A%0A    @
@@ -1971,26 +1971,20 @@
    .map(
-Importador
+this
 ::servic
@@ -3460,23 +3460,16 @@
 private 
-static 
 Servico 
@@ -3561,35 +3561,42 @@
     
-UUID.randomUUID().toString(
+slugify.slugify(legado.getTitulo()
 ),%0A 

Usa slugify(titulo) como id