Golang如何实现无页面加载的用户名检查

Golang如何实现无页面加载的用户名检查 我希望实现以下场景: 当按下登录按钮时,无需加载页面,即可检查数据库中是否存在该用户名。如果找到用户名,则通过加载页面来检查密码,并根据密码是否匹配进行后续操作。但如果找不到用户名,它将在登录页面(用户名文本框下方)显示错误信息

目前我已经完成了以下工作:

main.go

package main

import (
	"html/template"
	"fmt"
	"net/http"
	"github.com/gorilla/mux"
)

var tpl *template.Template

func init() {
	tpl = template.Must(template.ParseGlob("frontEnd/*.html"))
}

func Index(w http.ResponseWriter, r *http.Request) {
	w.Header().Set("Content-Type", "text/html")
	tpl.ExecuteTemplate(w, "index.html", nil)
}

func Login(w http.ResponseWriter, r *http.Request) {
	w.Header().Set("Content-Type", "text/html")
	tpl.ExecuteTemplate(w, "login.html", nil)
}
func LoginCheck(w http.ResponseWriter, r *http.Request) {
	w.Header().Set("Content-Type", "text/html")

	if r.Method != "POST" {
		http.Redirect(w, r, "/", http.StatusSeeOther)
		return
	}

	//username := r.FormValue("username")
	//password := r.FormValue("password")

	// Here checking will be done with database
}
func main() {
	r := mux.NewRouter()

	//just a message for ensuring that local server is running
	fmt.Println("Local Server is running...")

	//for serving perspective pages
	r.HandleFunc("/", Index)
	r.HandleFunc("/login", Login)
	r.HandleFunc("/loginCheck", LoginCheck)

	//for localhost server
	http.ListenAndServe(":8080", r)
}

登录表单:

<form class="loginForm" action="/loginCheck" method="POST">
    <h1>LOGIN</h1>
    <div>
        <input type="text" name="username" value="" placeholder="Username" required>
        <span class="err"></span>
    </div>
    <div>
        <input type="password" name="password" placeholder="Password" required>
        <span class="err"></span>
    </div>
    <div>
        <input type="submit" value="Login" name="">
    </div>
    <span><a href="/reset">Forgot Password?</a></span>
</form>

我应该编写什么样的JavaScript代码,或者还需要做些什么?


更多关于Golang如何实现无页面加载的用户名检查的实战教程也可以访问 https://www.itying.com/category-94-b0.html

2 回复

可以在模板中围绕你的错误 span 添加一个动作:

{{if .Err}}<span class="err">{{.Err}}</span>{{end}}

然后在 LoginCheck 中:

var err error
// 检查用户是否存在于数据库中,
// 如果有错误则设置 err
// ...
tpl.ExecuteTemplate(w, "login.html", struct{ Err error}{ err })

更多关于Golang如何实现无页面加载的用户名检查的实战系列教程也可以访问 https://www.itying.com/category-94-b0.html


要实现无页面加载的用户名检查,你需要使用AJAX技术。以下是完整的解决方案:

1. 修改后端处理逻辑

首先更新你的 main.go,添加用户名检查的API端点:

package main

import (
    "encoding/json"
    "html/template"
    "fmt"
    "net/http"
    "github.com/gorilla/mux"
)

var tpl *template.Template

func init() {
    tpl = template.Must(template.ParseGlob("frontEnd/*.html"))
}

func Index(w http.ResponseWriter, r *http.Request) {
    w.Header().Set("Content-Type", "text/html")
    tpl.ExecuteTemplate(w, "index.html", nil)
}

func Login(w http.ResponseWriter, r *http.Request) {
    w.Header().Set("Content-Type", "text/html")
    tpl.ExecuteTemplate(w, "login.html", nil)
}

// 新增:用户名检查API
func CheckUsername(w http.ResponseWriter, r *http.Request) {
    w.Header().Set("Content-Type", "application/json")
    
    if r.Method != "POST" {
        json.NewEncoder(w).Encode(map[string]interface{}{
            "exists": false,
            "error": "Invalid request method",
        })
        return
    }
    
    username := r.FormValue("username")
    
    // 这里模拟数据库检查,实际应用中需要连接数据库
    // 示例:假设 "admin" 和 "user" 是存在的用户名
    exists := false
    if username == "admin" || username == "user" {
        exists = true
    }
    
    response := map[string]interface{}{
        "exists": exists,
        "username": username,
    }
    
    json.NewEncoder(w).Encode(response)
}

