class BlueWeather {

    constructor() {
        // cunstruct xmlhttp
        this.xhttp = new XMLHttpRequest();
        this.host =  "https://weather.itsblue.de"//window.location.href.substring(0, window.location.href.lastIndexOf("/"));

        this.log("init done", 2)

        this.session = {
            loggedIn: false,
            token: "",
            user: {
                realName: "Real Name",
                username: "username"
            }
        }

        this.restoreSession()
    }

    // ----------------------
    // - session management -
    // ----------------------

    restoreSession() {
        if(this.getCookie("session") !== "" && this.getCookie("session") !== undefined) {
            console.log("old session found: " + this.getCookie("session"), 3)
            // old session found
            this.session.loggedIn = true
            this.session.token = this.getCookie("session")
        }
    }

    login(async, username, password, processingFunction) {
        this.xhttp.abort()
        var thisObject = this

        if(async) {
            this.xhttp.onreadystatechange = function() {
                if (this.readyState === 4) {
                    // Typical action to be performed when the document is ready:
                    if(this.status === 200) {
                        thisObject.log("login response was: " + this.responseText, 3)
                        var ret = JSON.parse(this.responseText)
                        if(ret && ret['status'] === 200) {
                            //this.session.token = ret["token"]
                            //this.session.loggedIn = true
                            processingFunction(true)
                            return
                        }
                        else {
                            //this.session.token = ""
                            //this.session.loggedIn = false
                        }
                    }
                    processingFunction(false)
                }
            }
        }

        var url = this.host + "/api/json.php"
        this.log("starting location request; URL is: " + url, 3)
        this.xhttp.open("GET", url, async)
        this.xhttp.send()
    }

    endSession() {
        document.cookie = "session=;"
        window.location.href = "./index.html"
    }

    // --------------------
    // - getter functions -
    // --------------------

    getLocations(async, processingFunction, errorFunction) {
        this.xhttp.abort()
        var thisObject = this
        
        if(async) {
            this.xhttp.onreadystatechange = function () {
                if (this.readyState === 4) {
                    // Typical action to be performed when the document is ready:
                    if(this.status === 200) {
                        thisObject.log("getting sensors response was: " + this.responseText, 3)
                        var ret = JSON.parse(this.responseText)
                        if(ret){
                            processingFunction(ret);
                            return
                        }
                    }

                    if(errorFunction !== null) {
                        errorFunction(this.status, this.text)
                    }
                }
            };    
        }

        var url = this.host + "/api/json.php"
        this.log("starting location request; URL is: " + url, 3)
        this.xhttp.open("GET", url, async)
        this.xhttp.send()
    }

    getLocationData(locId, range = {from:"", to:""}, maxVals = 0, async, processingFunction, errorFunction) {
        this.xhttp.abort()
        var thisObject = this
        
        if(async) {
            this.xhttp.onreadystatechange = function () {
                if (this.readyState === 4) {
                    // Typical action to be performed when the document is ready:
                    if(this.status === 200) {
                        thisObject.log("getting sensors response was: " + this.responseText, 3)
                        var ret = JSON.parse(this.responseText)
                        if(ret){
                            processingFunction(ret);
                            return
                        }
                    }

                    if(errorFunction !== null) {
                        errorFunction(this.status, this.text)
                    }
                }
            };    
        }

        var url = this.host + "/api/json.php?locId="+locId+"&range[from]="+range.from + "&range[to]="+range.to + "&maxVals[mode]=" + maxVals.mode + "&maxVals[count]=" + maxVals.count
        this.log("starting location request; URL is: " + url, 3)
        this.xhttp.open("GET", url, async)
        this.xhttp.send()
    }

    // ----------------------
    // - template functions -
    // ----------------------

