Spaces:
Sleeping
Sleeping
File size: 2,357 Bytes
241884b 43be92e 241884b 43be92e 241884b 43be92e 241884b 43be92e 241884b 43be92e 241884b |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 |
"use server";
import { createClient } from "@/utils/supabase/server";
import { createClient as createSupabaseClient } from "@supabase/supabase-js";
export type ForgotResult =
| { ok: true; message: string }
| { ok: false; message: string };
export async function sendResetEmail(email: string): Promise<ForgotResult> {
const supabase = createClient();
if (!email || !/^[^\s@]+@[^\s@]+\.[^\s@]+$/.test(email)) {
return { ok: false, message: "Email tidak valid" };
}
// Admin-only: verify the email belongs to an admin user before sending reset link
try {
const adminClient = createSupabaseClient(
process.env.NEXT_PUBLIC_SUPABASE_URL!,
process.env.SUPABASE_SERVICE_KEY!,
);
// list users and find by email (no direct getUserByEmail in v2)
let page = 1;
const perPage = 200;
let foundRole: unknown = null;
while (true) {
const { data, error } = await adminClient.auth.admin.listUsers({ page, perPage });
if (error) throw error;
const users = data?.users || [];
const match = users.find((u) => u.email?.toLowerCase() === email.toLowerCase());
if (match) {
foundRole = match.user_metadata?.role;
break;
}
if (!data || users.length < perPage) break; // no more pages
page += 1;
// safety cap to avoid excessive loops
if (page > 50) break;
}
if (foundRole !== "admin") {
// Do not reveal whether the email exists; return a generic message
return {
ok: false,
message: "Akun tidak diizinkan melakukan reset di aplikasi admin.",
};
}
} catch {
// Fail closed: if role check fails, do not proceed
return {
ok: false,
message: "Gagal memverifikasi akun. Coba lagi.",
};
}
// Determine redirect URL for the password reset flow
const siteUrl =
process.env.NEXT_PUBLIC_SITE_URL?.replace(/\/$/, "") ||
(process.env.VERCEL_URL
? `https://${process.env.VERCEL_URL}`
: "http://localhost:3000");
const redirectTo = `${siteUrl}/reset-password`;
const { error } = await supabase.auth.resetPasswordForEmail(email, {
redirectTo,
});
if (error) {
return { ok: false, message: "Gagal mengirim email reset. Coba lagi." };
}
return {
ok: true,
message: "Email reset telah dikirim. Periksa kotak masuk Anda.",
};
}
|