package ru.yandex.wmtools.common.data.xmlsearch;

import org.jdom.Document;
import org.jdom.Element;

import ru.yandex.wmtools.common.error.InternalException;
import ru.yandex.wmtools.common.service.OwnerDomainService;

/**
 * Created by IntelliJ IDEA.
 * User: senin
 * Date: 01.12.2007
 * Time: 15:06:36
 */
public abstract class AbstractRequest implements XmlSearchRequest {
    protected static final String GROUP_BY_ATTR_D = "d";
    protected static final String GROUP_BY_ATTR_EMPTY = "";
    protected static final String GROUP_BY_MODE_DEEP = "deep";
    public static final String GROUP_BY_MODE_FLAT = "flat";

    protected static final String LONG_REQUEST_PARAM = "long-request=1";
    protected static final String RD0_RDBA0_PARAMS = "rd=0&rdba=0";
    protected static final String LONGREQUEST1_PARAMS = "long-request=1";
    protected static final String EMPTY_PARAMS = "";
    protected static final String DBGWZR_PARAMS = "dbgwzr=1"; // debug wizard
    protected static final String PRON_PARAMS = "pron=noprune";
    protected static final String COMMON_PARAMS = "notests=1&srcskip=PPS";
    protected static final String DOSEARCHLINKS_YES_PARAMS = "dosearchlinks=yes"; // internal attribute - whether we need external links or not
    protected static final String RELEV_PARAMS="relev=attr_limit%3D10000000";
    protected static final String NO_CACHE_PARAM = "nocache=da";

    // Результаты только от быстрого робота
    protected static final String FAST_ROBOT_PARAM = "sss=QUICK";

    // Отключает переранжирования, включающие разгруппировку при небольшом числе результатов
    // при использовании запросов с группировкой
    protected static final String REARRANGE_OFF_PARAMS = "rearr=no2docs&rearr=UngroupVital_off&rearr=UngroupSmall_off";

    private Document request;

    @Override
    public Document getDocument() throws InternalException {
        if (request == null) {
            request = createRequest();
        }
        return request;
    }

    private Document createRequest() throws InternalException {
        Element requestElement = new Element("request");
        Document document = new Document(requestElement);

        Element queryElement = new Element("query");
        queryElement.setText(getQueryText());
        document.getRootElement().addContent(queryElement);

        Element pageElement = new Element("page");
        pageElement.setText(Integer.toString(getPageNum()));
        document.getRootElement().addContent(pageElement);

        Element groupingsElement = new Element("groupings");
        document.getRootElement().addContent(groupingsElement);

        Element groupByElement = new Element("groupby");
        groupByElement.setAttribute("attr", getGroupByAttr());
        groupByElement.setAttribute("mode", getGroupByMode());
        groupByElement.setAttribute("groups-on-page", Integer.toString(getPageSize()));
        groupByElement.setAttribute("docs-in-group", "1");
        groupingsElement.addContent(groupByElement);

        return document;
    }

    protected abstract String getQueryText() throws InternalException;

    protected abstract String getGroupByAttr();

    protected abstract String getGroupByMode();

    protected abstract int getPageNum();

    protected abstract int getPageSize();

    @Override
    public long getQueryHashCode() throws InternalException {
        return getQueryHashCode(getQueryText(), getUrlParams());
    }

    public static long getQueryHashCode(String query, String params) {
        long hash = 7;
        hash += 31 * (query == null ? 0 : query.hashCode());
        hash += 31 * (params == null ? 0 : params.hashCode());
        return hash;
    }

    protected String getOwnerReversed(String hostname) throws InternalException {
        return OwnerDomainService.getOwnerDomainRPattern(hostname);
    }

    protected String getOwnerDomain(String hostname) throws InternalException {
        return OwnerDomainService.getOwnerDomain(hostname);
    }
}

