package ru.yandex.direct.web.entity.keyword.service.validation;

import java.util.Collection;
import java.util.Map;

import ru.yandex.direct.validation.builder.Constraint;
import ru.yandex.direct.validation.builder.ItemValidationBuilder;
import ru.yandex.direct.validation.result.Defect;
import ru.yandex.direct.validation.result.ValidationResult;
import ru.yandex.direct.validation.wrapper.DefaultValidator;
import ru.yandex.direct.web.entity.keyword.model.CheckMinusKeywordsInclusionRequestItem;

import static ru.yandex.direct.core.entity.keyword.service.validation.phrase.minusphrase.MinusPhraseDefects.minusKeywordIsIncludedInKeyword;
import static ru.yandex.direct.web.entity.keyword.model.CheckMinusKeywordsInclusionRequestItem.MINUS_KEYWORDS_FIELD_NAME;

public class CheckMinusKeywordInclusionValidator implements DefaultValidator<CheckMinusKeywordsInclusionRequestItem> {

    private final Map<Long, ? extends Collection<String>> wrongMinusKeywordsByParentId;

    private CheckMinusKeywordInclusionValidator(
            Map<Long, ? extends Collection<String>> wrongMinusKeywordsByParentId) {
        this.wrongMinusKeywordsByParentId = wrongMinusKeywordsByParentId;
    }

    public static CheckMinusKeywordInclusionValidator checkInclusionValidator(
            Map<Long, ? extends Collection<String>> wrongMinusKeywordsByParentId) {
        return new CheckMinusKeywordInclusionValidator(wrongMinusKeywordsByParentId);
    }

    @Override
    public ValidationResult<CheckMinusKeywordsInclusionRequestItem, Defect> apply(
            CheckMinusKeywordsInclusionRequestItem item) {
        Long parentId = item.getId();
        Collection<String> wrongKeywords = wrongMinusKeywordsByParentId.get(parentId);
        if (wrongKeywords == null) {
            return new ValidationResult<>(item);
        }

        Constraint<String, Defect> wrongKeywordConstraint =
                (keyword) -> {
                    if (wrongKeywords.contains(keyword)) {
                        return minusKeywordIsIncludedInKeyword();
                    } else {
                        return null;
                    }
                };

        ItemValidationBuilder<CheckMinusKeywordsInclusionRequestItem, Defect> ivb =
                ItemValidationBuilder.of(item);
        ivb.list(item.getMinusKeywords(), MINUS_KEYWORDS_FIELD_NAME)
                .checkEach(wrongKeywordConstraint);
        return ivb.getResult();
    }

}
