/* BdfServer_HtmlProducers - Copyright (c) 2012-2024 Vincent Calame - Exemole
 * Logiciel libre donné sous triple licence :
 * 1) selon les termes de la CeCILL V2
 * 2) selon les termes de l’EUPL V.1.1
 * 3) selon les termes de la GNU GPLv3
 * Voir le fichier licences.txt
 */


package fr.exemole.bdfserver.htmlproducers.thesaurus;

import fr.exemole.bdfserver.api.BdfServerEditor;
import fr.exemole.bdfserver.api.interaction.domains.ThesaurusDomain;
import fr.exemole.bdfserver.api.namespaces.BdfUserSpace;
import fr.exemole.bdfserver.api.users.BdfUser;
import fr.exemole.bdfserver.api.users.BdfUserPrefsEditor;
import java.text.ParseException;
import java.util.ArrayList;
import java.util.List;
import net.fichotheque.SubsetKey;
import net.fichotheque.thesaurus.Thesaurus;
import net.mapeadores.util.annotation.Nullable;
import net.mapeadores.util.attr.Attribute;
import net.mapeadores.util.attr.AttributeBuilder;
import net.mapeadores.util.attr.AttributeKey;
import net.mapeadores.util.localisation.Lang;
import net.mapeadores.util.request.RequestMap;
import net.mapeadores.util.text.CleanedString;


/**
 *
 * @author Vincent Calame
 */
public class ThesaurusParameters {

    private Lang labelLang;
    private String labelFilter;
    private SubsetKey satelliteCorpusKey;
    private String satelliteFilter;

    @Nullable
    public Lang getLabelLang() {
        return labelLang;
    }

    @Nullable
    public String getLabelFilter() {
        return labelFilter;
    }

    @Nullable
    public SubsetKey getSatelliteCorpusKey() {
        return satelliteCorpusKey;
    }

    @Nullable
    public String getSatelliteFilter() {
        return satelliteFilter;
    }

    public boolean isEmpty() {
        if (labelLang != null) {
            return false;
        }
        if (labelFilter != null) {
            return false;
        }
        return true;
    }

    private boolean populate(String paramName, String paramValue) {
        if (paramValue.isEmpty()) {
            switch (paramName) {
                case ThesaurusDomain.LABELLANG_PARAMNAME:
                case ThesaurusDomain.LABELFILTER_PARAMNAME:
                case ThesaurusDomain.SATELLITECORPUS_PARAMNAME:
                case ThesaurusDomain.SATELLITEFILTER_PARAMNAME:
                    return true;
                default:
                    return false;
            }
        }
        switch (paramName) {
            case ThesaurusDomain.LABELLANG_PARAMNAME:
                try {
                this.labelLang = Lang.parse(paramValue);
                return true;
            } catch (ParseException pe) {
                return false;
            }
            case ThesaurusDomain.LABELFILTER_PARAMNAME:
                this.labelFilter = paramValue;
                return true;
            case ThesaurusDomain.SATELLITECORPUS_PARAMNAME:
                try {
                this.satelliteCorpusKey = SubsetKey.parse(SubsetKey.CATEGORY_CORPUS, paramValue);
                return true;
            } catch (ParseException pe) {
                return false;
            }
            case ThesaurusDomain.SATELLITEFILTER_PARAMNAME:
                this.satelliteFilter = paramValue;
                return true;
            default:
                return false;
        }
    }


    public void save(BdfServerEditor bdfServerEditor, BdfUser bdfUser, Thesaurus thesaurus) {
        BdfUserPrefsEditor bdfUserPrefsEditor = bdfServerEditor.getBdfUserPrefsEditor(bdfUser.getPrefs());
        AttributeKey attributeKey = BdfUserSpace.toFilterParametersKey(thesaurus);
        List<CleanedString> valueList = getAttributeValueList();
        if (valueList.isEmpty()) {
            bdfUserPrefsEditor.removeAttribute(attributeKey);
        } else {
            AttributeBuilder attributeBuilder = new AttributeBuilder(attributeKey);
            for (CleanedString value : valueList) {
                attributeBuilder.addValue(value);
            }
            bdfUserPrefsEditor.putAttribute(attributeBuilder.toAttribute());
        }
    }

    private List<CleanedString> getAttributeValueList() {
        List<CleanedString> result = new ArrayList<CleanedString>();
        if (labelLang != null) {
            result.add(CleanedString.newInstance(ThesaurusDomain.LABELLANG_PARAMNAME + "=" + labelLang.toString()));
        }
        if (labelFilter != null) {
            result.add(CleanedString.newInstance(ThesaurusDomain.LABELFILTER_PARAMNAME + "=" + labelFilter));
        }
        if (satelliteCorpusKey != null) {
            result.add(CleanedString.newInstance(ThesaurusDomain.SATELLITECORPUS_PARAMNAME + "=" + satelliteCorpusKey.getSubsetName()));
        }
        if (satelliteFilter != null) {
            result.add(CleanedString.newInstance(ThesaurusDomain.SATELLITEFILTER_PARAMNAME + "=" + satelliteFilter));
        }
        return result;
    }

    public static ThesaurusParameters buildFromThesaurus(BdfUser bdfUser, Thesaurus thesaurus) {
        ThesaurusParameters parameters = new ThesaurusParameters();
        AttributeKey attributeKey = BdfUserSpace.toFilterParametersKey(thesaurus);
        Attribute attribute = bdfUser.getPrefs().getAttributes().getAttribute(attributeKey);
        if (attribute == null) {
            return parameters;
        }
        for (String value : attribute) {
            int idx = value.indexOf('=');
            if (idx > 0) {
                String paramName = value.substring(0, idx).trim();
                String paramValue = value.substring(idx + 1).trim();
                if (paramName.length() > 0) {
                    parameters.populate(paramName, paramValue);
                }
            }
        }
        return parameters;
    }

    @Nullable
    public static ThesaurusParameters buildFromRequest(RequestMap requestMap) {
        ThesaurusParameters parameters = new ThesaurusParameters();
        boolean done = false;
        for (String paramName : requestMap.getParameterNameSet()) {
            boolean result = parameters.populate(paramName, requestMap.getParameter(paramName));
            if (result) {
                done = true;
            }
        }
        if (done) {
            return parameters;
        } else {
            return null;
        }
    }

}
