package com.magistr.app.controller;

import com.magistr.app.config.auth.AuthContext;
import com.magistr.app.config.auth.AuthenticatedUser;
import com.magistr.app.model.Role;
import com.magistr.app.model.Subject;
import com.magistr.app.model.TeacherSubject;
import com.magistr.app.model.User;
import com.magistr.app.repository.SubjectRepository;
import com.magistr.app.repository.TeacherSubjectRepository;
import com.magistr.app.repository.UserRepository;
import com.magistr.app.service.TeacherDepartmentService;
import org.junit.jupiter.api.AfterEach;
import org.junit.jupiter.api.Test;
import org.mockito.ArgumentCaptor;

import java.time.LocalDate;
import java.util.Map;
import java.util.Optional;

import static org.assertj.core.api.Assertions.assertThat;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.when;

class TeacherSubjectControllerTest {

    @AfterEach
    void clearAuthContext() {
        AuthContext.clear();
    }

    @Test
    void departmentCanManageTeacherThroughAdditionalActiveAssignment() {
        TeacherSubjectRepository teacherSubjectRepository = mock(TeacherSubjectRepository.class);
        UserRepository userRepository = mock(UserRepository.class);
        SubjectRepository subjectRepository = mock(SubjectRepository.class);
        TeacherDepartmentService teacherDepartmentService = mock(TeacherDepartmentService.class);
        User teacher = teacher();
        Subject subject = new Subject();
        subject.setId(20L);
        subject.setName("Высшая математика");
        subject.setDepartmentId(1L);
        when(userRepository.findById(teacher.getId())).thenReturn(Optional.of(teacher));
        when(subjectRepository.findById(subject.getId())).thenReturn(Optional.of(subject));
        when(teacherDepartmentService.hasAssignmentAtDate(
                teacher.getId(),
                1L,
                LocalDate.now()
        )).thenReturn(true);
        TeacherSubjectController controller = new TeacherSubjectController(
                teacherSubjectRepository,
                userRepository,
                subjectRepository,
                teacherDepartmentService
        );
        AuthContext.setCurrentUser(new AuthenticatedUser(1L, "кафедра", Role.DEPARTMENT, 1L));

        var response = controller.create(Map.of("userId", teacher.getId(), "subjectId", subject.getId()));

        assertThat(response.getStatusCode().value()).isEqualTo(200);
        ArgumentCaptor<TeacherSubject> captor = ArgumentCaptor.forClass(TeacherSubject.class);
        verify(teacherSubjectRepository).save(captor.capture());
        assertThat(captor.getValue().getUserId()).isEqualTo(teacher.getId());
        assertThat(captor.getValue().getSubjectId()).isEqualTo(subject.getId());
    }

    private User teacher() {
        User teacher = new User();
        teacher.setId(10L);
        teacher.setUsername("teacher");
        teacher.setRole(Role.TEACHER);
        teacher.setFullName("Петров Пётр Петрович");
        teacher.setJobTitle("Доцент");
        teacher.setDepartmentId(2L);
        return teacher;
    }
}
