From 7b703f3f97b24c1209c3189dc30eb837be9f48cd Mon Sep 17 00:00:00 2001 From: csasq Date: Fri, 13 Mar 2026 00:36:35 +0300 Subject: [PATCH] =?UTF-8?q?=D0=A0=D0=B0=D0=B7=D1=80=D0=B0=D0=B1=D0=BE?= =?UTF-8?q?=D1=82=D0=B0=D0=BD=D0=BE=20=D0=B2=D0=B5=D0=B1-=D0=BF=D1=80?= =?UTF-8?q?=D0=B8=D0=BB=D0=BE=D0=B6=D0=B5=D0=BD=D0=B8=D0=B5?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- index.html | 45 +++++++++++++++++++++++++++++++++++++ script.js | 65 ++++++++++++++++++++++++++++++++++++++++++++++++++++++ style.css | 17 ++++++++++++++ 3 files changed, 127 insertions(+) create mode 100644 index.html create mode 100644 script.js create mode 100644 style.css diff --git a/index.html b/index.html new file mode 100644 index 0000000..a191ea5 --- /dev/null +++ b/index.html @@ -0,0 +1,45 @@ + + + + + OTP AUTH Parser + + + + +
+
+ + +
+ +
+ + +
+ +
+ + +
+ +
+ + +
+ +
+ + +
+ +
+ +
+ +
+ + +
+ + diff --git a/script.js b/script.js new file mode 100644 index 0000000..7e614da --- /dev/null +++ b/script.js @@ -0,0 +1,65 @@ +window.addEventListener('DOMContentLoaded', () => { + const $url = document.querySelector('#url') + const $type = document.querySelector('#type') + const $label = document.querySelector('#label') + const $secret = document.querySelector('#secret') + const $issuer = document.querySelector('#issuer') + const $dynamic = document.querySelector('#dynamic') + + $url.oninput = () => { + const url = new URL($url.value) + + $type.value = decodeURIComponent(url.hostname || 'totp') + $type.oninput = () => { + url.hostname = encodeURIComponent($type.value) + $url.value = url.href + } + + $label.value = decodeURIComponent(url.pathname.replace(/^\//, '') || '') + $label.oninput = () => { + url.pathname = encodeURIComponent($label.value) + $url.value = url.href + } + + const onInput = ($input, key) => { + $input.value = url.searchParams.get(key) || '' + $input.oninput = () => { + if ($input.value) + url.searchParams.set(key, $input.value || '') + else + url.searchParams.delete(key) + $url.value = url.href + } + } + + onInput($secret, 'secret') + onInput($issuer, 'issuer') + + let dynamicCount = 0 + + $dynamic.innerHTML = '' + + url.searchParams.keys().forEach(key => { + switch (key) { + case 'secret': + case 'issuer': + break; + + default: + dynamicCount += 1 + const id = `dynamic-${dynamicCount}` + const $label = document.createElement('label') + $label.for = id + $label.textContent = key + const $input = document.createElement('input') + $input.id = id + onInput($input, key) + const $div = document.createElement('div') + $div.appendChild($label) + $div.appendChild($input) + $dynamic.appendChild($div) + break; + } + }) + } +}) diff --git a/style.css b/style.css new file mode 100644 index 0000000..c6822d5 --- /dev/null +++ b/style.css @@ -0,0 +1,17 @@ +#form, #dynamic { + display: flex; + flex-direction: column; + gap: 1rem; +} + +label { + font-family: sans-serif; + font-weight: bold; +} + +input { + margin-top: .25rem; + width: 100%; + box-sizing: border-box; + font-size: 1.5rem; +}