package ru.yandex.autotests.directintapi.bstransport.main.campaign.parameters.finance;
import java.util.List;

import org.junit.Before;
import org.junit.ClassRule;
import org.junit.Test;

import ru.yandex.aqua.annotations.project.Aqua;
import ru.yandex.autotests.direct.utils.money.Currency;
import ru.yandex.autotests.direct.utils.tags.TagDictionary;
import ru.yandex.autotests.directapi.common.api45mng.APIPort_PortType;
import ru.yandex.autotests.directapi.darkside.Logins;
import ru.yandex.autotests.directapi.darkside.connection.Semaphore;
import ru.yandex.autotests.directapi.darkside.datacontainers.http.response.json.ClientsCreateResponse;
import ru.yandex.autotests.directapi.darkside.datacontainers.jsonrpc.fake.VATRateInfo;
import ru.yandex.autotests.directapi.darkside.model.RunBsTransportScriptResponse;
import ru.yandex.autotests.directapi.darkside.model.bslogs.clientdata.Campaign;
import ru.yandex.autotests.directapi.darkside.model.bslogs.clientdata.NdsHistoryElem;
import ru.yandex.autotests.directapi.darkside.steps.DarkSideSteps;
import ru.yandex.autotests.directapi.model.api5.agencyclients.AddRequestMap;
import ru.yandex.autotests.directapi.rules.ApiSteps;
import ru.yandex.autotests.directintapi.bstransport.FeatureNames;
import ru.yandex.autotests.directintapi.bstransport.StoriesNames;
import ru.yandex.qatools.Tag;
import ru.yandex.qatools.allure.annotations.Features;
import ru.yandex.qatools.allure.annotations.Issue;
import ru.yandex.qatools.allure.annotations.Stories;
import ru.yandex.qatools.allure.annotations.Title;
import ru.yandex.qatools.hazelcast.SemaphoreRule;

import static org.hamcrest.Matchers.allOf;
import static org.hamcrest.Matchers.greaterThan;
import static org.hamcrest.Matchers.hasItem;
import static org.hamcrest.Matchers.hasItems;
import static org.hamcrest.Matchers.hasSize;
import static org.hamcrest.Matchers.notNullValue;
import static ru.yandex.autotests.direct.db.steps.ClientsOptionsSteps.ClientFlagsEnum.CREATE_WITHOUT_WALLET;
import static ru.yandex.autotests.direct.utils.matchers.BeanEquals.beanEquals;
import static ru.yandex.autotests.irt.testutils.allure.TestSteps.assertThat;
import static ru.yandex.autotests.irt.testutils.allure.TestSteps.assumeThat;

@Aqua.Test
@Tag(TagDictionary.RELEASE)
@Title("Транспорт: проверка отправки в БК графика НДС")
@Stories(StoriesNames.CAMPAIGN_PARAMS_FINANCE)
@Features({FeatureNames.CAMPAIGNS, FeatureNames.NOT_FOR_FULL_EXPORT})
@Issue("https://st.yandex-team.ru/TESTIRT-1869")
public class BsTransportOfNdsHistoryTest {

    private static final Currency CURRENCY = Currency.RUB;
    private static final double EXPECTED_NDS_1 = 1.618;
    private static final double EXPECTED_NDS_2 = 2.718;

    private static final String MANAGER_LOGIN = Logins.LOGIN_MNGR;

    @ClassRule
    public static ApiSteps api = new ApiSteps().wsdl(APIPort_PortType.class).as(MANAGER_LOGIN);
    private static DarkSideSteps darkSideSteps = api.userSteps.getDarkSideSteps();

    @ClassRule
    public static SemaphoreRule semaphore = Semaphore.getSemaphore();

    private String login;
    private int shard;

    @Before
    public void before() {
        String userLogin = AddRequestMap.generateLogin("transport-nds-");
        ClientsCreateResponse createClientResponse = darkSideSteps.getClientsSteps()
                .createManagerClient(userLogin, MANAGER_LOGIN, CURRENCY);
        login = createClientResponse.getLogin();
        Integer clientId = Integer.parseInt(createClientResponse.getClientId());

        api.as(MANAGER_LOGIN).userSteps.getDirectJooqDbSteps().useShardForLogin(login);
        api.userSteps.getDirectJooqDbSteps().clientsOptionsSteps().setClientFlag(clientId.longValue(), CREATE_WITHOUT_WALLET);
        shard = api.userSteps.clientFakeSteps().getUserShard(login);
    }

    @Test
    @Title("Проверка отправки графика НДС с одним элементом в БК")
    public void testNdsHistoryWithOneElement() {
        api.userSteps.clientFakeSteps().setVATRate(login, EXPECTED_NDS_1);
        Long cid = api.userSteps.campaignSteps().addDefaultTextCampaign(login);
        api.userSteps.campaignFakeSteps().makeNewCampaignReadyForSendingToBS(cid);


        RunBsTransportScriptResponse response = api.userSteps.getDarkSideSteps().getTransportSteps().sendCampaign(shard, cid);
        Campaign campaign = api.userSteps.getDarkSideSteps().getTransportSteps().getClientDataRequestCampaign(response, cid);
        List<NdsHistoryElem> ndsHistory = campaign.getNdsHistory();
        assumeThat("имеется непустой массив NdsHistory", ndsHistory, allOf(notNullValue(), hasSize(greaterThan(0))));

        NdsHistoryElem expectedNdsElem = new NdsHistoryElem();
        expectedNdsElem.setNds(EXPECTED_NDS_1);
        assertThat("значение НДС соответствует ожидаемому", ndsHistory, allOf(
                notNullValue(),
                hasItem(beanEquals(expectedNdsElem))));
    }

    @Test
    @Title("Проверка корректности отправки графика НДС с двумя элементами в БК")
    public void testNdsHistoryWithTwoElements() {
        api.userSteps.clientFakeSteps().setVATRate(
                new VATRateInfo(login, EXPECTED_NDS_1, "2014-01-01", "2014-04-01"),
                new VATRateInfo(login, EXPECTED_NDS_2, "2015-01-01", "2015-04-01"));
        Long cid = api.userSteps.campaignSteps().addDefaultTextCampaign(login);
        api.userSteps.campaignFakeSteps().makeNewCampaignReadyForSendingToBS(cid);

        RunBsTransportScriptResponse response = api.userSteps.getDarkSideSteps().getTransportSteps().sendCampaign(shard, cid);
        Campaign campaign = api.userSteps.getDarkSideSteps().getTransportSteps().getClientDataRequestCampaign(response, cid);
        List<NdsHistoryElem> ndsHistory = campaign.getNdsHistory();
        assumeThat("имеется непустой массив NdsHistory", ndsHistory, allOf(notNullValue(), hasSize(greaterThan(0))));

        NdsHistoryElem expectedNdsElem1 = new NdsHistoryElem();
        expectedNdsElem1.setNds(EXPECTED_NDS_1);
        NdsHistoryElem expectedNdsElem2 = new NdsHistoryElem();
        expectedNdsElem2.setNds(EXPECTED_NDS_2);
        assertThat("значение НДС соответствует ожидаемому", ndsHistory, allOf(
                notNullValue(),
                hasItems(beanEquals(expectedNdsElem1), beanEquals(expectedNdsElem2))));
    }
}
