package ru.yandex.webmaster3.viewer.http.feeds;

import java.util.List;

import lombok.RequiredArgsConstructor;
import lombok.Setter;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import org.springframework.util.CollectionUtils;

import ru.yandex.autodoc.common.doc.annotation.Description;
import ru.yandex.webmaster3.core.WebmasterException;
import ru.yandex.webmaster3.core.data.WebmasterHostId;
import ru.yandex.webmaster3.core.feeds.feed.NativeFeedInfo2;
import ru.yandex.webmaster3.core.feeds.mbi.DatacampPartnerProperties;
import ru.yandex.webmaster3.core.feeds.mbi.MbiService;
import ru.yandex.webmaster3.core.feeds.mbi.UpdateFeedFeaturesRequest;
import ru.yandex.webmaster3.core.http.Action;
import ru.yandex.webmaster3.core.http.ActionResponse;
import ru.yandex.webmaster3.core.http.RequestQueryProperty;
import ru.yandex.webmaster3.core.http.WriteAction;
import ru.yandex.webmaster3.core.metrics.Category;
import ru.yandex.webmaster3.core.util.WwwUtil;
import ru.yandex.webmaster3.storage.feeds.FeedsNative2YDao;
import ru.yandex.webmaster3.storage.feeds.FeedsService;
import ru.yandex.webmaster3.viewer.http.AbstractUserVerifiedHostRequest;


/**
 * @author kravchenko99
 * @date 7/30/21
 */

@Component("/feeds/changeFeed")
@WriteAction
@RequiredArgsConstructor(onConstructor_ = @Autowired)
@Category("feeds")
public class ChangeFeedAction extends Action<ChangeFeedAction.Req, ChangeFeedAction.Res> {

    private final FeedsNative2YDao feedsNative2YDao;
    private final MbiService mbiService;
    private final FeedsService feedsService;

    @Override
    public Res process(Req request) throws WebmasterException {
        WebmasterHostId hostId = request.getHostId();
        String domain = WwwUtil.cutWWWAndM(hostId);
        // temp parse url + login + password
        FeedsService.UrlWithUserInfo urlWithUserInfo = feedsService.parseUrl(request.url);
        request.url = urlWithUserInfo.url();
        //
        NativeFeedInfo2 info = feedsNative2YDao.get(domain, request.url);
        if (info == null) {
            return new Res.FeedNotExistsResponse();
        }

        if (CollectionUtils.isEmpty(request.regionsId)) {
            return new Res.NoRegionsResponse();
        }

        if (!info.getRegionsId().equals(request.regionsId)) {
            info = info.withRegionsId(request.regionsId);
            if (info.getPartnerId() != null) {
                var req =
                        new UpdateFeedFeaturesRequest(info.getPartnerId(), new DatacampPartnerProperties(null, null,
                                info.getRegionsId()));
                mbiService.updateFeatures(req);
            }
        }
        feedsNative2YDao.update(info);

        return new Res.NormalResponse();
    }

    @Setter(onMethod_ = @RequestQueryProperty)
    public static class Req extends AbstractUserVerifiedHostRequest {
        String url;
        List<Integer> regionsId;

        @RequestQueryProperty(required = true)
        public void setUrl(String url) {
            this.url = url;
        }
    }

    public abstract static class Res implements ActionResponse {

        static class NormalResponse extends Res implements ActionResponse.NormalResponse {
        }


        public enum ErrorCode {
            FEED_NOT_EXISTS,
            NO_REGIONS
        }

        public abstract static class AbstractChangeFeedError extends Res implements ActionResponse.ErrorResponse {
            private final ErrorCode code;

            public AbstractChangeFeedError(ErrorCode code) {
                this.code = code;
            }

            @Override
            public Enum<?> getCode() {
                return code;
            }
        }

        @Description("Фид не добавлен")
        public static class FeedNotExistsResponse extends Res.AbstractChangeFeedError {
            public FeedNotExistsResponse() {
                super(ErrorCode.FEED_NOT_EXISTS);
            }
        }

        @Description("Нет регионов")
        public static class NoRegionsResponse extends Res.AbstractChangeFeedError {
            public NoRegionsResponse() {
                super(ErrorCode.NO_REGIONS);
            }
        }


    }
}
