package be.jeffcheasey88.peeratcode.routes;

import static be.jeffcheasey88.peeratcode.framework.RequestType.POST;

import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.util.regex.Matcher;

import org.json.simple.JSONObject;

import be.jeffcheasey88.peeratcode.bonus.extract.RouteDoc;
import be.jeffcheasey88.peeratcode.framework.HttpReader;
import be.jeffcheasey88.peeratcode.framework.HttpWriter;
import be.jeffcheasey88.peeratcode.framework.Response;
import be.jeffcheasey88.peeratcode.framework.Route;
import be.jeffcheasey88.peeratcode.framework.Router;
import be.jeffcheasey88.peeratcode.framework.User;
import be.jeffcheasey88.peeratcode.repository.DatabaseRepository;

public class Register implements Response {

	private DatabaseRepository databaseRepo;
	private Router router;
	private String usersFilesPath;

	public Register(DatabaseRepository databaseRepo, Router router, String initUsersFilesPath) {
		this.databaseRepo = databaseRepo;
		this.router = router;
		usersFilesPath = initUsersFilesPath;
	}
	
	@RouteDoc(path = "/register", responseCode = 200, responseDescription = "L'utilisateur est inscrit")
	@RouteDoc(responseCode = 403, responseDescription = "L'utilisateur est connecté")
	@RouteDoc(responseCode = 400, responseDescription = "Aucune données fournie / données invalide")

	@Route(path = "^\\/register$", type = POST)
	public void exec(Matcher matcher, User user, HttpReader reader, HttpWriter writer) throws Exception{
		if (user != null){
			writer.response(403, "Access-Control-Allow-Origin: *");
			return;
		}
		JSONObject informations = reader.readJson();
		if (informations != null) {
			boolean allFieldsFilled = informations.containsKey("pseudo") && informations.containsKey("email")
					&& informations.containsKey("passwd") && informations.containsKey("firstname")
					&& informations.containsKey("lastname") && informations.containsKey("description")
					&& informations.containsKey("sgroup") && informations.containsKey("avatar");
			if (!allFieldsFilled) {
				writer.response(403, "Access-Control-Allow-Origin: *");
				return;
			}
			String pseudo = (String) informations.get("pseudo");
			String email = (String) informations.get("email");
			String password = (String) informations.get("passwd");
			String firstname = (String) informations.get("firstname");
			String lastname = (String) informations.get("lastname");
			String description = (String) informations.get("description");
			String group = (String) informations.get("sgroup");
			String avatar = (String) informations.get("avatar");

			boolean pseudoAvailable = databaseRepo.checkPseudoAvailability(pseudo);
			boolean emailAvailable = databaseRepo.checkEmailAvailability(email);
			if (pseudoAvailable && emailAvailable) {
				int id;
				if ((id = databaseRepo.register(pseudo, email, password, firstname, lastname, description, group,
						avatar)) >= 0) {
					writer.response(200, "Access-Control-Allow-Origin: *",
							"Access-Control-Expose-Headers: Authorization",
							"Authorization: Bearer " + this.router.createAuthUser(id));
					createFolderToSaveSourceCode(pseudo);
					return;
				}
			} else {
				writer.response(400, "Access-Control-Allow-Origin: *");
				JSONObject error = new JSONObject();
				error.put("username_valid", pseudoAvailable);
				error.put("email_valid", emailAvailable);
				writer.write(error.toJSONString());
				return;
			}
		}
		writer.response(400, "Access-Control-Allow-Origin: *");
	}

	private void createFolderToSaveSourceCode(String pseudo) throws IOException {

		Files.createDirectories(Paths.get(String.format("%s/%s", usersFilesPath, pseudo)));
	}

}
