aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorAdam Soltys <[email protected]>2023-12-07 22:34:23 -0800
committerAdam Soltys <[email protected]>2023-12-07 22:34:23 -0800
commit8940118dd22c5f2ab680ef8036bcfafecc5696ab (patch)
treea49db92b3ba5f8668cc79ab1dae46e7a09999ba0
parent00e88944abb529d07e189f1181de8a4804f8ae9c (diff)
downloadcoinos-ui-8940118dd22c5f2ab680ef8036bcfafecc5696ab.tar.gz
coinos-ui-8940118dd22c5f2ab680ef8036bcfafecc5696ab.zip
password reset
-rw-r--r--src/locales/en.json3
-rw-r--r--src/routes/(app)/+layout.server.js5
-rw-r--r--src/routes/(app)/+layout.svelte6
-rw-r--r--src/routes/(app)/[username]/generate/+page.svelte12
-rw-r--r--src/routes/(app)/forgot/+page.server.js4
-rw-r--r--src/routes/(app)/forgot/+page.svelte62
-rw-r--r--src/routes/(app)/login/+page.svelte2
-rw-r--r--src/routes/(app)/reset/[code]/+page.server.js30
-rw-r--r--src/routes/(app)/reset/[code]/+page.svelte80
9 files changed, 168 insertions, 36 deletions
diff --git a/src/locales/en.json b/src/locales/en.json
index 0dda9362..6d10da6c 100644
--- a/src/locales/en.json
+++ b/src/locales/en.json
@@ -123,9 +123,10 @@
"token": "2FA Token",
"username": "Username",
"password": "Password",
+ "newPassword": "New password",
"email": "Email",
"passwordRecommendation": "We recommend using a long, random password if you intend to keep funds in your account.",
- "forgotUserOrPassword": "Forgot Username or Password?",
+ "forgotUserOrPassword": "Forgot password?",
"haveAccount": "Already have an account?",
"noAccount": "Don't have an account?",
"register": "Register",
diff --git a/src/routes/(app)/+layout.server.js b/src/routes/(app)/+layout.server.js
index 9fcf6411..67250769 100644
--- a/src/routes/(app)/+layout.server.js
+++ b/src/routes/(app)/+layout.server.js
@@ -34,8 +34,9 @@ export async function load({ cookies, request, url, params }) {
throw redirect(307, "/login");
}
- if (user && !user.pubkey && !pathname.includes("generate"))
- throw redirect(307, `/${user.username}/generate`);
+ if (user && !user.pubkey && !pathname.includes("generate")) {
+ throw redirect(303, `/${user.username}/generate`);
+ }
try {
rate = await get("/rate");
diff --git a/src/routes/(app)/+layout.svelte b/src/routes/(app)/+layout.svelte
index 2d3aa192..237e931c 100644
--- a/src/routes/(app)/+layout.svelte
+++ b/src/routes/(app)/+layout.svelte
@@ -8,18 +8,18 @@
request,
ndef,
passwordPrompt,
+ password,
pin,
} from "$lib/store";
import { page } from "$app/stores";
import { browser } from "$app/environment";
- import { goto } from "$app/navigation";
import LoadingSplash from "$comp/LoadingSplash.svelte";
import Invoice from "$comp/Invoice.svelte";
import Password from "$comp/Password.svelte";
import Request from "$comp/Request.svelte";
import { warning, protectedRoutes } from "$lib/utils";
import { t, locale } from "$lib/translations";
- import { onNavigate } from "$app/navigation";
+ import { goto, onNavigate } from "$app/navigation";
export let data;
@@ -34,7 +34,7 @@
});
});
- let { rate, user, subject, token, rates } = data;
+ let { generate, rate, user, subject, token, rates } = data;
$: update(data);
let update = (data) => {
diff --git a/src/routes/(app)/[username]/generate/+page.svelte b/src/routes/(app)/[username]/generate/+page.svelte
index 71f828dc..0c83fad4 100644
--- a/src/routes/(app)/[username]/generate/+page.svelte
+++ b/src/routes/(app)/[username]/generate/+page.svelte
@@ -3,6 +3,7 @@
import { onMount } from "svelte";
import { goto, invalidate } from "$app/navigation";
import Pin from "$comp/Pin.svelte";
+ import Spinner from "$comp/Spinner.svelte";
import { loginRedirect, pin, password, passwordPrompt } from "$lib/store";
import { generate } from "$lib/nostr";
import { browser } from "$app/environment";
@@ -19,6 +20,7 @@
return;
}
+ console.log("PASSWORRRRD", $password);
if (!$password) $passwordPrompt = true;
try {
@@ -58,6 +60,10 @@
{#if loaded && user?.haspin && $pin?.length !== 6}
<Pin />
{/if}
-{loaded}
-{JSON.stringify(user)}
-{$pin}
+
+<div class="container px-4 text-center mx-auto">
+ <h1 class="text-3xl md:text-4xl font-bold mb-6">Generating new account keys</h1>
+ <div class="flex w-full py-5 max-w-[200px] mx-auto bg-black rounded-2xl">
+ <Spinner />
+ </div>
+</div>
diff --git a/src/routes/(app)/forgot/+page.server.js b/src/routes/(app)/forgot/+page.server.js
index db2005e7..48411539 100644
--- a/src/routes/(app)/forgot/+page.server.js
+++ b/src/routes/(app)/forgot/+page.server.js
@@ -3,13 +3,11 @@ import { fd, post, login } from "$lib/utils";
export const actions = {
default: async ({ request }) => {
- let { email } = await fd(request);
-
try {
+ let { email } = await fd(request);
await post("/forgot", { email });
return { success: true };
} catch (e) {
- console.log(e.message);
return fail(400, { error: e.message });
}
},
diff --git a/src/routes/(app)/forgot/+page.svelte b/src/routes/(app)/forgot/+page.svelte
index 91c4290a..9490d531 100644
--- a/src/routes/(app)/forgot/+page.svelte
+++ b/src/routes/(app)/forgot/+page.svelte
@@ -1,4 +1,6 @@
<script>
+ import { focus } from "$lib/utils";
+ import { enhance } from "$app/forms";
import { t } from "$lib/translations";
import Icon from "$comp/Icon.svelte";
import Spinner from "$comp/Spinner.svelte";
@@ -28,31 +30,45 @@
</div>
{/if}
- <form class="space-y-5" method="POST">
- <div>
- <label for="email" class="font-semibold">{$t("login.email")}</label>
- <input
- name="email"
- type="text"
- required
- class="bg-primary"
- bind:value={email}
- use:focus
- autocapitalize="none"
- />
+ {#if form?.success}
+ <div class="text-secondary">
+ A password reset link will be sent to your email if we have it on file.
</div>
- <button
- type="submit"
- class="bg-black text-white w-full rounded-2xl p-4 font-semibold hover:opacity-80"
- disabled={loading}>
- {#if loading}
- <Spinner />
- {:else}
- {$t("login.submit")}
- {/if}
- </button>
- </form>
+ <div class="flex w-full">
+ <a
+ href="/login"
+ class="bg-black text-white w-full rounded-2xl p-4 font-semibold hover:opacity-80 text-center">
+ Continue
+ </a>
+ </div>
+ {:else}
+ <form class="space-y-5" method="POST" use:enhance>
+ <div>
+ <label for="email" class="font-semibold">{$t("login.email")}</label>
+ <input
+ name="email"
+ type="text"
+ required
+ class="bg-primary"
+ bind:value={email}
+ use:focus
+ autocapitalize="none"
+ />
+ </div>
+
+ <button
+ type="submit"
+ class="bg-black text-white w-full rounded-2xl p-4 font-semibold hover:opacity-80"
+ disabled={loading}>
+ {#if loading}
+ <Spinner />
+ {:else}
+ {$t("login.submit")}
+ {/if}
+ </button>
+ </form>
+ {/if}
</div>
</div>
</div>
diff --git a/src/routes/(app)/login/+page.svelte b/src/routes/(app)/login/+page.svelte
index 61eea586..b729d70f 100644
--- a/src/routes/(app)/login/+page.svelte
+++ b/src/routes/(app)/login/+page.svelte
@@ -153,7 +153,7 @@
<div class="flex justify-end items-center">
<a
href="/forgot"
- class="underline underline-offset-4 text-black text-sm"
+ class="underline underline-offset-4 text-black"
>{$t("login.forgotUserOrPassword")}</a
>
</div>
diff --git a/src/routes/(app)/reset/[code]/+page.server.js b/src/routes/(app)/reset/[code]/+page.server.js
new file mode 100644
index 00000000..92ad1d0f
--- /dev/null
+++ b/src/routes/(app)/reset/[code]/+page.server.js
@@ -0,0 +1,30 @@
+import { fail, redirect } from "@sveltejs/kit";
+import { fd, post, login } from "$lib/utils";
+
+export const actions = {
+ default: async ({ cookies, params, request }) => {
+ let ip = request.headers.get("cf-connecting-ip");
+ let error;
+
+ let { code } = params;
+ let { password } = await fd(request);
+
+ try {
+ let user = await post("/reset", { code, password });
+ user.password = password;
+
+ try {
+ await login(user, cookies, ip);
+ error = null;
+ } catch (e) {
+ error ||= e.message;
+ }
+
+ if (error) return fail(400, { error });
+ throw redirect(307, `/${user.username}`);
+ } catch (e) {
+ console.log(e.message);
+ return fail(400, { error: e.message });
+ }
+ },
+};
diff --git a/src/routes/(app)/reset/[code]/+page.svelte b/src/routes/(app)/reset/[code]/+page.svelte
new file mode 100644
index 00000000..83e860ae
--- /dev/null
+++ b/src/routes/(app)/reset/[code]/+page.svelte
@@ -0,0 +1,80 @@
+<script>
+ import { t } from "$lib/translations";
+ import Icon from "$comp/Icon.svelte";
+ import Spinner from "$comp/Spinner.svelte";
+ import { fly } from "svelte/transition";
+ import { password } from "$lib/store";
+
+ export let form;
+ let email;
+ let loading;
+ let revealPassword;
+</script>
+
+<div class="pt-10">
+ <div class="w-[243px] mx-auto mb-10">
+ <a href="/">
+ <Icon icon="logo" />
+ </a>
+ </div>
+
+ <div class="flex justify-center items-center">
+ <div
+ class="shadow-xl rounded-3xl p-10 pb-12 space-y-5 w-full mx-5 md:mx-0 md:w-[400px]"
+ >
+ <h1 class="text-2xl font-bold text-center">{$t("login.reset")}</h1>
+
+ {#if form?.error}
+ <div class="text-red-600 text-center" in:fly>
+ {form.error}
+ </div>
+ {/if}
+
+ <form class="space-y-5" method="POST">
+ <div class="relative">
+ <label for="password" class="block font-semibold"
+ >{$t("login.newPassword")}</label
+ >
+ {#if revealPassword}
+ <input
+ name="password"
+ type="text"
+ required
+ class="bg-primary"
+ bind:value={$password}
+ autocapitalize="none"
+ />
+ {:else}
+ <input
+ name="password"
+ type="password"
+ required
+ class="bg-primary"
+ bind:value={$password}
+ autocapitalize="none"
+ />
+ {/if}
+ <button
+ type="button"
+ on:click={() => (revealPassword = !revealPassword)}
+ class="absolute right-5 top-10">
+ <Icon icon={revealPassword ? "eye" : "eye-off"} />
+ </button>
+ </div>
+
+ <div class="text-secondary">A new seed phrase will be generated for your account. You'll need to import your old seed phrase if you want to use the same nostr profile and savings account as before.</div>
+
+ <button
+ type="submit"
+ class="bg-black text-white w-full rounded-2xl p-4 font-semibold hover:opacity-80"
+ disabled={loading}>
+ {#if loading}
+ <Spinner />
+ {:else}
+ {$t("login.submit")}
+ {/if}
+ </button>
+ </form>
+ </div>
+ </div>
+</div>