调用event.preventDefault()后页面仍重载的问题求助
注册页面提交后页面重载问题排查与解决
问题描述
开发注册页面时,点击未包裹在<form>标签内的提交按钮,已调用event.preventDefault()但页面仍重载,错误提示框仅显示0.2秒就消失;尝试将输入框放入<form>并绑定submit事件,问题依旧。
相关代码
HTML代码
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta http-equiv="X-UA-Compatible" content="IE=edge"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>Sign Up</title> <link rel="stylesheet" type="text/css" href="../../styles/signUp.css"> </head> <body> <nav id="nav"> <div id="logo">Studentship</div> </nav> <div class="container"> <div class="left-section"> <h2>For students...</h2> <div id="Serror-message"""></div> <div id="inputContainer"> <input type="text" id="Susername" name="username" placeholder="Username (What People See)" required> <input type="password" id="Spassword" name="password" placeholder="Password" required> <input type="number" id="Sgrade" name="grade" min=1 max=12 placeholder="Grade" required> <input type="number" id="Szipcode" name="zipcode" min=00501 max=99950 placeholder="Zip-Code" required> <button id="Ssubmit">Join</button> </div> </div> <div class="right-section"> <h2>For companies...</h2> <div id="Cerror-message" style="display: none;"></div> <div id="inputContainer"> <input type="text" id="Cname" name="name" placeholder="Official Company Name" required> <input type="password" id="Cpassword" name="password" placeholder="Password" required> <input type="number" id="Czipcode" name="zipcode" placeholder="Zip-Code" required> <!-- TODO: Add Categories for Industries --> <label for="Industry">Industry</label> <select id="Cindustry" name="Industry"> <option value="Research">Research</option> <option value="Tutoring">Tutoring</option> </select> <button id="Csubmit">Join</button> </div> </div> </div> </body> <script src="../../scripts/signUp.js"></script> </html>
JavaScript代码
// Praneeth O - 03/06/2023 // Code for Student const studentButton = document.getElementById('Ssubmit'); const studErrorBox = document.getElementById('Serror-message'); studentButton.addEventListener('click', event => { event.preventDefault(); var formData = { username: document.getElementById("Susername").value, password: document.getElementById("Spassword").value, grade: document.getElementById("Sgrade").value, zip: document.getElementById("Szipcode").value, role: true, industry: "null" } const url = 'http://localhost:8000/users'; // Replace with your API endpoint URL try { fetch(url, { method: 'POST', body: JSON.stringify(formData), headers: { 'Content-Type': 'application/json' } }) .then((response) => { if(response.status === 201) { console.log("User Created Successfully"); window.location.href = "../dashboard.html"; } else if(response.status === 409) { studErrorBox.innerHTML = "Username already exists :)"; } else if(response.status === 401) { studErrorBox.innerHTML = "Make sure to enter all of your info!" } else { throw new Error("Something Went Wrong"); } studentButton.disabled = true; }); } catch (error) { studErrorBox.innerHTML = "Something went wrong. Contact us with details!"; } })
解决方案
1. 修复HTML语法错误
HTML中存在一处多余双引号的错误,会导致DOM元素识别异常:
<!-- 错误代码 --> <div id="Serror-message"""></div> <!-- 修正后 --> <div id="Serror-message"></div>
2. 显式设置按钮类型为button
浏览器默认会将未指定类型的按钮视为submit类型,即使不在<form>内也可能触发页面提交。给按钮添加type="button"彻底禁用默认提交行为:
<button id="Ssubmit" type="button">Join</button> <button id="Csubmit" type="button">Join</button>
3. 完善fetch错误处理逻辑
原代码的try/catch无法捕获HTTP错误状态码(仅捕获请求发送失败的异常),需要在then中完整处理响应,并在错误时恢复按钮可用性:
studentButton.addEventListener('click', event => { event.preventDefault(); const formData = { username: document.getElementById("Susername").value, password: document.getElementById("Spassword").value, grade: document.getElementById("Sgrade").value, zip: document.getElementById("Szipcode").value, role: true, industry: "null" }; const url = 'http://localhost:8000/users'; fetch(url, { method: 'POST', body: JSON.stringify(formData), headers: { 'Content-Type': 'application/json' } }) .then(async (response) => { studentButton.disabled = true; if(response.status === 201) { console.log("User Created Successfully"); window.location.href = "../dashboard.html"; } else if(response.status === 409) { studErrorBox.innerHTML = "用户名已存在 :)"; } else if(response.status === 401) { studErrorBox.innerHTML = "请填写所有必填信息!"; } else { const errorDetail = await response.text(); throw new Error(`请求失败: ${errorDetail}`); } }) .catch (error) { studErrorBox.innerHTML = "出现错误,请联系我们反馈详情!"; console.error(error); studentButton.disabled = false; // 错误时恢复按钮可点击 }; });
4. 若使用<form>标签的补充处理
如果后续选择用<form>包裹输入框,需绑定form的submit事件而非按钮的click事件,并在事件中阻止默认行为:
<form id="studentForm"> <!-- 学生输入框 --> <button type="submit">Join</button> </form>
document.getElementById('studentForm').addEventListener('submit', event => { event.preventDefault(); // 执行提交逻辑 });
内容的提问来源于stack exchange,提问作者PraneethO
相关产品推荐
相关产品推荐

