/* FichothequeLib_Tools - Copyright (c) 2010-2022 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 net.fichotheque.tools.extraction.builders;

import net.fichotheque.extraction.ExtractionConstants;
import net.fichotheque.extraction.def.GroupClause;
import net.fichotheque.extraction.def.GroupParams;
import net.fichotheque.extraction.def.TagNameInfo;
import net.fichotheque.utils.ExtractionUtils;


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

    private final String groupType;
    private String sortOrder = ExtractionConstants.ASCENDING_SORT;
    private TagNameInfo tagNameInfo = TagNameInfo.DEFAULT;
    private GroupParams groupParams = null;
    private GroupClause subGroupClause = null;

    public GroupClauseBuilder(String groupType) {
        this.groupType = groupType;
    }

    public GroupClauseBuilder setTagNameInfo(TagNameInfo tagNameInfo) {
        this.tagNameInfo = tagNameInfo;
        return this;
    }

    public GroupClauseBuilder setSortOrder(String sortOrder) {
        this.sortOrder = ExtractionUtils.checkSort(sortOrder);
        return this;
    }

    public GroupClauseBuilder setGroupParams(GroupParams groupParams) {
        this.groupParams = groupParams;
        return this;
    }

    public GroupClauseBuilder setSubGroupClause(GroupClause groupClause) {
        this.subGroupClause = groupClause;
        return this;
    }

    public GroupClause toGroupClause() {
        switch (groupType) {
            case ExtractionConstants.FIELDS_TYPE:
                if (groupParams == null) {
                    throw new IllegalStateException("groupParams is null");
                }
        }
        return new InternalGroupClause(groupType, sortOrder, tagNameInfo, groupParams, subGroupClause);
    }

    public static GroupClauseBuilder init(String groupType) {
        return new GroupClauseBuilder(groupType);
    }

    public static GroupClause getGroupClause(String groupClauseString, boolean hidden) {
        int idx = groupClauseString.indexOf('-');
        if (idx == -1) {
            return null;
        }
        String type;
        try {
            type = ExtractionUtils.checkType(groupClauseString.substring(0, idx));
        } catch (IllegalArgumentException iae) {
            return null;
        }
        String sortOrder = ExtractionUtils.checkSort(groupClauseString.substring(idx + 1));
        switch (type) {
            case ExtractionConstants.WEIGHT_TYPE:
            case ExtractionConstants.TITLE_TYPE:
            case ExtractionConstants.YEAR_TYPE:
            case ExtractionConstants.LANG_TYPE:
            case ExtractionConstants.POSITION_TYPE:
                break;
            default:
                return null;
        }
        TagNameInfo tagNameInfo = (hidden) ? TagNameInfo.NULL : TagNameInfo.DEFAULT;
        return new InternalGroupClause(type, sortOrder, tagNameInfo, null, null);
    }


    private static class InternalGroupClause implements GroupClause {

        private final String groupType;
        private final String sortOrder;
        private final TagNameInfo tagNameInfo;
        private final GroupParams groupParams;
        private final GroupClause subGroupClause;

        private InternalGroupClause(String groupType, String sortOrder, TagNameInfo tagNameInfo, GroupParams groupParams, GroupClause subGroupClause) {
            this.groupType = groupType;
            this.sortOrder = sortOrder;
            this.tagNameInfo = tagNameInfo;
            this.groupParams = groupParams;
            this.subGroupClause = subGroupClause;
        }

        @Override
        public String getGroupType() {
            return groupType;
        }

        @Override
        public String getSortOrder() {
            return sortOrder;
        }

        @Override
        public TagNameInfo getTagNameInfo() {
            return tagNameInfo;
        }

        @Override
        public GroupParams getGroupParams() {
            return groupParams;
        }

        @Override
        public GroupClause getSubGroupClause() {
            return subGroupClause;
        }

    }

}
