我有一个简单的表格,需要输入一个 4 位数的 PIN 码。但是,我还想在用户再次返回网站时使用 JS cookie 自动填充该 PIN 码。
JS:
function loginCheck() {
var pinCode = document.getElementById("pinCode").value;
if (pinCode.match(/^[0-9]+$/) != null) {
if (pinCode.length == 4) {
function setCookie(cname, cvalue) {
document.cookie = cname + "=" + cvalue + ";"
}
function getCookie(cname) {
var name = cname + "=";
var ca = document.cookie.split(';');
for(var i = 0; i < ca.length; i++) {
var c = ca[i];
while (c.charAt(0) == ' ') {
c = c.substring(1);
}
if (c.indexOf(name) == 0) {
return c.substring(name.length, c.length);
}
}
return "";
}
function checkCookie() {
var pinCode = document.getElementById("pinCode").value;
var userPIN = getCookie("userPIN");
if (userPIN != "") {
pinCode.value = userPIN;
} else {
setCookie("username", userPIN);
}
}
checkCookie();
} else {
document.getElementById("rightorwrong").innerHTML = "Not 4 digits!";
}
} else {
document.getElementById("rightorwrong").innerHTML = "Not a number!";
}
}
HTML:
<div id = "validation">
<form id = "validationForm" target = "frame">
<fieldset>
<label for = "pass">Password:</label><br />
<input type = "text" id = "pass" name = "pass" /><br />
<label for = "pinCode">4-digit PIN:</label><br />
<input type = "text" id = "pinCode" name = "pinCode" /><br />
<input type = "submit" value="Log In" onclick = "loginCheck()" />
</fieldset>
</form>
</div>
<p id = "rightorwrong"></p>
我知道这段代码有一些错误。
- 在
checkCookie()
函数中,如果用户存储了 cookie,那么我不完全确定如何检索他们首先输入的 PIN。 - 在函数内部定义函数,并通过简单地执行
checkCookie();
调用它们,而不做其他任何事情,通常是不好的做法。 - 当我运行
checkCookie();
时,它只执行if
语句的第一部分,而不执行第二部分。我不确定为什么,也想不通。 - 代码一般可能有一些错误。我从 here 修改了一个 cookies 脚本但它似乎不起作用。
我对 cookie 的概念还很陌生,并且仍在努力学习它们。分步解释会更有帮助。
非常感谢您的帮助,TIA。
最佳答案
对于 cookie,我使用带有 set/getVal 方法的“simpleCookie”对象来读取或保存 cookie。
例如:
simpleCookie.setVal( 'my cookie', 'ab/kjf;c', 3 )
let valueX = simpleCookie.getVal('my cookie')) // return 'ab/kjf;c'
simpleCookie.setVal( 'my cookie', '', -1) remove the cookie
此对象是通过 IIEF function 实现的, 我强烈建议您使用 mozilla 文档
由于存在自动表单验证,我不再使用文本框来指示输入错误,但我稍微改变了它的“正常”用法,因为我发现它非常有限制,正如您将在我的代码中看到的那样。
在您的问题基础上,您只需找到输入的名称与可能的同名 cookie 之间的匹配项,然后在表单有效时保存此 cookie。
哦,我还放了一些 css 来简化编写 html(不再需要 <br>
)
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>login form</title>
<style>
fieldset { margin: 1em; width: 15em; }
fieldset * { display: block; float: left; clear: both; margin-top: 0.2em; }
fieldset label { margin-top: 0.7em; }
fieldset button { margin-top: 2em; }
fieldset button:last-of-type { clear: none; float: right; }
</style>
</head>
<body>
<form id="login-form" action="">
<fieldset>
<label>Name:</label>
<input type="text" name="name" autocomplete="off" pattern="[A-Za-z0-9]{1,20}">
<label>Password:</label>
<input type="password" name="pass" pattern="[A-Za-z0-9]{1,20}">
<label>4-digit PIN:</label>
<input type="text" name="pinCode" autocomplete="off" pattern="[0-9]{4}">
<button type="reset">clear</button>
<button type="submit">Log In</button>
</fieldset>
</form>
<script src="simpleCoolie.js"></script> <!-- the cookie object (IIFE) -->
<script src="login_form.js"></script>
</body>
</html>
simpleCoolie.js:
// the cookie object (IIFE)
const simpleCookie = (function()
{
const OneDay_ms = 24 *60 *60 *1000 // one Day in milliseconds
return {
setVal:(cName, cValue='', exDays=10)=> // 10 days is default cookie recovery,
{ // negative value remove the cookie
cName = encodeURIComponent(cName.trim())
cValue = encodeURIComponent(cValue.trim())
if (cName)
{
let dte = new Date()
dte.setTime(dte.getTime() + (exDays *OneDay_ms))
document.cookie = `${cName}=${cValue};expires=${dte.toUTCString()};SameSite=Strict;path=/`
} }
, getVal:cName=>
{
cName = encodeURIComponent(cName.trim())
let xCookie = document.cookie.split('; ').find(x=>x.startsWith(`${cName}=`))
return xCookie ? decodeURIComponent(xCookie.split('=')[1]) : ''
} }
})()
登录表单.js:
const formLogin = document.getElementById('login-form')
, msgErrorDuration = 5000
, checkInputs =
[...formLogin.querySelectorAll('input[pattern]')]
.map(el=>
{
let pattern = el.pattern
el.removeAttribute('pattern')
return { name:el.name, pattern }
});
// generic set checking for report validyty
const getCheckingValidity=(formElement, patternValue)=>
{
formElement.pattern = patternValue
formElement.required = true
return formElement.reportValidity()
}
// generic checking remove after delay
const unCheckElement=(formElement,isOK)=>
{
formElement.removeAttribute('pattern')
formElement.required = false
if(!isOK)
{
formElement.setCustomValidity('')
if(document.activeElement === formElement ) // bugg fix: Firefox doesnt remove error message after delay
{ // (other browser do)
formElement.blur(); // double flip focus
formElement.focus(); // --> will remove message bubble
}
}
}
// client-side form validation mecanism to get error message for each input
formLogin.name.oninvalid=_=>
{
formLogin.name.setCustomValidity('Please enter a name')
setTimeout(unCheckElement, msgErrorDuration, formLogin.name, false)
}
formLogin.pass.oninvalid=_=>
{
formLogin.pass.setCustomValidity("can't do anything without password !")
setTimeout(unCheckElement, msgErrorDuration, formLogin.pass, false)
}
formLogin.pinCode.oninvalid=_=>
{
if (formLogin.pinCode.value==='')
{ formLogin.pinCode.setCustomValidity("PIN code can't be empty !") }
else
{ formLogin.pinCode.setCustomValidity('PIN code must be 4 digits') }
setTimeout(unCheckElement, msgErrorDuration, formLogin.pinCode, false)
}
formLogin.onsubmit=e=>
{
let validForm = true
for (let Elm of checkInputs)
{
validForm = validForm && getCheckingValidity(formLogin[Elm.name], Elm.pattern )
if (validForm)
{ unCheckElement(formLogin[Elm.name], true) }
else break
}
if (validForm)
{ simpleCookie.setVal( formLogin.name.value, formLogin.pinCode.value ) }
else
{ e.preventDefault() } // disable form submiting
}
formLogin.name.oninput=()=> // check for cookie pin code on name
{
formLogin.pinCode.value = simpleCookie.getVal(formLogin.name.value)
}
2009年, session /localStorage到了,可以代替cookies,特别适合这种用途。
为了不必重做之前的所有逻辑,我在这里创建了一个名为 pseudoCookie 的模块,它实际上使用了 localStorage
这里是完整的测试代码:
// the pseudo cookie object (IIFE)
const pseudoCookie = (function() // use localStorage
{
return {
setVal:(cName, cValue='', exDays=10)=> // negative value remove the value in localstorage
{ // the values are kept until your browser or your system crashes
cName = encodeURIComponent(cName.trim())
cValue = encodeURIComponent(cValue.trim())
if (cName) {
if (exDays < 0) localStorage.removeItem(cName)
else localStorage.setItem(cName, cValue)
} }
, getVal:cName=>
{
cName = encodeURIComponent(cName.trim())
let xCookie = localStorage.getItem(cName)
return xCookie ? decodeURIComponent(xCookie) : ''
} }
})()
以及在 JS 中更改的部分:
formLogin.onsubmit=e=>
{
let validForm = true
for (let Elm of checkInputs)
{
validForm = validForm && getCheckingValidity(formLogin[Elm.name], Elm.pattern )
if (validForm)
{ unCheckElement(formLogin[Elm.name], true) }
else break
}
if (validForm)
{ pseudoCookie.setVal( formLogin.name.value, formLogin.pinCode.value ) }
else
{ e.preventDefault() } // disable form submiting
}
formLogin.name.oninput=()=> // check for cookie pin code on name
{
formLogin.pinCode.value = pseudoCookie.getVal(formLogin.name.value)
}
关于javascript - 使用 cookie 启用 4 位密码自动填充,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/63633918/