diff --git a/src/app/api/auth/otp/route.ts b/src/app/api/auth/otp/route.ts new file mode 100644 index 0000000..be04e33 --- /dev/null +++ b/src/app/api/auth/otp/route.ts @@ -0,0 +1,59 @@ +import { prisma } from "@/module/_global"; +import { ILogin } from "@/types"; +import { NextRequest } from "next/server"; + +export async function POST(req: NextRequest) { + try { + const { phone }: ILogin = await req.json(); + + const user = await prisma.user.findUnique({ + where: { phone, isActive: true }, + select: { id: true, phone: true, isWithoutOTP: true }, + }); + + if (!user) { + return Response.json({ + success: false, + message: "Nomor telepon tidak terdaftar", + }); + } + + // Generate OTP + const code = Math.floor(1000 + Math.random() * 9000); + const message = `Desa+\nMasukkan kode ini ${code} pada web app Desa+ anda. Jangan berikan pada siapapun.`; + + // Send WhatsApp + try { + const resWa = await fetch(`${process.env.URL_OTP}/api/wa/send-text`, { + method: 'POST', + headers: { + 'Content-Type': 'application/json', + Authorization: `Bearer ${process.env.WA_SERVER_TOKEN}`, + }, + body: JSON.stringify({ + number: user.phone, + text: message, + }), + }); + + if (!resWa.ok) { + console.error("WhatsApp API Error:", resWa.status); + } + } catch (error) { + console.error("WhatsApp Fetch Error:", error); + } + + return Response.json({ + success: true, + message: "Sukses", + phone: user.phone, + isWithoutOTP: user.isWithoutOTP, + id: user.id, + otp: code, // Return OTP for client-side verification (as per existing logic) + }); + + } catch (error) { + console.error(error); + return Response.json({ message: "Internal Server Error (error: 500)", success: false }); + } +} diff --git a/src/app/api/version-app/route.ts b/src/app/api/version-app/route.ts index 027034b..6319559 100644 --- a/src/app/api/version-app/route.ts +++ b/src/app/api/version-app/route.ts @@ -2,7 +2,7 @@ import { NextResponse } from "next/server"; export async function GET(request: Request) { try { - return NextResponse.json({ success: true, version: "2.1.7", tahap: "beta", update: "-api untuk dashboard noc" }, { status: 200 }); + return NextResponse.json({ success: true, version: "2.1.8", tahap: "beta", update: "-api untuk dashboard noc; -perbaikan otp" }, { status: 200 }); } catch (error) { console.error(error); return NextResponse.json({ success: false, version: "Gagal mendapatkan version, coba lagi nanti (error: 500)", reason: (error as Error).message, }, { status: 500 }); diff --git a/src/module/auth/login/view/view_login.tsx b/src/module/auth/login/view/view_login.tsx index 774155f..7269ad5 100644 --- a/src/module/auth/login/view/view_login.tsx +++ b/src/module/auth/login/view/view_login.tsx @@ -5,7 +5,6 @@ import { useFocusTrap } from "@mantine/hooks"; import { useState } from "react"; import toast from "react-hot-toast"; import ViewVerification from "../../varification/view/view_verification"; - function ViewLogin() { const focusTrapRef = useFocusTrap() const textInfo = "Kami akan mengirimkan kode verifikasi melalui WhatsApp untuk mengonfirmasi nomor Anda."; @@ -34,23 +33,24 @@ function ViewLogin() { }) const cekLogin = await cek.json() if (cekLogin.success) { - const code = Math.floor(1000 + Math.random() * 9000) try { - const res = await fetch(`https://wa.wibudev.com/code?nom=${cekLogin.phone}&text=*DARMASABA*%0A%0A - JANGAN BERIKAN KODE RAHASIA ini kepada siapa pun TERMASUK PIHAK DARMASABA. Masukkan otentikasi: *${encodeURIComponent(code)}*`).then( - async (res) => { - if (res.status == 200) { - setValPhone(cekLogin.phone) - setOTP(code) - setUser(cekLogin.id) - setVerif(true) - toast.success('Kode verifikasi telah dikirim') - } else { - console.error(res.status) - toast.error('Internal Server Error') - } - } - ) + const res = await fetch('/api/auth/otp', { + method: 'POST', + headers: { + 'Content-Type': 'application/json' + }, + body: JSON.stringify({ phone: isPhone }) + }) + const data = await res.json() + if (data.success) { + setValPhone(data.phone) + setOTP(data.otp) + setUser(data.id) + setVerif(true) + toast.success('Kode verifikasi telah dikirim') + } else { + toast.error(data.message || 'Gagal mengirim kode verifikasi') + } } catch (error) { console.error(error) toast.error('Internal Server Error') diff --git a/src/module/auth/varification/view/view_verification.tsx b/src/module/auth/varification/view/view_verification.tsx index 678d183..49f135b 100644 --- a/src/module/auth/varification/view/view_verification.tsx +++ b/src/module/auth/varification/view/view_verification.tsx @@ -15,19 +15,20 @@ export default function ViewVerification({ phone, otp, user }: IVerification) { async function onResend() { try { - const code = Math.floor(1000 + Math.random() * 9000) - const res = await fetch(`https://wa.wibudev.com/code?nom=${phone}&text=*DARMASABA*%0A%0A - JANGAN BERIKAN KODE RAHASIA ini kepada siapa pun TERMASUK PIHAK DARMASABA. Masukkan otentikasi: *${encodeURIComponent(code)}*`) - .then( - async (res) => { - if (res.status == 200) { - toast.success('Kode verifikasi telah dikirim') - setOTP(code) - } else { - toast.error('Internal Server Error') - } - } - ); + const res = await fetch('/api/auth/otp', { + method: 'POST', + headers: { + 'Content-Type': 'application/json' + }, + body: JSON.stringify({ phone }) + }) + const data = await res.json() + if (data.success) { + toast.success('Kode verifikasi telah dikirim') + setOTP(data.otp) + } else { + toast.error(data.message || 'Gagal mengirim ulang kode') + } } catch (error) { console.error(error) toast.error('Internal Server Error')