/*
 * Queue - A Queueing system that can be used to handle labs in higher education
 * Copyright (C) 2016-2021  Delft University of Technology
 *
 * This program is free software: you can redistribute it and/or modify
 * it under the terms of the GNU Affero General Public License as
 * published by the Free Software Foundation, either version 3 of the
 * License, or (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU Affero General Public License for more details.
 *
 * You should have received a copy of the GNU Affero General Public License
 * along with this program.  If not, see <https://www.gnu.org/licenses/>.
 */
package nl.tudelft.queue.service;

import static org.assertj.core.api.Assertions.assertThat;

import java.util.Collections;
import java.util.List;
import java.util.Map;

import javax.transaction.Transactional;

import nl.tudelft.labracore.api.dto.PersonSummaryDTO;
import nl.tudelft.queue.model.LabRequest;
import nl.tudelft.queue.model.embeddables.RequestEventInfo;

import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;

import test.TestDatabaseLoader;
import test.labracore.PersonApiMocker;
import test.test.TestQueueApplication;

@Transactional
@SpringBootTest(classes = TestQueueApplication.class)
public class EditionStatusServiceTest {

	@Autowired
	private EditionStatusService ess;

	@Autowired
	private PersonApiMocker pApiMocker;

	@Autowired
	private TestDatabaseLoader db;

	private PersonSummaryDTO ta1;
	private PersonSummaryDTO ta2;

	private LabRequest r1;
	private LabRequest r2;
	private LabRequest r3;

	@BeforeEach
	void setUp() {
		pApiMocker.mock();

		ta1 = db.getStudents()[100];
		ta2 = db.getStudents()[200];

		r1 = new LabRequest();
		r2 = new LabRequest();
		r3 = new LabRequest();

		r1.setEventInfo(new RequestEventInfo());
		r2.setEventInfo(new RequestEventInfo());
		r3.setEventInfo(new RequestEventInfo());
	}

	@Test
	void countRequestsPerAssistantNoRequestsTest() {
		Map<String, Long> result = ess.countRequestsPerAssistant(Collections.emptyList());

		assertThat(result).isEmpty();
	}

	@Test
	void countRequestsPerAssistantNoRequestsTakenTest() {
		Map<String, Long> result = ess.countRequestsPerAssistant(List.of(r1, r2, r3));

		assertThat(result).isEmpty();
	}

	@Test
	void countRequestsPerAssistantAllByOneTATest() {
		r1.getEventInfo().setAssignedTo(ta1.getId());
		r2.getEventInfo().setAssignedTo(ta1.getId());
		r3.getEventInfo().setAssignedTo(ta1.getId());

		Map<String, Long> result = ess.countRequestsPerAssistant(List.of(r1, r2, r3));

		assertThat(result).containsExactlyEntriesOf(Map.of(ta1.getDisplayName(), 3L));
	}

	@Test
	void countRequestsPerAssistantSomeTakenByBothTAsTest() {
		r1.getEventInfo().setAssignedTo(ta1.getId());
		r3.getEventInfo().setAssignedTo(ta2.getId());

		Map<String, Long> result = ess.countRequestsPerAssistant(List.of(r1, r2, r3));

		assertThat(result).containsExactlyInAnyOrderEntriesOf(Map.of(
				ta1.getDisplayName(), 1L, ta2.getDisplayName(), 1L));

	}

	@Test
	void countRequestsPerAssistantAllTakenByBothTAsTest() {
		r1.getEventInfo().setAssignedTo(ta2.getId());
		r2.getEventInfo().setAssignedTo(ta1.getId());
		r3.getEventInfo().setAssignedTo(ta1.getId());

		Map<String, Long> result = ess.countRequestsPerAssistant(List.of(r1, r2, r3));

		assertThat(result).containsExactlyInAnyOrderEntriesOf(Map.of(
				ta1.getDisplayName(), 2L, ta2.getDisplayName(), 1L));

	}
}
