package dev.peerat.backend.routes.groups;

import static dev.peerat.framework.RequestType.POST;

import java.time.LocalDateTime;
import java.util.regex.Matcher;

import dev.peerat.backend.Configuration;
import dev.peerat.backend.bonus.extract.RouteDoc;
import dev.peerat.backend.model.Chapter;
import dev.peerat.backend.model.Completion;
import dev.peerat.backend.model.Group;
import dev.peerat.backend.model.PeerAtUser;
import dev.peerat.backend.repository.DatabaseChapterRepository;
import dev.peerat.backend.repository.DatabaseGroupRepository;
import dev.peerat.backend.repository.DatabaseRepository;
import dev.peerat.framework.Context;
import dev.peerat.framework.HttpReader;
import dev.peerat.framework.HttpWriter;
import dev.peerat.framework.Injection;
import dev.peerat.framework.Locker;
import dev.peerat.framework.Response;
import dev.peerat.framework.Route;

public class GroupJoin implements Response{
	
	private DatabaseChapterRepository chapterRepo;
	private DatabaseGroupRepository groupRepo;
	private int groupDelay;
	private String waitTime;
	
	private final Locker<Completion> leaderboard;

	public GroupJoin(DatabaseRepository repo, Configuration config, @Injection("leaderboard") Locker<Completion> locker){
		this.chapterRepo = repo.getChapterRepository();
		this.groupRepo = repo.getGroupRepository();
		this.groupDelay = config.getGroupJoinMinutes();
		this.waitTime = config.getGroupQuitMinutes();
		this.leaderboard = locker;
	}

	@RouteDoc(path = "/groupJoin", responseCode = 200, responseDescription = "L'utilisateur a rejoint le groupe")
	@RouteDoc(responseCode = 403, responseDescription = "L'utilisateur est déjà dedans / ne peux pas le rejoindre")
	@RouteDoc(responseCode = 423, responseDescription = "L'utilisateur essaye de rejoindre un groupe après le délai maximum de création de l'event")
	@RouteDoc(responseCode = 409, responseDescription = "L'utilisateur est un peu débile... ou pas ?")
	
	@Route(path = "^\\/groupJoin$", type = POST, needLogin = true)
	public void exec(Matcher matcher, Context context, HttpReader reader, HttpWriter writer) throws Exception{
		Group group = new Group(reader.readJson());
		PeerAtUser user = context.getUser();
		
		Group userGroup = this.groupRepo.getPlayerGroup(user.getId(), group.getLinkToChapter());
		if(group.equals(userGroup)){
			context.response(403);
			return;
		}
		
		if(group.getLinkToChapter() == null){
			context.response(409);
			writer.write(waitTime);
			return;
		}
		
		if(group.getLinkToChapter() != null){
			Chapter chapter = this.chapterRepo.getChapter(group.getLinkToChapter());
			if(chapter.getStartDate() != null){
				LocalDateTime start = chapter.getStartDate().toLocalDateTime().plusMinutes(this.groupDelay);
				if(LocalDateTime.now().isAfter(start)){
					context.response(423);
					return;
				}
			}
		}
		
		if (this.groupRepo.insertUserInGroup(group, user)) {
			context.response(200);
			
			leaderboard.setValue(new Completion(0, 0, 0, null, 0));
		} else {
			context.response(403);
		}
	}
	
}
