password-first started
This commit is contained in:
parent
66abcc0d43
commit
3f999b9258
5
app.html
5
app.html
@ -5,6 +5,11 @@
|
||||
<title>Document</title>
|
||||
</head>
|
||||
<body>
|
||||
<script>
|
||||
/// burn vanjs into codebase
|
||||
{let e,t,r,o,n,s,l,i,f,h,w,a,u,d,c,_,S,g,y,b,m,v,j,x,O;l=Object.getPrototypeOf,f={},h=l(i={isConnected:1}),w=l(l),a=(e,t,r,o)=>(e??(o?setTimeout(r,o):queueMicrotask(r),new Set)).add(t),u=(e,t,o)=>{let n=r;r=t;try{return e(o)}catch(e){return console.error(e),o}finally{r=n}},d=e=>e.filter(e=>e.t?.isConnected),c=e=>n=a(n,e,()=>{for(let e of n)e.o=d(e.o),e.l=d(e.l);n=s},1e3),_={get val(){return r?.i?.add(this),this.rawVal},get oldVal(){return r?.i?.add(this),this.h},set val(o){r?.u?.add(this),o!==this.rawVal&&(this.rawVal=o,this.o.length+this.l.length?(t?.add(this),e=a(e,this,x)):this.h=o)}},S=e=>({__proto__:_,rawVal:e,h:e,o:[],l:[]}),g=(e,t)=>{let r={i:new Set,u:new Set},n={f:e},s=o;o=[];let l=u(e,r,t);l=(l??document).nodeType?l:new Text(l);for(let e of r.i)r.u.has(e)||(c(e),e.o.push(n));for(let e of o)e.t=l;return o=s,n.t=l},y=(e,t=S(),r)=>{let n={i:new Set,u:new Set},s={f:e,s:t};s.t=r??o?.push(s)??i,t.val=u(e,n,t.rawVal);for(let e of n.i)n.u.has(e)||(c(e),e.l.push(s));return t},b=(e,...t)=>{for(let r of t.flat(1/0)){let t=l(r??0),o=t===_?g(()=>r.val):t===w?g(r):r;o!=s&&e.append(o)}return e},m=(e,t,...r)=>{let[{is:o,...n},...i]=l(r[0]??0)===h?r:[{},...r],a=e?document.createElementNS(e,t,{is:o}):document.createElement(t,{is:o});for(let[e,r]of Object.entries(n)){let o=t=>t?Object.getOwnPropertyDescriptor(t,e)??o(l(t)):s,n=t+","+e,i=f[n]??=o(l(a))?.set??0,h=e.startsWith("on")?(t,r)=>{let o=e.slice(2);a.removeEventListener(o,r),a.addEventListener(o,t)}:i?i.bind(a):a.setAttribute.bind(a,e),u=l(r??0);e.startsWith("on")||u===w&&(r=y(r),u=_),u===_?g(()=>(h(r.val,r.h),a)):h(r)}return b(a,i)},v=e=>({get:(t,r)=>m.bind(s,e,r)}),j=(e,t)=>t?t!==e&&e.replaceWith(t):e.remove(),x=()=>{let r=0,o=[...e].filter(e=>e.rawVal!==e.h);do{t=new Set;for(let e of new Set(o.flatMap(e=>e.l=d(e.l))))y(e.f,e.s,e.t),e.t=s}while(++r<100&&(o=[...t]).length);let n=[...e].filter(e=>e.rawVal!==e.h);e=s;for(let e of new Set(n.flatMap(e=>e.o=d(e.o))))j(e.t,g(e.f,e.t)),e.t=s;for(let e of n)e.h=e.rawVal},O={tags:new Proxy(e=>new Proxy(m,v(e)),v()),hydrate:(e,t)=>j(e,g(t,e)),add:b,state:S,derive:y},window.van=O;}
|
||||
///
|
||||
</script>
|
||||
<script type="module" src="app.js"></script>
|
||||
</body>
|
||||
</html>
|
||||
90
app.js
90
app.js
@ -1,12 +1,6 @@
|
||||
/// burn vanjs into codebase
|
||||
{let e,t,r,o,n,s,l,i,f,h,w,a,u,d,c,_,S,g,y,b,m,v,j,x,O;l=Object.getPrototypeOf,f={},h=l(i={isConnected:1}),w=l(l),a=(e,t,r,o)=>(e??(o?setTimeout(r,o):queueMicrotask(r),new Set)).add(t),u=(e,t,o)=>{let n=r;r=t;try{return e(o)}catch(e){return console.error(e),o}finally{r=n}},d=e=>e.filter(e=>e.t?.isConnected),c=e=>n=a(n,e,()=>{for(let e of n)e.o=d(e.o),e.l=d(e.l);n=s},1e3),_={get val(){return r?.i?.add(this),this.rawVal},get oldVal(){return r?.i?.add(this),this.h},set val(o){r?.u?.add(this),o!==this.rawVal&&(this.rawVal=o,this.o.length+this.l.length?(t?.add(this),e=a(e,this,x)):this.h=o)}},S=e=>({__proto__:_,rawVal:e,h:e,o:[],l:[]}),g=(e,t)=>{let r={i:new Set,u:new Set},n={f:e},s=o;o=[];let l=u(e,r,t);l=(l??document).nodeType?l:new Text(l);for(let e of r.i)r.u.has(e)||(c(e),e.o.push(n));for(let e of o)e.t=l;return o=s,n.t=l},y=(e,t=S(),r)=>{let n={i:new Set,u:new Set},s={f:e,s:t};s.t=r??o?.push(s)??i,t.val=u(e,n,t.rawVal);for(let e of n.i)n.u.has(e)||(c(e),e.l.push(s));return t},b=(e,...t)=>{for(let r of t.flat(1/0)){let t=l(r??0),o=t===_?g(()=>r.val):t===w?g(r):r;o!=s&&e.append(o)}return e},m=(e,t,...r)=>{let[{is:o,...n},...i]=l(r[0]??0)===h?r:[{},...r],a=e?document.createElementNS(e,t,{is:o}):document.createElement(t,{is:o});for(let[e,r]of Object.entries(n)){let o=t=>t?Object.getOwnPropertyDescriptor(t,e)??o(l(t)):s,n=t+","+e,i=f[n]??=o(l(a))?.set??0,h=e.startsWith("on")?(t,r)=>{let o=e.slice(2);a.removeEventListener(o,r),a.addEventListener(o,t)}:i?i.bind(a):a.setAttribute.bind(a,e),u=l(r??0);e.startsWith("on")||u===w&&(r=y(r),u=_),u===_?g(()=>(h(r.val,r.h),a)):h(r)}return b(a,i)},v=e=>({get:(t,r)=>m.bind(s,e,r)}),j=(e,t)=>t?t!==e&&e.replaceWith(t):e.remove(),x=()=>{let r=0,o=[...e].filter(e=>e.rawVal!==e.h);do{t=new Set;for(let e of new Set(o.flatMap(e=>e.l=d(e.l))))y(e.f,e.s,e.t),e.t=s}while(++r<100&&(o=[...t]).length);let n=[...e].filter(e=>e.rawVal!==e.h);e=s;for(let e of new Set(n.flatMap(e=>e.o=d(e.o))))j(e.t,g(e.f,e.t)),e.t=s;for(let e of n)e.h=e.rawVal},O={tags:new Proxy(e=>new Proxy(m,v(e)),v()),hydrate:(e,t)=>j(e,g(t,e)),add:b,state:S,derive:y},window.van=O;}
|
||||
///
|
||||
|
||||
const $ = van.tags;
|
||||
const writeKey = "vault";
|
||||
|
||||
const password = van.state("");
|
||||
|
||||
const encrypt =(secret)=>
|
||||
{
|
||||
const serialized = JSON.stringify(vault.val);
|
||||
@ -44,35 +38,31 @@ const decrypt =(secret)=>
|
||||
const vault = van.state(/**@type{CredSet[]}*/([]));
|
||||
const vaultSerialized = van.state("");
|
||||
|
||||
let attempts = 0;
|
||||
const preexisting = van.state((localStorage.getItem(writeKey)||"").length>2 ? true : false);
|
||||
const accessError = van.state(false);
|
||||
const password = van.state("");
|
||||
const attemptsFailed = van.state(0);
|
||||
const preexisting = (localStorage.getItem(writeKey)||"");
|
||||
|
||||
|
||||
van.derive(()=>{
|
||||
if(preexisting.val)
|
||||
const PasswordChange =()=>
|
||||
{
|
||||
if(preexisting && attemptsFailed.val > -1)
|
||||
{
|
||||
const success = decrypt(password.val);
|
||||
if(success)
|
||||
{
|
||||
preexisting.val = false;
|
||||
accessError.val = false;
|
||||
attemptsFailed.val = -1;
|
||||
}
|
||||
else
|
||||
{
|
||||
if(attempts > 0)
|
||||
{
|
||||
accessError.val = true;
|
||||
}
|
||||
attemptsFailed.val = attemptsFailed.val+1;
|
||||
return;
|
||||
}
|
||||
}
|
||||
encrypt(password.val);
|
||||
console.log("password change");
|
||||
});
|
||||
};
|
||||
|
||||
/** @type {(credSet:CredSet)=>void} */
|
||||
const vaultAdd =(credSet)=>{
|
||||
const VaultAdd =(credSet)=>{
|
||||
const clone = [...vault.rawVal];
|
||||
let i;
|
||||
for(i=0; i<clone.length; i++)
|
||||
@ -84,6 +74,7 @@ const vaultAdd =(credSet)=>{
|
||||
}
|
||||
clone.splice(i, 0, credSet);
|
||||
vault.val = clone;
|
||||
encrypt(password.val);
|
||||
};
|
||||
|
||||
const Components = {
|
||||
@ -108,7 +99,7 @@ const Components = {
|
||||
{
|
||||
onsubmit(e){
|
||||
e.preventDefault();
|
||||
vaultAdd([inputSite.value, inputUser.value, inputPass.value, inputCode.value, new Date().getTime(), {}])
|
||||
VaultAdd([inputSite.value, inputUser.value, inputPass.value, inputCode.value, new Date().getTime(), {}])
|
||||
}
|
||||
},
|
||||
|
||||
@ -124,24 +115,57 @@ const Components = {
|
||||
Root()
|
||||
{
|
||||
const input = $.input({id:"passwordField", value:password.val});
|
||||
const status =()=>
|
||||
{
|
||||
let message = "";
|
||||
let showVault = false;
|
||||
let button = "Re-encrypt";
|
||||
if(preexisting)
|
||||
{
|
||||
if(attemptsFailed.val > -1)
|
||||
{
|
||||
message = `Existing session data found. Enter the correct password to recover it.`;
|
||||
button = `Recover`;
|
||||
if(attemptsFailed.val > 0)
|
||||
{
|
||||
message += ` Password Incorrect (${attemptsFailed.val} attempts).`;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
message = `Password changes will re-encrypt your active session data.`;
|
||||
showVault = true;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
message = `You are starting a new session.`;
|
||||
showVault = true;
|
||||
}
|
||||
return [message, button, showVault]
|
||||
}
|
||||
|
||||
const [message, buttonText, showVault] = status();
|
||||
|
||||
return $.div(
|
||||
$.h1(message),
|
||||
$.label({for:input.id}, "Password"),
|
||||
()=>input,
|
||||
$.strong(password.val),
|
||||
$.button({onclick(){
|
||||
attempts++;
|
||||
password.val = input.value;
|
||||
}}, "Set Password"),
|
||||
PasswordChange();
|
||||
}}, buttonText),
|
||||
$.div(
|
||||
$.h3("debug zone"),
|
||||
$.ul(
|
||||
$.li($.strong("preexisting "), preexisting),
|
||||
$.li($.strong("attemptsFailed "), attemptsFailed.val),
|
||||
$.li($.strong("vaultSerialized "), vaultSerialized.val),
|
||||
$.li($.strong("password "), password.val),
|
||||
)
|
||||
),
|
||||
$.hr(),
|
||||
$.em(preexisting.val),
|
||||
accessError.val ? $.strong("Password did not decrypt existing session.") : null,
|
||||
preexisting.val ? $.div(
|
||||
$.p("Existing session found. Unlock it with the right password, or destroy data."),
|
||||
$.button({onclick(){attempts = 0; accessError.val = false; preexisting.val = false;}}, "Destroy Data")
|
||||
) : null,
|
||||
(!preexisting.val && password.val) ? Components.Vault() : null,
|
||||
$.hr(),
|
||||
$.pre(vaultSerialized.val)
|
||||
showVault ? Components.Vault() : null
|
||||
);
|
||||
|
||||
},
|
||||
|
||||
Loading…
Reference in New Issue
Block a user