package ru.yandex.webmaster3.storage.delurl.dao;

import org.apache.commons.lang3.tuple.Pair;
import org.joda.time.DateTime;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import ru.yandex.webmaster3.core.data.WebmasterHostId;
import ru.yandex.webmaster3.core.delurl.DelUrlRequest;
import ru.yandex.webmaster3.storage.util.ydb.AbstractYDao;
import ru.yandex.webmaster3.storage.util.ydb.querybuilder.typesafe.DataMapper;
import ru.yandex.webmaster3.storage.util.ydb.querybuilder.typesafe.Field;
import ru.yandex.webmaster3.storage.util.ydb.querybuilder.typesafe.Fields;

import java.util.UUID;
import java.util.function.Consumer;

/**
 * @author leonidrom
 *
 * У таблицы TTL 3 дня
 */
@Service
public class DelUrlQueueYDao extends AbstractYDao  {
    private static final String TABLE_NAME = "delurl_queue";
    private static final String ADD_DATE_INDEX = "add_date_index";

    @Autowired
    public DelUrlQueueYDao() {
        super("/webmaster3/delurl", TABLE_NAME);
    }

    public void insert(DelUrlRequest request) {
        var st = upsert(
                F.REQUEST_ID.value(request.getRequestId()),
                F.HOST_ID.value(request.getHostId()),
                F.ADD_DATE.value(request.getAddDate())
        );

        execute(st);
    }

    public void delete(WebmasterHostId hostId, UUID requestId) {
        var st = delete().where(F.HOST_ID.eq(hostId)).and(F.REQUEST_ID.eq(requestId)).getStatement();
        execute(st);
    }

    public void forEach(Consumer<Pair<WebmasterHostId, UUID>> consumer) {
        streamReader(MAPPER, consumer);
    }

    public int count() {
        var st = select().countAll();
        return queryOne(st, DataMapper.SINGLE_COLUMN_INT_MAPPER);
    }

    public long maxAge() {
        var st = select(ADD_DATE_MAPPER).secondaryIndex(ADD_DATE_INDEX).order(F.ADD_DATE.asc()).limit(1);
        DateTime minAddDate = queryOne(st, ADD_DATE_MAPPER);
        return (minAddDate == null ? 0 : System.currentTimeMillis() - minAddDate.getMillis());
    }

    private interface F {
        Field<UUID> REQUEST_ID = Fields.uuidField("request_id");
        Field<WebmasterHostId> HOST_ID = Fields.hostIdField("host_id");
        Field<DateTime> ADD_DATE = Fields.jodaDateTimeField("add_date");
    }

    private final DataMapper<Pair<WebmasterHostId, UUID>> MAPPER = DataMapper.create(F.HOST_ID, F.REQUEST_ID, Pair::of);
    private final DataMapper<DateTime> ADD_DATE_MAPPER = DataMapper.create(F.ADD_DATE, r -> r);
}
