如何通过AJAX接口检测MongoDB Schema中用户名是否已存在
注册表单用户名实时查重功能故障排查与修复
问题描述
开发注册表单时,希望实现用户输入用户名时实时检查MongoDB中该用户名是否已存在,但当前功能无法正常运行。
现有代码
表单HTML代码
<form class="needs-validation" action="/register" method="POST" novalidate> <div class="text-center mb-3"> <p class="lead">Welcome to the team! We just need a few things to get started.</p> <div class="row"> <div class="col-md-6 mb-4"> <div class="form-outline"> <input type="text" id="first_name" name="first_name" class="form-control" required /> <label class="form-label" for="first_name" >First name</label > <div class="valid-feedback">Looks good!</div> <div class="invalid-feedback">Thats not right</div> </div> </div> <div class="col-md-6 mb-4"> <div class="form-outline"> <input type="text" id="last-name" name="last-name" class="form-control" required /> <label class="form-label" for="last-name" >Last name</label > <div class="valid-feedback">Looks good!</div> <div class="invalid-feedback">Thats not right</div> </div> </div> </div> <!-- Email input --> <div class="form-outline mb-4"> <input type="email" id="register_email" name="register_email" class="form-control" required /> <label class="form-label" for="register_email">Email</label> <div class="valid-feedback">Looks good!</div> <div class="invalid-feedback">Thats not right</div> </div> <div class="text-center mb-3"> <div class="form-outline mb-4"> <input type="text" id="register_username" name="register_username" class="form-control" placeholder="enter your username" required /> <label class="form-label" for="register_username">Username</label> <div id="username-check"></div> </div> <!-- Password input --> <div class="form-outline mb-4"> <input type="password" id="register_password" name="register_password" class="form-control" required/> <label class="form-label" for="register_password">Password</label> </div> </div> <!-- Submit button --> <div class="text-center"> <button type="submit" id="register" class="btn btn-lg btn-rounded bg-insider link-dark mb-3 fw-bold" disabled> Lets Go! <i class="fa-solid fa-gauge-max"></i> </button> </div> </form>
前端AJAX脚本
$('#register_username').on('keyup', function () { $.get('/usercheck?username=' + $(this).val().toLowerCase(), function (response) { $('#username-check').text(response.message); console.log('') var btn = document.getElementById('register'); btn.disabled = true; if ($('#username-check').html() === "user exists") { $('#username-check').text('username not available').css('color', 'red'); } else { console.log($('#register_username').val()) $('#username-check').text('username is available').css('color', 'green'); btn.disabled = false; } }) });
后端Express路由代码
var express = require("express"), router = express.Router(), passport = require("passport"), User = require("../models/user"); router.get('/usercheck', function(req, res) { console.log(req.query); User.findOne({username: req.query.register_username}, function(err, username){ if(err) { console.log(err); } var message; if(username) { console.log(username); message = "user exists"; console.log(message); } else { message= "user doesn't exist"; console.log(message); } res.json({message: message}); }); }); module.exports = router;
MongoDB User Schema代码
var mongoose = require("mongoose"); var passportLocalMongoose = require("passport-local-mongoose"); var UserSchema = new mongoose.Schema({ username: String, password: String, email: String, isAdmin: { type: Boolean, default: false } }); UserSchema.plugin(passportLocalMongoose); module.exports = mongoose.model("User",UserSchema);
问题排查
- 后端参数获取错误:前端AJAX请求传递的查询参数是
username,但后端路由错误使用req.query.register_username获取参数,导致查询条件为空,无法匹配数据库中的用户名。 - 前端逻辑冗余且易出错:先将后端返回消息写入DOM,再读取DOM内容判断,不仅冗余,还可能因DOM渲染延迟导致判断错误;应直接使用后端返回的
response.message做逻辑判断。 - 错误处理缺失:后端
findOne回调仅打印错误,未返回错误响应给前端;前端AJAX也未处理请求失败的情况。 - 大小写一致性问题:前端将用户名转为小写发送,但数据库中用户名可能大小写混合,未统一处理会导致查重结果不准确。
修复方案
修正后端路由代码
var express = require("express"), router = express.Router(), passport = require("passport"), User = require("../models/user"); router.get('/usercheck', function(req, res) { console.log(req.query); // 修复:使用正确的查询参数username User.findOne({username: req.query.username}, function(err, foundUser){ if(err) { console.log(err); // 新增:返回服务器错误响应 return res.status(500).json({message: "服务器错误"}); } var message; if(foundUser) { console.log(foundUser); message = "user exists"; console.log(message); } else { message= "user doesn't exist"; console.log(message); } res.json({message: message}); }); }); module.exports = router;
修正前端AJAX脚本
$('#register_username').on('keyup', function () { const username = $(this).val().toLowerCase(); // 新增:避免空输入时发送请求 if (!username.trim()) { $('#username-check').text(''); $('#register').prop('disabled', true); return; } $.get('/usercheck?username=' + username, function (response) { const btn = $('#register'); // 修复:直接使用后端返回的response.message判断,避免依赖DOM if (response.message === "user exists") { $('#username-check').text('用户名不可用').css('color', 'red'); btn.prop('disabled', true); } else { $('#username-check').text('用户名可用').css('color', 'green'); btn.prop('disabled', false); } }) // 新增:处理AJAX请求失败的情况 .fail(function() { $('#username-check').text('检查失败,请稍后重试').css('color', 'orange'); $('#register').prop('disabled', true); }); });
优化User Schema(可选)
为确保用户名唯一性并统一大小写,可在Schema中添加配置:
var mongoose = require("mongoose"); var passportLocalMongoose = require("passport-local-mongoose"); var UserSchema = new mongoose.Schema({ username: { type: String, unique: true, required: true, // 新增:自动将用户名转为小写存储,确保查重不区分大小写 lowercase: true }, password: String, email: String, isAdmin: { type: Boolean, default: false } }); UserSchema.plugin(passportLocalMongoose); module.exports = mongoose.model("User",UserSchema);
内容的提问来源于stack exchange,提问作者Andrew Buccellato
相关产品推荐
相关产品推荐