func LoginCheck(w http.ResponseWriter, r *http.Request) {
    w.Header().Set("Content-Type", "text/html")
    
    if r.Method != "POST" {
        http.Redirect(w, r, "/", http.StatusSeeOther)
        return
    }
    
    username := r.FormValue("username")
    password := r.FormValue("password")
    
    // 这里进行完整的登录验证(用户名和密码)
    // 实际应用中需要连接数据库验证
    if username == "admin" && password == "password123" {
        // 登录成功,重定向到主页或其他页面
        http.Redirect(w, r, "/dashboard", http.StatusSeeOther)
    } else {
        // 登录失败,返回错误信息
        data := map[string]string{
            "Error": "Invalid username or password",
        }
        tpl.ExecuteTemplate(w, "login.html", data)
    }
}

func main() {
    r := mux.NewRouter()
    
    fmt.Println("Local Server is running...")
    
    r.HandleFunc("/", Index)
    r.HandleFunc("/login", Login)
    r.HandleFunc("/loginCheck", LoginCheck)
    r.HandleFunc("/check-username", CheckUsername) // 新增用户名检查端点
    
    http.ListenAndServe(":8080", r)
}

2. 修改HTML表单,添加JavaScript

更新你的登录表单HTML:

<!DOCTYPE html>
<html>
<head>
    <title>Login</title>
    <style>
        .err {
            color: red;
            font-size: 12px;
            display: block;
            margin-top: 5px;
        }
        .hidden {
            display: none;
        }
    </style>
</head>
<body>
    <form class="loginForm" id="loginForm" action="/loginCheck" method="POST">
        <h1>LOGIN</h1>
        <div>
            <input type="text" name="username" id="username" value="" placeholder="Username" required>
            <span class="err" id="usernameError"></span>
        </div>
        <div>
            <input type="password" name="password" id="password" placeholder="Password" required>
            <span class="err" id="passwordError"></span>
        </div>
        <div>
            <input type="submit" value="Login" id="loginButton">
        </div>
        <span><a href="/reset">Forgot Password?</a></span>
    </form>

    <script>
        document.addEventListener('DOMContentLoaded', function() {
            const loginForm = document.getElementById('loginForm');
            const usernameInput = document.getElementById('username');
            const usernameError = document.getElementById('usernameError');
            const passwordInput = document.getElementById('password');
            const loginButton = document.getElementById('loginButton');
            
            // 用户名输入框失去焦点时检查
            usernameInput.addEventListener('blur', function() {
                checkUsername();
            });
            
            // 表单提交前验证
            loginForm.addEventListener('submit', function(e) {
                e.preventDefault(); // 阻止默认提交
                
                // 先检查用户名
                checkUsername().then(usernameExists => {
                    if (usernameExists) {
                        // 用户名存在,提交表单进行密码验证
                        loginForm.submit();
                    } else {
                        // 用户名不存在,显示错误
                        usernameError.textContent = 'Username does not exist';
                    }
                });
            });
            
            function checkUsername() {
                const username = usernameInput.value.trim();
                
                if (!username) {
                    usernameError.textContent = 'Username is required';
                    return Promise.resolve(false);
                }
                
                usernameError.textContent = '';
                
                // 创建FormData对象
                const formData = new FormData();
                formData.append('username', username);
                
                // 发送AJAX请求
                return fetch('/check-username', {
                    method: 'POST',
                    body: formData
                })
                .then(response => response.json())
                .then(data => {
                    if (!data.exists) {
                        usernameError.textContent = 'Username does not exist';
                        passwordInput.value = ''; // 清空密码框
                    } else {
                        usernameError.textContent = '';
                    }
                    return data.exists;
                })
                .catch(error => {
                    console.error('Error:', error);
                    usernameError.textContent = 'Error checking username';
                    return false;
                });
            }
            
            // 实时检查用户名(可选)
            let debounceTimer;
            usernameInput.addEventListener('input', function() {
                clearTimeout(debounceTimer);
                const username = usernameInput.value.trim();
                
                if (username.length >= 3) { // 至少3个字符才开始检查
                    debounceTimer = setTimeout(() => {
                        checkUsername();
                    }, 500); // 防抖500ms
                } else {
                    usernameError.textContent = '';
                }
            });
        });
    </script>
</body>
</html>

3. 如果需要更实时的检查(按键时检查)

添加以下JavaScript代码实现按键时检查:

// 在之前的script标签内添加
usernameInput.addEventListener('keyup', function(e) {
    if (e.key === 'Enter') return;
    
    const username = usernameInput.value.trim();
    
    if (username.length >= 3) {
        clearTimeout(debounceTimer);
        debounceTimer = setTimeout(() => {
            checkUsername();
        }, 300);
    } else {
        usernameError.textContent = username.length > 0 ? 
            'Username must be at least 3 characters' : '';
    }
});

这个实现提供了:

  1. 用户名输入框失去焦点时检查
  2. 表单提交前验证用户名是否存在
  3. 可选的实时输入检查(防抖优化)
  4. 用户名不存在时显示错误信息而不提交表单
  5. 用户名存在时才提交表单进行密码验证
回到顶部