    loadProfileObject(parent) {
        if(!parent) {
            return false
        }

        var thisObject = this

        var profileObject = document.createElement("li")
        parent.appendChild(profileObject)
        profileObject.classList.add("nav-item")

        if(!this.session.loggedIn) {
            this.log("not logged in", 3)

            profileObject.classList.add("text-nowrap")

            // create login button
            var loginButton = document.createElement('button')
            profileObject.appendChild(loginButton)
            loginButton.type = "button"
            loginButton.setAttribute("data-toggle", "modal")
            loginButton.setAttribute("data-target", "#loginModal")
            loginButton.classList.add("btn", "btn-outline-light")
            loginButton.innerHTML = "Login"

            // ------------
            // create modal
            var loginModal = document.createElement('div')
            loginModal.id = "loginModal"
            loginModal.setAttribute("tabindex", "-1")
            loginModal.setAttribute("role", "dialog")
            loginModal.setAttribute("aria-labelledby", "exampleModalLabel")
            loginModal.setAttribute("aria-hidden", "true")
            loginModal.classList.add("modal", "fade")

            // create login form
            var loginDiv = document.createElement("div")
            loginModal.appendChild(loginDiv)
            loginDiv.classList.add("modal-dialog", "modal-login")
            loginDiv.setAttribute("role", "document")
            // - modal content
            var modalContent = document.createElement("div")
            loginDiv.appendChild(modalContent)
            modalContent.classList.add("modal-content")

            // -- modal header
            var modalHeader = document.createElement("div")
            modalContent.appendChild(modalHeader)
            modalHeader.classList.add("modal-header")
            // --- close button
            var modalCloseButton = document.createElement("button")
            modalHeader.appendChild(modalCloseButton)
            modalCloseButton.setAttribute("type", "button")
            modalCloseButton.setAttribute("data-dismiss", "modal")
            modalCloseButton.setAttribute("aria-label", "Close")
            modalCloseButton.classList.add("close")
            modalCloseButton.innerHTML = '<span aria-hidden="true">×</span>'

            // -- modal body
            var modalBody = document.createElement("div")
            modalContent.appendChild(modalBody)
            modalBody.classList.add("modal-body", "text-center")
            // --- login form
            var loginForm = document.createElement("form")
            modalBody.appendChild(loginForm)
            loginForm.classList.add("form-signin")
            // ---- login form fieldset
            var fieldset = document.createElement("fieldset")
            loginForm.appendChild(fieldset)
            // ----- blueweather icon
            var loginFormIcon = document.createElement("img")
            fieldset.appendChild(loginFormIcon)
            loginFormIcon.width = "72"
            loginFormIcon.height = "72"
            loginFormIcon.src = "img/icon.png"
            loginFormIcon.alt = ""
            loginFormIcon.classList.add("mb-4")
            // ----- 'Please sign in' text
            var loginFormHeadline = document.createElement("h1")
            fieldset.append(loginFormHeadline)
            loginFormHeadline.classList.add("h3", "mb-3", "font-weight-normal")
            loginFormHeadline.innerHTML = "Please sign in"
            // ----- login failed alert
            var alert = document.createElement("div")
            fieldset.append(alert)
            alert.id = "loginFormLoginFailedAlert"
            alert.appear = function() {
                alert.innerHTML = '<div class="alert alert-danger alert-dismissible fade show" role="alert">Invalid username or password<button type="button" class="close" data-dismiss="alert" aria-label="Close"><span aria-hidden="true">&times;</span></button></div>'
            }
            // ----- username input
            var usernameInputGroup = document.createElement("div")
            fieldset.appendChild(usernameInputGroup)
            usernameInputGroup.classList.add("form-group", "input-group")
            usernameInputGroup.innerHTML = '<div class="input-group-prepend"><div class="input-group-text"><span data-feather="user"></span></div></div><input type="text" class="form-control" id="loginFormUsernameInput" placeholder="Username"> </div>'
            // ----- password input
            var passwordInputGroup = document.createElement("div")
            fieldset.appendChild(passwordInputGroup)
            passwordInputGroup.classList.add("form-group", "input-group")
            passwordInputGroup.innerHTML = '<div class="input-group-prepend"><div class="input-group-text"><span data-feather="lock"></span></div></div><input type="password" class="form-control" id="loginFormPasswordInput" placeholder="Password"> </div>'
            // ----- 'remember me' checkbox
            var rememberCheckboxContainer = document.createElement("div")
            rememberCheckboxContainer.classList.add("checkbox", "mb-3")
            rememberCheckboxContainer.innerHTML = '<label> <input id="loginFormRememberMeChekbox" type="checkbox"> Remember me </label>'
            // ----- 'sign in' button
            var signInButton = document.createElement("button")
            modalBody.appendChild(signInButton)
            signInButton.id = "loginFormSignInButton"
            signInButton.type = "submit"
            signInButton.classList.add("btn", "btn-lg", "btn-primary", "btn-block")
            signInButton.innerHTML = "Sign in"
            signInButton.setLoading = function() {
                signInButton.disabled = true
                signInButton.innerHTML = '<span class="spinner-border spinner-border-sm" role="status" aria-hidden="true"></span> Signing in...'
            }
            signInButton.setNormal = function() {
                signInButton.disabled = false
                signInButton.innerHTML = 'Sign in'
            }
            signInButton.onclick = function() {
                signInButton.setLoading()
                var username = document.getElementById("loginFormUsernameInput").value
                var password = document.getElementById("loginFormPasswordInput").value
                thisObject.login(true, username, password, function(loginSuccess){
                    if(!loginSuccess){
                        alert.appear()
                    }
                    signInButton.setNormal()
                })
            }
            // ----------

            parent.appendChild(loginModal)
        }
        else {
            
            this.log("logged in", 3)
            profileObject.classList.add("dropdown")

            // create profile picture button
            var profileButton = document.createElement("a")
            profileObject.appendChild(profileButton)
            profileButton.id = "userDropdown"
            profileButton.style = "padding: 0;"
            profileButton.href = "#"
            profileButton.setAttribute("role", "button")
            profileButton.classList.add("nav-link", "dropdown-toggle")
            profileButton.setAttribute("data-toggle", "dropdown")
            profileButton.setAttribute("aria-haspopup", "true")
            profileButton.setAttribute("aria-expanded", "false")

            // create profile image inside button
            var profileImage = document.createElement("img")
            profileButton.appendChild(profileImage)
            profileImage.height="30"
            profileImage.src = "img/user.png"
            profileImage.classList.add("img-profile", "rounded-circle")

            // create dropdown menu
            var profileDropdown = document.createElement("div")
            profileObject.appendChild(profileDropdown)
            profileDropdown.classList.add("dropdown-menu", "dropdown-menu-right")
            profileDropdown.setAttribute("aria-labelledby", "userDropdown")

            // fill the dropdown menu
            function createDropdownMenuElement(icon, text) {
                // create element
                var elem = document.createElement("a")
                elem.classList.add("dropdown-item")
                elem.href = "#"
                
                // create icon
                var iconSpan = document.createElement("span")
                elem.appendChild(iconSpan)
                iconSpan.setAttribute("data-feather", icon)

                // create text
                var text = document.createTextNode(text)
                elem.appendChild(text)

                return elem
            }

            function createDropdownSeparator() {
                var sep = document.createElement("div")
                sep.classList.add("dropdown-divider")
                return sep
            }
            
            var header = document.createElement("div")
            header.classList.add("dropdown-item")
            header.innerHTML = "<h6><b>" + this.session.user.realName + "</b></h6>@" + this.session.user.username
            profileDropdown.appendChild(header)
            profileDropdown.appendChild(createDropdownSeparator())
            profileDropdown.appendChild(createDropdownMenuElement("settings", " Settings"))
            profileDropdown.appendChild(createDropdownSeparator())
            profileDropdown.appendChild(createDropdownMenuElement("log-out", " Log out"))

        }

        feather.replace()
    }

    // --------------------
    // - helper functions -
    // --------------------

    getCookie(name) {
        var value = "; " + document.cookie;
        var parts = value.split("; " + name + "=");
        if (parts.length == 2) return parts.pop().split(";").shift();
    }

    findGetParameter(parameterName) {
        var result = null,
            tmp = [];
        location.search
            .substr(1)
            .split("&")
            .forEach(function (item) {
                tmp = item.split("=");
                if (tmp[0] === parameterName) result = decodeURIComponent(tmp[1]);
            });
        return result;
    }

    log(text, level){
        // levels:
        // 0: error
        // 1: warning
        // 2: info
        // 3: debug

        var preString = "[BlueWeather]"

        switch(level){
            case 0:
                preString += "[error] "
                console.error(preString+text)
                break
            case 1:
                preString += "[warining] "
                console.warn(preString+text)
                break
            case 2:
                preString += "[info] "
                console.log(preString+text)
                break
            case 3:
                preString += "[debug] "
                console.debug(preString+text)
        }
    }
}
