function loginError(message, code = null) {
    let errorStr;
    if (code) {
        errorStr = `Status code ${code}: ${message}`;
    } else {
        errorStr = message;
    }

    document.getElementById("error-text").textContent = errorStr;

    document.getElementById("login-error").style.display = "block";
}

async function generateToken(username, password) {
    let response;
    try {
        response = await fetch("/api/v1/login/generate_token", {
            method: "POST",
            headers: {
                "Content-Type": "application/json",
            },
            body: JSON.stringify({
                username,
                password,
            }),
        })
    } catch (err) {
        loginError(`Internal Server Error: ${err.message}`)
        throw new Error(err);
    }

    if (!response.ok) {
        if (response.status == 400) { // Invalid Login
            loginError("Invalid SFID or Password");
        } else {
            loginError(await response.text(), response.status);
        }

        throw new Error("Network Response was not okay when Generating Token");
    };
    
    const data = await response.json();

    if (data["error"]) {
        let error = data["error"];
        if (error == "invalid_client" || error == "unsupported_grant_type") {
            loginError("Website is misconfigured, contact a SPFN developer to fix this", 502);
        } else if (error == "invalid_request") {
            loginError("Website sent invalid data to account, contact a SPFN developer to fix this", 502);
        } else if (error == "invalid_grant") {
            loginError("Invalid SFID or Password");
        } else {
            loginError(error);
        }
        
        throw new Error(`Token Generation Returned Error: ${data["error"]}`);
    }

    if (!data["access_token"]) {
        loginError("Malformed Response from API, contact a SPFN developer to fix this", 502);
        throw new Error(`No Token in Response from API but No Error Field Either: ${data}`)
    }

    sessionStorage.setItem("authToken", data["access_token"]);

    if (!data["expires_in"]) {
        loginError("Malformed Response from API, contact a SPFN developer to fix this", 502);
        throw new Error(`No Expiry in Response from API but No Error Field Either: ${data}`)
    }

    const expiry = Date.now() + (data["expires_in"] * 1000);
    sessionStorage.setItem("authExpires", expiry)
    return data["access_token"];
}

async function getToken(username, password) {
    let token = sessionStorage.getItem("authToken");

    let expiryStr = sessionStorage.getItem("authExpires");
    if (expiryStr) { // Expiry exists so token should exist
        let expiry = new Date(expiryStr);
        if (expiry < new Date()) { // Expired token
            token = await generateToken(username, password);
        } else if (!token) { // Expiry Saved but No Token (shouldn't be possible but it'll be caught if it happens)
            token = await generateToken(username, password);
        }
    } else { // Token Never Saved in Session
        token = await generateToken(username, password);
    }

    return token
}

document.getElementById("login").addEventListener("submit", async function(event) {
    event.preventDefault();

    document.getElementById("login-error").style.display = "none";

    const username = await document.getElementById("username").value;
    const password = await document.getElementById("password").value;
    
    let token = await getToken(username, password);
    if (!token) return;

    document.getElementById("password").value = "";

    // Go Back to Origin Page
    const params = new URLSearchParams(window.location.search);
    const redirectURL = params.get("redirect")

    window.location.href = redirectURL;
})

window.onload = async function () { // Check if the token expired
    let expiryStr = sessionStorage.getItem("authExpires");
    if (expiryStr) {
        let expiry = new Date(expiryStr);

        if (expiry < new Date()) { // Expired - Tell the user it expired
            loginError("Login Expired - Please Log In Again")
        }
    }
}