/*
 * 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.dto.view;

import static nl.tudelft.librador.SpringContext.getBean;

import java.time.LocalDateTime;
import java.util.stream.Collectors;

import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.EqualsAndHashCode;
import lombok.NoArgsConstructor;
import nl.tudelft.labracore.api.dto.PersonSummaryDTO;
import nl.tudelft.labracore.api.dto.RolePersonLayer1DTO;
import nl.tudelft.labracore.api.dto.StudentGroupDetailsDTO;
import nl.tudelft.librador.dto.view.View;
import nl.tudelft.queue.cache.SessionCacheManager;
import nl.tudelft.queue.cache.StudentGroupCacheManager;
import nl.tudelft.queue.model.Feedback;
import nl.tudelft.queue.model.LabRequest;

import com.beust.jcommander.Strings;

@Data
@NoArgsConstructor
@AllArgsConstructor
@EqualsAndHashCode(callSuper = false)
public class FeedbackViewDTO extends View<Feedback> {
	private Feedback.Id id;
	private PersonSummaryDTO assistant;

	private LabRequest request;

	private String feedback;
	private Integer rating;

	private LocalDateTime createdAt;
	private LocalDateTime lastUpdatedAt;

	private String groupName;
	private String editionName;

	@Override
	public void postApply() {
		super.postApply();

		groupName = requesterEntityName(data.getRequest().getStudentGroup());
		editionName = editionName(data.getRequest().getSession().getSession());
	}

	private String editionName(Long sessionId) {
		var session = getBean(SessionCacheManager.class).getRequired(sessionId);

		return (session.getEdition() == null) ? session.getEditionCollection().getName()
				: session.getEdition().getName();
	}

	/**
	 * Gets the name of the student group that this request is from.
	 *
	 * @return The name of the group that the request was created for with description of its members.
	 */
	private String studentGroupName(StudentGroupDetailsDTO studentGroup) {
		return "Group " + studentGroup.getName() + " (" +
				Strings.join(", ", studentGroup.getMembers().stream()
						.filter(r -> r.getType() == RolePersonLayer1DTO.TypeEnum.STUDENT)
						.map(r -> r.getPerson().getDisplayName()).collect(Collectors.toList()))
				+
				")";
	}

	/**
	 * Converts the student group name or requester name into a string.
	 *
	 * @return The name of the requesting entity (either the group or the student).
	 */
	private String requesterEntityName(Long studentGroupId) {
		var studentGroup = getBean(StudentGroupCacheManager.class).getRequired(studentGroupId);
		if (studentGroup.getMemberUsernames().size() == 1) {
			return studentGroup.getMembers().get(0).getPerson().getDisplayName();
		} else {
			return studentGroupName(studentGroup);
		}
	}
}
