package ru.mcs.diary.parent;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import ru.mcs.diary.auth.AuthService;
import ru.mcs.diary.common.exception.ResourceNotFoundException;
import ru.mcs.diary.parent.dto.ParentCreateRequest;
import ru.mcs.diary.parent.dto.ParentListDto;
import ru.mcs.diary.student.StudentParentRepository;
import ru.mcs.diary.teacher.Teacher;
import ru.mcs.diary.teacher.TeacherRepository;
import java.util.List;
@Slf4j
@Service
@RequiredArgsConstructor
public class ParentService {
private final ParentRepository parentRepository;
private final StudentParentRepository studentParentRepository;
private final TeacherRepository teacherRepository;
private final AuthService authService;
@Transactional(readOnly = true)
public List<ParentListDto> getAllParents(Long teacherId) {
return parentRepository.findAllByTeacherIdOrderByLastNameAsc(teacherId)
.stream()
.map(this::toListDto)
.toList();
}
@Transactional(readOnly = true)
public Parent getParent(Long id, Long teacherId) {
return parentRepository.findById(id)
.filter(p -> p.getTeacher().getId().equals(teacherId))
.orElseThrow(() -> new ResourceNotFoundException("Родитель", id));
}
@Transactional
public Parent createParent(ParentCreateRequest request, Long teacherId) {
log.info("Creating parent: {} {}", request.getLastName(), request.getFirstName());
Teacher teacher = teacherRepository.findById(teacherId)
.orElseThrow(() -> new ResourceNotFoundException("Преподаватель", teacherId));
// Проверяем уникальность email для данного преподавателя
if (parentRepository.existsByEmailAndTeacherId(request.getEmail().toLowerCase(), teacherId)) {
throw new IllegalArgumentException("Родитель с таким email уже существует");
}
Parent parent = Parent.builder()
.firstName(request.getFirstName().trim())
.lastName(request.getLastName().trim())
.patronymic(request.getPatronymic() != null ? request.getPatronymic().trim() : null)
.email(request.getEmail().toLowerCase().trim())
.phone(request.getPhone().trim())
.teacher(teacher)
.enabled(false)
.build();
return parentRepository.save(parent);
}
@Transactional
public Parent updateParent(Long id, ParentCreateRequest request, Long teacherId) {
log.info("Updating parent: {}", id);
Parent parent = getParent(id, teacherId);
// Проверяем уникальность email если он изменился
String newEmail = request.getEmail().toLowerCase().trim();
if (!parent.getEmail().equals(newEmail) &&
parentRepository.existsByEmailAndTeacherId(newEmail, teacherId)) {
throw new IllegalArgumentException("Родитель с таким email уже существует");
}
parent.setFirstName(request.getFirstName().trim());
parent.setLastName(request.getLastName().trim());
parent.setPatronymic(request.getPatronymic() != null ? request.getPatronymic().trim() : null);
parent.setEmail(newEmail);
parent.setPhone(request.getPhone().trim());
return parentRepository.save(parent);
}
@Transactional
public void deleteParent(Long id, Long teacherId) {
log.info("Deleting parent: {}", id);
Parent parent = getParent(id, teacherId);
parentRepository.delete(parent);
}
@Transactional
public void sendInvite(Long id, Long teacherId) {
Parent parent = getParent(id, teacherId);
Teacher teacher = teacherRepository.findById(teacherId)
.orElseThrow(() -> new ResourceNotFoundException("Преподаватель", teacherId));
authService.sendParentInvite(parent, teacher.getFullName());
log.info("Invite sent to parent: {}", parent.getEmail());
}
public long countByTeacher(Long teacherId) {
return parentRepository.findAllByTeacherIdOrderByLastNameAsc(teacherId).size();
}
private ParentListDto toListDto(Parent parent) {
return ParentListDto.builder()
.id(parent.getId())
.fullName(parent.getFullName())
.email(parent.getEmail())
.phone(parent.getPhone())
.childrenCount(studentParentRepository.countChildrenByParentId(parent.getId()))
.activated(parent.getEnabled())
.build();
}
}