119 lines
3.2 KiB
JavaScript
119 lines
3.2 KiB
JavaScript
|
function initEnterPassword() {
|
||
|
const form = document.querySelector("form#enter-password");
|
||
|
const fieldset = document.querySelector("fieldset#enter-password");
|
||
|
const submit = document.querySelector("button#enter-password");
|
||
|
|
||
|
const dialog = document.querySelector("dialog#link");
|
||
|
const link = document.querySelector("input#link");
|
||
|
const copy = document.querySelector("button#link-copy");
|
||
|
const close = document.querySelector("button#link-close");
|
||
|
|
||
|
form.addEventListener("submit", async (ev) => {
|
||
|
const data = new FormData(ev.target);
|
||
|
ev.preventDefault();
|
||
|
|
||
|
try {
|
||
|
fieldset.disabled = true;
|
||
|
submit.ariaBusy = "true";
|
||
|
|
||
|
const password = await encryptPassword(data.get("password"));
|
||
|
|
||
|
const id = await uploadPassword(
|
||
|
password.password,
|
||
|
parseInt(data.get("expires-in")),
|
||
|
);
|
||
|
|
||
|
const url = new URL(window.location.toString());
|
||
|
url.hash = [id, password.key, password.iv].join(":");
|
||
|
|
||
|
link.value = url.toString();
|
||
|
dialog.showModal();
|
||
|
} finally {
|
||
|
fieldset.disabled = false;
|
||
|
submit.ariaBusy = "false";
|
||
|
ev.target.reset();
|
||
|
}
|
||
|
});
|
||
|
|
||
|
dialog.addEventListener("close", (ev) => {
|
||
|
this.link.value = "";
|
||
|
});
|
||
|
|
||
|
copy.addEventListener("click", (ev) => {
|
||
|
link.select();
|
||
|
link.setSelectionRange(0, 99999);
|
||
|
navigator.clipboard.writeText(link.value);
|
||
|
});
|
||
|
|
||
|
close.addEventListener("click", (ev) => {
|
||
|
dialog.close();
|
||
|
});
|
||
|
}
|
||
|
|
||
|
async function confirmViewPassword() {
|
||
|
const dialog = document.querySelector("dialog#confirm");
|
||
|
const close = document.querySelector("button#confirm-close");
|
||
|
const ok = document.querySelector("button#confirm-ok");
|
||
|
const notFoundDialog = document.querySelector("dialog#not-found");
|
||
|
const notFoundClose = document.querySelector("button#not-found-close");
|
||
|
|
||
|
let hash = window.location.hash;
|
||
|
hash = hash.substring(1);
|
||
|
if (hash.trim() == "") {
|
||
|
return;
|
||
|
}
|
||
|
|
||
|
const [id, key, iv] = hash.split(":");
|
||
|
const has = await hasPassword(id);
|
||
|
if (!has) {
|
||
|
notFoundClose.addEventListener("click", () => notFoundDialog.close());
|
||
|
notFoundDialog.addEventListener("close", () => (window.location.hash = ""));
|
||
|
|
||
|
notFoundDialog.showModal();
|
||
|
return;
|
||
|
}
|
||
|
|
||
|
dialog.addEventListener("close", () => (window.location.hash = ""));
|
||
|
|
||
|
close.addEventListener("click", () => {
|
||
|
dialog.close();
|
||
|
});
|
||
|
|
||
|
ok.addEventListener("click", async () => {
|
||
|
try {
|
||
|
close.disabled = true;
|
||
|
ok.disabled = true;
|
||
|
ok.ariaBusy = "true";
|
||
|
|
||
|
const encryptedPassword = await getPassword(id);
|
||
|
const password = await decryptPassword(encryptedPassword, key, iv);
|
||
|
|
||
|
viewPassword(password);
|
||
|
} finally {
|
||
|
close.disabled = false;
|
||
|
ok.disabled = false;
|
||
|
ok.ariaBusy = "false";
|
||
|
dialog.close();
|
||
|
}
|
||
|
});
|
||
|
|
||
|
dialog.showModal();
|
||
|
}
|
||
|
|
||
|
async function viewPassword(password) {
|
||
|
const dialog = document.querySelector("dialog#view");
|
||
|
const viewPassword = document.querySelector("textarea#view-password");
|
||
|
const close = document.querySelector("button#view-close");
|
||
|
|
||
|
close.addEventListener("click", () => dialog.close());
|
||
|
dialog.addEventListener("close", () => (window.location.hash = ""), 0);
|
||
|
|
||
|
viewPassword.value = password;
|
||
|
dialog.showModal();
|
||
|
}
|
||
|
|
||
|
window.addEventListener("load", () => {
|
||
|
initEnterPassword();
|
||
|
confirmViewPassword();
|
||
|
});
|