package com.example.projectback.controllers;

import com.example.projectback.model.*;
import com.example.projectback.repository.*;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.web.bind.annotation.*;

import java.util.List;
import java.util.Optional;

@RestController
@CrossOrigin(origins = "http://localhost:4200")
@RequestMapping("/students")
public class StudentController {
    private final StudentRepository studentRepository;
    private final SubjectRepository subjectRepository;
    private final GradeRepository gradeRepository;
    private final SubjectStudentRepository subjectStudentRepository;
    private final UserRepository userRepository;

    @Autowired
    public StudentController(StudentRepository studentRepository,
                             SubjectRepository subjectRepository,
                             GradeRepository gradeRepository,
                             SubjectStudentRepository subjectStudentRepository,
                             UserRepository userRepository) {
        this.studentRepository = studentRepository;
        this.subjectRepository = subjectRepository;
        this.gradeRepository = gradeRepository;
        this.subjectStudentRepository = subjectStudentRepository;
        this.userRepository = userRepository;
    }

    @GetMapping
    @PreAuthorize("hasRole('ADMIN')")
    public List<Student> getAllStudents() {
        return studentRepository.findAll();
    }

    @PostMapping
    @PreAuthorize("hasRole('ADMIN')")
    public ResponseEntity<Student> addStudent(@RequestBody Student student) {
        studentRepository.save(student);
        return new ResponseEntity<>(student, HttpStatus.CREATED);
    }

    @PostMapping("/delete")
    @PreAuthorize("hasRole('ADMIN')")
    public ResponseEntity<Changeset> deleteStudents(@RequestBody Changeset changeset) {
        for (Long recId : changeset.getRecords()) {
            Optional<Student> student = studentRepository.findById(recId);
            if (student.isEmpty()) continue;
            Optional<User> user = userRepository.findByEmail(student.get().getEmail());
            user.ifPresent(userRepository::delete);
            List<SubjectStudent> subjectStudents = subjectStudentRepository.getAllByStudent(student.get());
            subjectStudentRepository.deleteAll(subjectStudents);
            studentRepository.delete(student.get());
        }
        return new ResponseEntity<>(changeset, HttpStatus.OK);
    }

    @PostMapping("/{id}/grades")
    @PreAuthorize("hasRole('ADMIN')")
    public ResponseEntity<Grade> addGrade(@PathVariable("id") Long id, @RequestBody Grade grade) {
        Student student = this.studentRepository.getById(id);
        student.getGrades().add(grade);
        this.gradeRepository.save(grade);
        this.studentRepository.save(student);
        return new ResponseEntity<>(grade, HttpStatus.OK);
    }

    @DeleteMapping("/{studentID}/grades/{gradeID}")
    @PreAuthorize("hasRole('ADMIN')")
    public ResponseEntity<Student> deleteGrade(@PathVariable("studentID") Long studentID, @PathVariable("gradeID") Long gradeID) {
        Student student = this.studentRepository.getById(studentID);
        Grade grade = this.gradeRepository.getById(gradeID);
        student.getGrades().remove(grade);
        this.studentRepository.save(student);
        this.gradeRepository.delete(grade);
        return new ResponseEntity<>(student, HttpStatus.OK);
    }

    @PatchMapping("/{studentID}/payment/{subjectID}")
    @PreAuthorize("hasRole('ADMIN')")
    public ResponseEntity<Student> confirmPayment(@PathVariable("studentID") Long studentID, @PathVariable("subjectID") Long subjectID, @RequestBody SubjectStudent subjectStudentReq) {
        Student student = this.studentRepository.getById(studentID);
        Subject subject = this.subjectRepository.getById(subjectID);
        SubjectStudent subjectStudent = this.subjectStudentRepository.getByStudentAndSubject(student, subject);
        subjectStudent.setPaymentConfirmed(subjectStudentReq.isPaymentConfirmed());
        this.subjectStudentRepository.save(subjectStudent);
        return new ResponseEntity<>(student, HttpStatus.OK);
    }
}
