Fix: middleware
Deskripsi - Fix middleware - Fix metode login ( sekarang menggunakan api )
This commit is contained in:
@@ -1,4 +1,4 @@
|
||||
import { funCheckCookies } from "@/app_modules/_global/fun/get/fun_check_cookies";
|
||||
|
||||
import { Login } from "@/app_modules/auth";
|
||||
import versionUpdate from "../../../../package.json";
|
||||
|
||||
|
||||
@@ -1,8 +0,0 @@
|
||||
import { Register } from "@/app_modules/auth";
|
||||
import { auth_getCodeOtpByNumber } from "@/app_modules/auth/fun/get_kode_otp_by_id";
|
||||
|
||||
export default async function Page({ params }: { params: { id: string } }) {
|
||||
let otpId = params.id;
|
||||
const dataOtp = await auth_getCodeOtpByNumber({ kodeId: otpId });
|
||||
return <Register dataOtp={dataOtp} />;
|
||||
}
|
||||
5
src/app/(user)/register/page.tsx
Normal file
5
src/app/(user)/register/page.tsx
Normal file
@@ -0,0 +1,5 @@
|
||||
import { Register } from "@/app_modules/auth";
|
||||
|
||||
export default async function Page() {
|
||||
return <Register />;
|
||||
}
|
||||
7
src/app/(user)/splash/page.tsx
Normal file
7
src/app/(user)/splash/page.tsx
Normal file
@@ -0,0 +1,7 @@
|
||||
import { SplashScreen } from "@/app_modules/auth";
|
||||
|
||||
export default async function Page() {
|
||||
return <>
|
||||
<SplashScreen/>
|
||||
</>
|
||||
}
|
||||
@@ -1,9 +0,0 @@
|
||||
import { Validasi } from "@/app_modules/auth";
|
||||
import { auth_getCodeOtpByNumber } from "@/app_modules/auth/fun/get_kode_otp_by_id";
|
||||
|
||||
export default async function Page({ params }: { params: { id: string } }) {
|
||||
let kodeId = params.id;
|
||||
const dataOtp = await auth_getCodeOtpByNumber({ kodeId: kodeId });
|
||||
|
||||
return <Validasi dataOtp={dataOtp as any} />;
|
||||
}
|
||||
5
src/app/(user)/validasi/page.tsx
Normal file
5
src/app/(user)/validasi/page.tsx
Normal file
@@ -0,0 +1,5 @@
|
||||
import { Validasi } from "@/app_modules/auth";
|
||||
|
||||
export default async function Page() {
|
||||
return <Validasi />;
|
||||
}
|
||||
19
src/app/(user)/waiting-room/page.tsx
Normal file
19
src/app/(user)/waiting-room/page.tsx
Normal file
@@ -0,0 +1,19 @@
|
||||
import { funGetUserIdByToken } from "@/app_modules/_global/fun/get";
|
||||
import { funGlobal_checkActivationUseById } from "@/app_modules/_global/fun/get/fun_check_activation_use_by_id";
|
||||
import WaitingRoom_View from "@/app_modules/waiting_room/view";
|
||||
|
||||
export default async function Page() {
|
||||
const userLoginId = await funGetUserIdByToken();
|
||||
const activationUser = await funGlobal_checkActivationUseById({
|
||||
userId: userLoginId as string,
|
||||
});
|
||||
|
||||
return (
|
||||
<>
|
||||
<WaitingRoom_View
|
||||
activationUser={activationUser as boolean}
|
||||
userLoginId={userLoginId as string}
|
||||
/>
|
||||
</>
|
||||
);
|
||||
}
|
||||
21
src/app/api/auth/check/route.ts
Normal file
21
src/app/api/auth/check/route.ts
Normal file
@@ -0,0 +1,21 @@
|
||||
import { prisma } from "@/app/lib";
|
||||
import { data } from "autoprefixer";
|
||||
import { NextResponse } from "next/server";
|
||||
|
||||
export async function GET(request: Request) {
|
||||
const { searchParams } = new URL(request.url);
|
||||
const id = searchParams.get("id");
|
||||
|
||||
try {
|
||||
const data = await prisma.kodeOtp.findFirst({
|
||||
where: {
|
||||
id: id as string,
|
||||
},
|
||||
});
|
||||
return new Response(JSON.stringify({ data }), { status: 200 });
|
||||
} catch (error) {
|
||||
console.log(error);
|
||||
}
|
||||
|
||||
return new Response(JSON.stringify({ data: null }), { status: 404 });
|
||||
}
|
||||
@@ -1,31 +1,64 @@
|
||||
|
||||
|
||||
import { prisma } from "@/app/lib";
|
||||
import { randomOTP } from "@/app_modules/auth/fun/rondom_otp";
|
||||
import { NextResponse } from "next/server";
|
||||
|
||||
export async function POST(req: Request) {
|
||||
if (req.method === "POST") {
|
||||
const codeOtp = randomOTP();
|
||||
const body = await req.json();
|
||||
// console.log(body);
|
||||
const { nomor } = body;
|
||||
|
||||
if (body.nomor === "1234567890") {
|
||||
return NextResponse.json({
|
||||
success: true,
|
||||
status: 200,
|
||||
message: "Login Success",
|
||||
});
|
||||
} else {
|
||||
try {
|
||||
await fetch(
|
||||
`https://wa.wibudev.com/code?nom=${body.nomor}&text=Masukan Kode OTP:${body.otp}`
|
||||
try {
|
||||
const res = await fetch(
|
||||
`https://wa.wibudev.com/code?nom=${nomor}&text=HIPMI - Kode ini bersifat RAHASIA dan JANGAN DI BAGIKAN KEPADA SIAPAPUN, termasuk anggota ataupun pengurus HIPMI lainnya.
|
||||
\n
|
||||
>> Kode OTP anda: ${codeOtp}.
|
||||
`
|
||||
);
|
||||
|
||||
const sendWa = await res.json();
|
||||
if (sendWa.status !== "success")
|
||||
return new Response(
|
||||
JSON.stringify({
|
||||
success: false,
|
||||
message: "Nomor Whatsapp Tidak Aktif",
|
||||
}),
|
||||
{ status: 400 }
|
||||
);
|
||||
return NextResponse.json({
|
||||
body,
|
||||
status: 200,
|
||||
message: "Login Success",
|
||||
});
|
||||
} catch (error) {
|
||||
return NextResponse.json({ status: 500, message: "Server Error !!!" });
|
||||
}
|
||||
|
||||
const createOtpId = await prisma.kodeOtp.create({
|
||||
data: {
|
||||
nomor: nomor,
|
||||
otp: codeOtp,
|
||||
},
|
||||
});
|
||||
|
||||
if (!createOtpId)
|
||||
return new Response(
|
||||
JSON.stringify({
|
||||
success: false,
|
||||
message: "Gagal Membuat Kode OTP",
|
||||
}),
|
||||
{ status: 400 }
|
||||
);
|
||||
|
||||
return new Response(
|
||||
JSON.stringify({
|
||||
success: true,
|
||||
message: "Kode Verifikasi Dikirim",
|
||||
kodeId: createOtpId.id,
|
||||
}),
|
||||
{ status: 200 }
|
||||
);
|
||||
} catch (error) {
|
||||
console.log(error);
|
||||
return new Response(
|
||||
JSON.stringify({
|
||||
success: false,
|
||||
message: "Server Whatsapp Error !!",
|
||||
}),
|
||||
{ status: 500 }
|
||||
);
|
||||
}
|
||||
}
|
||||
return NextResponse.json({ success: false });
|
||||
|
||||
@@ -1,12 +1,28 @@
|
||||
import { prisma } from "@/app/lib";
|
||||
import { cookies } from "next/headers";
|
||||
import { NextResponse } from "next/server";
|
||||
export async function GET(request: Request) {
|
||||
const { searchParams } = new URL(request.url);
|
||||
const id = searchParams.get("id");
|
||||
|
||||
export async function GET() {
|
||||
cookies().set({
|
||||
name: "mySession",
|
||||
value: "",
|
||||
maxAge: 0,
|
||||
});
|
||||
const delToken = await prisma.userSession.delete({
|
||||
where: {
|
||||
userId: id as string,
|
||||
},
|
||||
});
|
||||
|
||||
return NextResponse.json({ status: 200, message: "Logout" });
|
||||
const del = cookies().delete(process.env.NEXT_PUBLIC_BASE_SESSION_KEY!);
|
||||
return new Response(JSON.stringify({ success: true, message: "Logout Berhasil" }), {status: 200});
|
||||
}
|
||||
|
||||
// import { cookies } from "next/headers";
|
||||
// import { NextResponse } from "next/server";
|
||||
|
||||
// export async function GET() {
|
||||
// cookies().set({
|
||||
// name: "mySession",
|
||||
// value: "",
|
||||
// maxAge: 0,
|
||||
// });
|
||||
|
||||
// return NextResponse.json({ status: 200, message: "Logout" });
|
||||
// }
|
||||
|
||||
@@ -1,51 +1,69 @@
|
||||
import { sessionCreate } from "@/app/auth/_lib/session_create";
|
||||
import prisma from "@/app/lib/prisma";
|
||||
import { ServerEnv } from "@/app/lib/server_env";
|
||||
import { sealData } from "iron-session";
|
||||
import { cookies } from "next/headers";
|
||||
import { NextResponse } from "next/server";
|
||||
|
||||
export async function POST(req: Request) {
|
||||
if (req.method === "POST") {
|
||||
const body = await req.json();
|
||||
// MyConsole(body);
|
||||
const { data } = await req.json();
|
||||
|
||||
const cekUsername = await prisma.user.findUnique({
|
||||
where: {
|
||||
username: body.username,
|
||||
username: data.username,
|
||||
},
|
||||
});
|
||||
|
||||
if (cekUsername)
|
||||
return NextResponse.json({ status: 400, message: "Username sudah ada" });
|
||||
return new Response(
|
||||
JSON.stringify({
|
||||
success: false,
|
||||
message: "Username sudah digunakan",
|
||||
}),
|
||||
{ status: 400 }
|
||||
);
|
||||
|
||||
const data = await prisma.user.create({
|
||||
const createUser = await prisma.user.create({
|
||||
data: {
|
||||
username: body.username,
|
||||
nomor: body.nomor,
|
||||
username: data.username,
|
||||
nomor: data.nomor,
|
||||
},
|
||||
});
|
||||
|
||||
if (data) {
|
||||
const seal = await sealData(
|
||||
JSON.stringify({
|
||||
id: data.id,
|
||||
username: data.username,
|
||||
}),
|
||||
{
|
||||
password: ServerEnv.value?.WIBU_PWD as string,
|
||||
}
|
||||
);
|
||||
const token = await sessionCreate({
|
||||
sessionKey: process.env.NEXT_PUBLIC_BASE_SESSION_KEY!,
|
||||
encodedKey: process.env.NEXT_PUBLIC_BASE_TOKEN_KEY!,
|
||||
user: createUser as any,
|
||||
});
|
||||
|
||||
cookies().set({
|
||||
name: "mySession",
|
||||
value: seal,
|
||||
maxAge: 60 * 60 * 24 * 7,
|
||||
try {
|
||||
const createUserSession = await prisma.userSession.create({
|
||||
data: {
|
||||
token: token as string,
|
||||
userId: createUser.id,
|
||||
},
|
||||
});
|
||||
|
||||
return NextResponse.json({ status: 201 });
|
||||
if (!createUserSession)
|
||||
return new Response(
|
||||
JSON.stringify({
|
||||
success: false,
|
||||
message: "Gagal Membuat Session",
|
||||
}),
|
||||
{ status: 400 }
|
||||
);
|
||||
} catch (error) {
|
||||
console.log(error);
|
||||
}
|
||||
|
||||
return NextResponse.json({ success: true });
|
||||
return new Response(
|
||||
JSON.stringify({
|
||||
success: true,
|
||||
message: "Berhasil Login",
|
||||
}),
|
||||
|
||||
{ status: 200 }
|
||||
);
|
||||
}
|
||||
return NextResponse.json({ success: false });
|
||||
return new Response(
|
||||
JSON.stringify({ success: false, message: "Method Not Allowed" }),
|
||||
{ status: 405 }
|
||||
);
|
||||
}
|
||||
|
||||
65
src/app/api/auth/resend/route.ts
Normal file
65
src/app/api/auth/resend/route.ts
Normal file
@@ -0,0 +1,65 @@
|
||||
import { prisma } from "@/app/lib";
|
||||
import { randomOTP } from "@/app_modules/auth/fun/rondom_otp";
|
||||
import { NextResponse } from "next/server";
|
||||
|
||||
export async function POST(req: Request) {
|
||||
if (req.method === "POST") {
|
||||
const codeOtp = randomOTP();
|
||||
const body = await req.json();
|
||||
const { nomor } = body;
|
||||
|
||||
try {
|
||||
const res = await fetch(
|
||||
`https://wa.wibudev.com/code?nom=${nomor}&text=HIPMI - Kode ini bersifat RAHASIA dan JANGAN DI BAGIKAN KEPADA SIAPAPUN, termasuk anggota ataupun pengurus HIPMI lainnya.
|
||||
\n
|
||||
>> Kode OTP anda: ${codeOtp}.
|
||||
`
|
||||
);
|
||||
|
||||
const sendWa = await res.json();
|
||||
if (sendWa.status !== "success")
|
||||
return new Response(
|
||||
JSON.stringify({
|
||||
success: false,
|
||||
message: "Nomor Whatsapp Tidak Aktif",
|
||||
}),
|
||||
{ status: 400 }
|
||||
);
|
||||
|
||||
const createOtpId = await prisma.kodeOtp.create({
|
||||
data: {
|
||||
nomor: nomor,
|
||||
otp: codeOtp,
|
||||
},
|
||||
});
|
||||
|
||||
if (!createOtpId)
|
||||
return new Response(
|
||||
JSON.stringify({
|
||||
success: false,
|
||||
message: "Gagal Membuat Kode OTP",
|
||||
}),
|
||||
{ status: 400 }
|
||||
);
|
||||
|
||||
return new Response(
|
||||
JSON.stringify({
|
||||
success: true,
|
||||
message: "Kode Verifikasi Dikirim",
|
||||
kodeId: createOtpId.id,
|
||||
}),
|
||||
{ status: 200 }
|
||||
);
|
||||
} catch (error) {
|
||||
console.log(error);
|
||||
return new Response(
|
||||
JSON.stringify({
|
||||
success: false,
|
||||
message: "Server Whatsapp Error !!",
|
||||
}),
|
||||
{ status: 500 }
|
||||
);
|
||||
}
|
||||
}
|
||||
return NextResponse.json({ success: false });
|
||||
}
|
||||
@@ -1,3 +1,4 @@
|
||||
import { sessionCreate } from "@/app/auth/_lib/session_create";
|
||||
import prisma from "@/app/lib/prisma";
|
||||
import { ServerEnv } from "@/app/lib/server_env";
|
||||
import { sealData } from "iron-session";
|
||||
@@ -7,45 +8,100 @@ import { NextResponse } from "next/server";
|
||||
|
||||
export async function POST(req: Request) {
|
||||
if (req.method === "POST") {
|
||||
const body = await req.json();
|
||||
const { nomor } = await req.json();
|
||||
|
||||
const data = await prisma.user.findUnique({
|
||||
const dataUser = await prisma.user.findUnique({
|
||||
where: {
|
||||
nomor: body.nomor,
|
||||
nomor: nomor,
|
||||
},
|
||||
select: {
|
||||
id: true,
|
||||
nomor: true,
|
||||
username: true,
|
||||
active: true,
|
||||
masterUserRoleId: true,
|
||||
},
|
||||
});
|
||||
|
||||
if (!data) return NextResponse.json({ status: 404 });
|
||||
|
||||
if (data) {
|
||||
const res = await sealData(
|
||||
JSON.stringify({
|
||||
id: data.id,
|
||||
username: data.username,
|
||||
}),
|
||||
{
|
||||
password: ServerEnv.value?.WIBU_PWD as string,
|
||||
}
|
||||
if (dataUser === null)
|
||||
return new Response(
|
||||
JSON.stringify({ success: false, message: "Nomor Belum Terdaftar" }),
|
||||
{ status: 404 }
|
||||
);
|
||||
|
||||
cookies().set({
|
||||
name: "mySession",
|
||||
value: res,
|
||||
maxAge: 60 * 60 * 24 * 7,
|
||||
const token = await sessionCreate({
|
||||
sessionKey: process.env.NEXT_PUBLIC_BASE_SESSION_KEY!,
|
||||
encodedKey: process.env.NEXT_PUBLIC_BASE_TOKEN_KEY!,
|
||||
user: dataUser as any,
|
||||
});
|
||||
|
||||
const cekSessionUser = await prisma.userSession.findFirst({
|
||||
where: {
|
||||
userId: dataUser.id,
|
||||
},
|
||||
});
|
||||
|
||||
if (cekSessionUser !== null) {
|
||||
await prisma.userSession.delete({
|
||||
where: {
|
||||
userId: dataUser.id,
|
||||
},
|
||||
});
|
||||
|
||||
revalidatePath("/dev/home");
|
||||
|
||||
return NextResponse.json({ status: 200, data });
|
||||
}
|
||||
|
||||
return NextResponse.json({ success: true });
|
||||
try {
|
||||
const createUserSession = await prisma.userSession.create({
|
||||
data: {
|
||||
token: token as string,
|
||||
userId: dataUser.id,
|
||||
},
|
||||
});
|
||||
|
||||
if (!createUserSession)
|
||||
return new Response(
|
||||
JSON.stringify({ success: false, message: "Gagal Membuat Session" }),
|
||||
{ status: 400 }
|
||||
);
|
||||
} catch (error) {
|
||||
console.log(error);
|
||||
}
|
||||
|
||||
// if (data) {
|
||||
// const res = await sealData(
|
||||
// JSON.stringify({
|
||||
// id: data.id,
|
||||
// username: data.username,
|
||||
// }),
|
||||
// {
|
||||
// password: ServerEnv.value?.WIBU_PWD as string,
|
||||
// }
|
||||
// );
|
||||
|
||||
// cookies().set({
|
||||
// name: "mySession",
|
||||
// value: res,
|
||||
// maxAge: 60 * 60 * 24 * 7,
|
||||
// });
|
||||
|
||||
// revalidatePath("/dev/home");
|
||||
|
||||
// return NextResponse.json({ status: 200, data });
|
||||
// }
|
||||
|
||||
// return NextResponse.json({ success: true });
|
||||
return new Response(
|
||||
JSON.stringify({
|
||||
success: true,
|
||||
message: "Berhasil Login",
|
||||
roleId: dataUser.masterUserRoleId,
|
||||
active: dataUser.active,
|
||||
}),
|
||||
{ status: 200 }
|
||||
);
|
||||
}
|
||||
return NextResponse.json({ success: false });
|
||||
return new Response(
|
||||
JSON.stringify({ success: false, message: "Method Not Allowed" }),
|
||||
{ status: 405 }
|
||||
);
|
||||
}
|
||||
|
||||
7
src/app/api/validasi/route.ts
Normal file
7
src/app/api/validasi/route.ts
Normal file
@@ -0,0 +1,7 @@
|
||||
export async function GET(req: Request) {
|
||||
const auth = req.headers.get("Authorization");
|
||||
const token = auth?.split(" ")[1];
|
||||
if (!token)
|
||||
return new Response(JSON.stringify({ success: false }), { status: 401 });
|
||||
return new Response(JSON.stringify({ success: true }));
|
||||
}
|
||||
22
src/app/auth/_lib/decrypt.ts
Normal file
22
src/app/auth/_lib/decrypt.ts
Normal file
@@ -0,0 +1,22 @@
|
||||
import { jwtVerify } from "jose";
|
||||
|
||||
export async function decrypt({
|
||||
token,
|
||||
encodedKey,
|
||||
}: {
|
||||
token: string;
|
||||
encodedKey: string;
|
||||
}): Promise<Record<string, any> | null> {
|
||||
try {
|
||||
const enc = new TextEncoder().encode(encodedKey);
|
||||
const { payload } = await jwtVerify(token, enc, {
|
||||
algorithms: ["HS256"],
|
||||
});
|
||||
return (payload.user as Record<string, any>) || null;
|
||||
} catch (error) {
|
||||
console.error("Gagal verifikasi session", error);
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
// wibu:0.2.82
|
||||
25
src/app/auth/_lib/encrypt.ts
Normal file
25
src/app/auth/_lib/encrypt.ts
Normal file
@@ -0,0 +1,25 @@
|
||||
import { SignJWT } from "jose";
|
||||
|
||||
export async function encrypt({
|
||||
user,
|
||||
exp = "7 year",
|
||||
encodedKey,
|
||||
}: {
|
||||
user: Record<string, any>;
|
||||
exp?: string;
|
||||
encodedKey: string;
|
||||
}): Promise<string | null> {
|
||||
try {
|
||||
const enc = new TextEncoder().encode(encodedKey);
|
||||
return new SignJWT({ user })
|
||||
.setProtectedHeader({ alg: "HS256" })
|
||||
.setIssuedAt()
|
||||
.setExpirationTime(exp)
|
||||
.sign(enc);
|
||||
} catch (error) {
|
||||
console.error("Gagal mengenkripsi", error);
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
// wibu:0.2.82
|
||||
35
src/app/auth/_lib/session_create.ts
Normal file
35
src/app/auth/_lib/session_create.ts
Normal file
@@ -0,0 +1,35 @@
|
||||
import { cookies } from "next/headers";
|
||||
import { encrypt } from "./encrypt";
|
||||
|
||||
export async function sessionCreate({
|
||||
sessionKey,
|
||||
exp = "7 year",
|
||||
encodedKey,
|
||||
user,
|
||||
}: {
|
||||
sessionKey: string;
|
||||
exp?: string;
|
||||
encodedKey: string;
|
||||
user: Record<string, unknown>;
|
||||
}) {
|
||||
const token = await encrypt({
|
||||
exp,
|
||||
encodedKey,
|
||||
user,
|
||||
});
|
||||
|
||||
const cookie: any = {
|
||||
key: sessionKey,
|
||||
value: token,
|
||||
options: {
|
||||
httpOnly: true,
|
||||
sameSite: "lax",
|
||||
path: "/",
|
||||
},
|
||||
};
|
||||
|
||||
cookies().set(cookie.key, cookie.value, { ...cookie.options });
|
||||
return token;
|
||||
}
|
||||
|
||||
// wibu:0.2.82
|
||||
27
src/app/auth/api/login/route.ts
Normal file
27
src/app/auth/api/login/route.ts
Normal file
@@ -0,0 +1,27 @@
|
||||
import { prisma } from "@/app/lib";
|
||||
import { sessionCreate } from "../../_lib/session_create";
|
||||
|
||||
export async function POST(req: Request) {
|
||||
const user = await prisma.user.findUnique({
|
||||
where: {
|
||||
nomor: "6281339158911",
|
||||
},
|
||||
select: {
|
||||
id: true,
|
||||
nomor: true,
|
||||
},
|
||||
});
|
||||
|
||||
if (!user)
|
||||
return new Response(
|
||||
JSON.stringify({ success: false, message: "User not found" }), {status: 404}
|
||||
);
|
||||
|
||||
const token = await sessionCreate({
|
||||
sessionKey: process.env.NEXT_PUBLIC_BASE_SESSION_KEY!,
|
||||
encodedKey: process.env.NEXT_PUBLIC_BASE_TOKEN_KEY!,
|
||||
user: user as any,
|
||||
});
|
||||
|
||||
return new Response(JSON.stringify({ success: true, token }));
|
||||
}
|
||||
5
src/app/auth/api/logout/route.ts
Normal file
5
src/app/auth/api/logout/route.ts
Normal file
@@ -0,0 +1,5 @@
|
||||
import { cookies } from "next/headers";
|
||||
export async function GET() {
|
||||
const del = cookies().delete(process.env.NEXT_PUBLIC_BASE_SESSION_KEY!);
|
||||
return new Response(JSON.stringify({ success: true }));
|
||||
}
|
||||
39
src/app/auth/login/page.tsx
Normal file
39
src/app/auth/login/page.tsx
Normal file
@@ -0,0 +1,39 @@
|
||||
"use client";
|
||||
import { Button } from "@mantine/core";
|
||||
import { useState } from "react";
|
||||
|
||||
export default function Page() {
|
||||
const [loading, setLoading] = useState(false);
|
||||
|
||||
|
||||
async function login() {
|
||||
setLoading(true);
|
||||
try {
|
||||
const res = await fetch("/auth/api/login", {
|
||||
method: "POST",
|
||||
});
|
||||
|
||||
const dataText = await res.text();
|
||||
|
||||
if (!res.ok) {
|
||||
console.error(dataText);
|
||||
throw new Error(res.statusText);
|
||||
}
|
||||
|
||||
const dataJson = JSON.parse(dataText);
|
||||
console.log(dataJson);
|
||||
// window.location.replace("/dev/home");
|
||||
} catch (error) {
|
||||
console.error(error);
|
||||
} finally {
|
||||
setLoading(false);
|
||||
}
|
||||
}
|
||||
return (
|
||||
<>
|
||||
<Button loading={loading} onClick={login}>
|
||||
Login
|
||||
</Button>
|
||||
</>
|
||||
);
|
||||
}
|
||||
@@ -6,9 +6,9 @@ import { redirect } from "next/navigation";
|
||||
export default async function Page() {
|
||||
const version = versionUpdate.version;
|
||||
|
||||
const checkCookies = await funCheckCookies();
|
||||
console.log(checkCookies, "ini halaman login");
|
||||
if (!checkCookies) return redirect("/");
|
||||
// const checkCookies = await funCheckCookies();
|
||||
// console.log(checkCookies, "ini halaman login");
|
||||
// if (!checkCookies) return redirect("/");
|
||||
|
||||
return (
|
||||
<>
|
||||
|
||||
@@ -4,5 +4,5 @@ import { auth_getCodeOtpByNumber } from "@/app_modules/auth/fun/get_kode_otp_by_
|
||||
export default async function Page({ params }: { params: { id: string } }) {
|
||||
let otpId = params.id;
|
||||
const dataOtp = await auth_getCodeOtpByNumber({ kodeId: otpId });
|
||||
return <Register dataOtp={dataOtp} />;
|
||||
return <Register />;
|
||||
}
|
||||
|
||||
@@ -3,7 +3,7 @@ import { SplashScreen } from "@/app_modules/auth";
|
||||
export default async function PageSplash() {
|
||||
return (
|
||||
<>
|
||||
<SplashScreen checkCookies/>
|
||||
<SplashScreen />
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
||||
@@ -5,6 +5,5 @@ export default async function Page({ params }: { params: { id: string } }) {
|
||||
let kodeId = params.id;
|
||||
const dataOtp = await auth_getCodeOtpByNumber({ kodeId: kodeId });
|
||||
|
||||
|
||||
return <Validasi dataOtp={dataOtp as any} />;
|
||||
return <Validasi />;
|
||||
}
|
||||
|
||||
@@ -6,16 +6,16 @@ import { CheckCookies_UiView } from "@/app_modules/check_cookies";
|
||||
import { redirect } from "next/navigation";
|
||||
|
||||
export default async function Page() {
|
||||
const userLoginId = await funGetUserIdByToken();
|
||||
const dataUser = await funGlobal_getUserById({ userId: userLoginId });
|
||||
// const userLoginId = await funGetUserIdByToken();
|
||||
// const dataUser = await funGlobal_getUserById({ userId: userLoginId });
|
||||
|
||||
if (dataUser?.masterUserRoleId === "1") {
|
||||
return redirect(RouterHome.main_home);
|
||||
}
|
||||
// if (dataUser?.masterUserRoleId === "1") {
|
||||
// return redirect(RouterHome.main_home);
|
||||
// }
|
||||
|
||||
if (dataUser?.masterUserRoleId !== "1") {
|
||||
return redirect(RouterAdminDashboard.splash_admin);
|
||||
}
|
||||
// if (dataUser?.masterUserRoleId !== "1") {
|
||||
// return redirect(RouterAdminDashboard.splash_admin);
|
||||
// }
|
||||
|
||||
// return <CheckCookies_UiView />;
|
||||
}
|
||||
|
||||
@@ -16,7 +16,7 @@ export default async function Page({ params }: { params: { id: string } }) {
|
||||
page: 1,
|
||||
});
|
||||
|
||||
dataPosting?.isActive === false && redirect(RouterForum.beranda);
|
||||
// dataPosting?.isActive === false && redirect(RouterForum.beranda);
|
||||
|
||||
const countKomentar = await forum_countTotalKomenById(postingId);
|
||||
|
||||
|
||||
@@ -1,10 +1,14 @@
|
||||
import { RouterAdminDashboard } from "@/app/lib/router_hipmi/router_admin";
|
||||
import { funGetUserIdByToken } from "@/app_modules/_global/fun/get";
|
||||
import { HomeView } from "@/app_modules/home";
|
||||
import { user_getOneByUserId } from "@/app_modules/home/fun/get/get_one_user_by_id";
|
||||
import { job_getTwoForHomeView } from "@/app_modules/job/fun/get/get_two_for_home_view";
|
||||
import notifikasi_countUserNotifikasi from "@/app_modules/notifikasi/fun/count/fun_count_by_id";
|
||||
|
||||
export default async function Page() {
|
||||
import { cookies } from "next/headers";
|
||||
import { redirect } from "next/navigation";
|
||||
|
||||
export default async function PageHome() {
|
||||
const userLoginId = await funGetUserIdByToken();
|
||||
const dataUser = await user_getOneByUserId(userLoginId as string);
|
||||
const dataJob = await job_getTwoForHomeView();
|
||||
@@ -16,8 +20,8 @@ export default async function Page() {
|
||||
// if (dataUser?.active === false) {
|
||||
// return redirect(RouterHome.home_user_non_active);
|
||||
// }
|
||||
// if (dataUser?.masterUserRoleId === "2" || dataUser?.masterUserRoleId === "3")
|
||||
// return redirect(RouterAdminDashboard.splash_admin);
|
||||
if (dataUser?.masterUserRoleId === "2" || dataUser?.masterUserRoleId === "3")
|
||||
return redirect(RouterAdminDashboard.main_admin);
|
||||
|
||||
return (
|
||||
<>
|
||||
|
||||
@@ -1,28 +1,23 @@
|
||||
import { funGetUserIdByToken } from "@/app_modules/_global/fun/get";
|
||||
import { funCheckCookies } from "@/app_modules/_global/fun/get/fun_check_cookies";
|
||||
import { permanentRedirect, redirect } from "next/navigation";
|
||||
import { funGlobal_getUserById } from "@/app_modules/_global/fun/get/fun_get_user_by_id";
|
||||
import { redirect } from "next/navigation";
|
||||
import { RealtimeProvider } from "../lib";
|
||||
import { ServerEnv } from "../lib/server_env";
|
||||
import { funGlobal_getUserById } from "@/app_modules/_global/fun/get/fun_get_user_by_id";
|
||||
import { RouterHome } from "../lib/router_hipmi/router_home";
|
||||
import { CheckCookies_UiLayout } from "@/app_modules/check_cookies";
|
||||
import { RouterAdminDashboard } from "../lib/router_hipmi/router_admin";
|
||||
import { funGlobal_checkActivationUseById } from "@/app_modules/_global/fun/get/fun_check_activation_use_by_id";
|
||||
|
||||
export default async function Layout({
|
||||
children,
|
||||
}: {
|
||||
children: React.ReactNode;
|
||||
}) {
|
||||
const checkCookies = await funCheckCookies();
|
||||
const userLoginId = await funGetUserIdByToken();
|
||||
if (!checkCookies) return redirect("/");
|
||||
|
||||
// const dataUser = await funGlobal_getUserById({ userId: userLoginId });
|
||||
// console.log(dataUser?.active, dataUser?.username, "ini di layout");
|
||||
|
||||
// if(dataUser?.active == false) return permanentRedirect(RouterHome.home_user_non_active);
|
||||
// const WIBU_REALTIME_TOKEN = process.env.NEXT_PUBLIC_WIBU_REALTIME_TOKEN;
|
||||
// console.log(WIBU_REALTIME_TOKEN, "check cookies di layout dalam");
|
||||
|
||||
const activationUser = await funGlobal_checkActivationUseById({
|
||||
userId: userLoginId as string,
|
||||
});
|
||||
console.log(activationUser, "ini di layout");
|
||||
if (activationUser == false) return redirect("/waiting-room");
|
||||
|
||||
return (
|
||||
<>
|
||||
<RealtimeProvider
|
||||
|
||||
@@ -1,6 +1,4 @@
|
||||
import { Home_UserNonActive } from "@/app_modules/home";
|
||||
// import { redirect } from "next/navigation";
|
||||
|
||||
export default async function Page() {
|
||||
return (
|
||||
<>
|
||||
|
||||
@@ -16,7 +16,7 @@ export default async function Layout({
|
||||
<>
|
||||
<LayoutVote_DetailSemuaRiwayat
|
||||
votingId={votingId}
|
||||
userLoginId={userLoginId}
|
||||
userLoginId={userLoginId as string}
|
||||
>
|
||||
{children}
|
||||
</LayoutVote_DetailSemuaRiwayat>
|
||||
|
||||
@@ -1,13 +1,8 @@
|
||||
import MqttLoader from "@/util/mqtt_loader";
|
||||
import RootStyleRegistry from "./emotion";
|
||||
// import "./globals.css";
|
||||
import { TokenProvider } from "./lib/token";
|
||||
import dotenv from "dotenv";
|
||||
import { ServerEnv } from "./lib/server_env";
|
||||
import { RealtimeProvider } from "./lib";
|
||||
import { funGetUserIdByToken } from "@/app_modules/_global/fun/get";
|
||||
import { funCheckCookies } from "@/app_modules/_global/fun/get/fun_check_cookies";
|
||||
import { redirect } from "next/navigation";
|
||||
import { TokenProvider } from "./lib/token";
|
||||
dotenv.config({
|
||||
path: ".env",
|
||||
});
|
||||
|
||||
@@ -1,24 +1,10 @@
|
||||
import { funCheckCookies } from "@/app_modules/_global/fun/get/fun_check_cookies";
|
||||
import PageSplash from "./dev/auth/splash/page";
|
||||
import { redirect } from "next/navigation";
|
||||
import { Login, SplashScreen } from "@/app_modules/auth";
|
||||
import { RouterAuth } from "./lib/router_hipmi/router_auth";
|
||||
import versionUpdate from "../../package.json";
|
||||
import { funGetUserIdByToken } from "@/app_modules/_global/fun/get";
|
||||
import { funGlobal_getUserById } from "@/app_modules/_global/fun/get/fun_get_user_by_id";
|
||||
import { RouterHome } from "./lib/router_hipmi/router_home";
|
||||
import { RouterAdminDashboard } from "./lib/router_hipmi/router_admin";
|
||||
|
||||
export default async function Page() {
|
||||
const version = versionUpdate.version;
|
||||
|
||||
const checkCookies = await funCheckCookies();
|
||||
// console.log(checkCookies, "ini check cookies di page awal");
|
||||
if (checkCookies) return redirect("/dev/check-cookies");
|
||||
return redirect("/login");
|
||||
// const WIBU_REALTIME_TOKEN = process.env.NEXT_PUBLIC_WIBU_REALTIME_TOKEN;
|
||||
|
||||
// return <Login version={version} />;
|
||||
// return <SplashScreen checkCookies={checkCookies} />;
|
||||
return <PageSplash />;
|
||||
return redirect("/dev/home");
|
||||
// return <PageSplash />;
|
||||
}
|
||||
|
||||
@@ -0,0 +1,22 @@
|
||||
"use server";
|
||||
|
||||
import { prisma } from "@/app/lib";
|
||||
import { RouterAuth } from "@/app/lib/router_hipmi/router_auth";
|
||||
import { permanentRedirect } from "next/navigation";
|
||||
|
||||
export async function funGlobal_checkActivationUseById({
|
||||
userId,
|
||||
}: {
|
||||
userId: string;
|
||||
}) {
|
||||
const data = await prisma.user.findFirst({
|
||||
where: {
|
||||
id: userId,
|
||||
},
|
||||
select: {
|
||||
active: true,
|
||||
},
|
||||
});
|
||||
|
||||
return data?.active;
|
||||
}
|
||||
@@ -1,26 +1,27 @@
|
||||
"use server";
|
||||
|
||||
import { prisma } from "@/app/lib";
|
||||
import { ServerEnv } from "@/app/lib/server_env";
|
||||
import { unsealData } from "iron-session";
|
||||
import { cookies } from "next/headers";
|
||||
|
||||
export async function funGetUserIdByToken() {
|
||||
const c = cookies().get("mySession");
|
||||
const c = cookies().get(process.env.NEXT_PUBLIC_BASE_SESSION_KEY!);
|
||||
|
||||
const token = JSON.parse(
|
||||
await unsealData(c?.value as string, {
|
||||
password: process.env.WIBU_PWD as string,
|
||||
})
|
||||
);
|
||||
// const token = JSON.parse(
|
||||
// await unsealData(c?.value as string, {
|
||||
// password: process.env.WIBU_PWD as string,
|
||||
// })
|
||||
// );
|
||||
// return token.id;
|
||||
|
||||
return token.id;
|
||||
// const token = c?.value
|
||||
// const cekToken = await prisma.userSession.findFirst({
|
||||
// where: {
|
||||
// token: token,
|
||||
// },
|
||||
// });
|
||||
const token = c?.value
|
||||
const cekToken = await prisma.userSession.findFirst({
|
||||
where: {
|
||||
token: token,
|
||||
},
|
||||
});
|
||||
|
||||
// if (cekToken === null) return null
|
||||
// return cekToken.userId;
|
||||
return cekToken?.userId
|
||||
}
|
||||
|
||||
@@ -1,14 +1,8 @@
|
||||
"use client";
|
||||
|
||||
import { RouterAuth } from "@/app/lib/router_hipmi/router_auth";
|
||||
import { Warna } from "@/app/lib/warna";
|
||||
import { AccentColor } from "@/app_modules/_global/color";
|
||||
import {
|
||||
ComponentGlobal_NotifikasiBerhasil,
|
||||
ComponentGlobal_NotifikasiPeringatan,
|
||||
} from "@/app_modules/_global/notif_global";
|
||||
import { auth_Logout } from "@/app_modules/auth/fun/fun_logout";
|
||||
import { gs_kodeId } from "@/app_modules/auth/state/state";
|
||||
import { ComponentGlobal_NotifikasiBerhasil } from "@/app_modules/_global/notif_global";
|
||||
import { MODEL_USER } from "@/app_modules/home/model/interface";
|
||||
import {
|
||||
ActionIcon,
|
||||
@@ -25,7 +19,6 @@ import {
|
||||
Title,
|
||||
} from "@mantine/core";
|
||||
import { IconPhone, IconUser, IconUserCircle } from "@tabler/icons-react";
|
||||
import { useAtom } from "jotai";
|
||||
import { useRouter } from "next/navigation";
|
||||
import { useState } from "react";
|
||||
|
||||
@@ -38,21 +31,18 @@ export function Admin_ComponentButtonUserCircle({
|
||||
const [isOpenMenuUser, setOpenMenuUser] = useState(false);
|
||||
const [openPop, setOpenPop] = useState(false);
|
||||
const [openModal, setOpenModal] = useState(false);
|
||||
const [loading, setLoading] = useState(false);
|
||||
const [kodeId, setKodeId] = useAtom(gs_kodeId);
|
||||
const [loadingLogout, setLoadingLogout] = useState(false);
|
||||
|
||||
async function onClickLogout() {
|
||||
const res = await auth_Logout();
|
||||
setLoadingLogout(true);
|
||||
const res = await fetch(`/api/auth/logout?id=${dataUser.id}`, {
|
||||
method: "GET",
|
||||
});
|
||||
|
||||
const result = await res.json();
|
||||
if (res.status === 200) {
|
||||
console.log(res);
|
||||
setLoadingLogout(true);
|
||||
ComponentGlobal_NotifikasiBerhasil(res.message);
|
||||
setKodeId("");
|
||||
setOpenModal(false);
|
||||
router.push(RouterAuth.login, { scroll: false });
|
||||
} else {
|
||||
ComponentGlobal_NotifikasiPeringatan(res.message);
|
||||
ComponentGlobal_NotifikasiBerhasil(result.message);
|
||||
router.push("/", { scroll: false });
|
||||
}
|
||||
}
|
||||
|
||||
@@ -114,7 +104,6 @@ export function Admin_ComponentButtonUserCircle({
|
||||
<Button
|
||||
onClick={() => {
|
||||
setOpenModal(false);
|
||||
setLoading(false);
|
||||
}}
|
||||
radius={50}
|
||||
>
|
||||
|
||||
@@ -4,6 +4,7 @@ import { gs_admin_ntf } from "@/app/lib/global_state";
|
||||
import {
|
||||
ActionIcon,
|
||||
AppShell,
|
||||
Button,
|
||||
Divider,
|
||||
Drawer,
|
||||
Grid,
|
||||
@@ -18,8 +19,10 @@ import {
|
||||
import { useMediaQuery, useShallowEffect } from "@mantine/hooks";
|
||||
import { IconBell } from "@tabler/icons-react";
|
||||
import { useAtom } from "jotai";
|
||||
import { useRouter } from "next/navigation";
|
||||
import { useState } from "react";
|
||||
import { AccentColor } from "../_global/color";
|
||||
import { ComponentGlobal_NotifikasiBerhasil } from "../_global/notif_global";
|
||||
import { MODEL_USER } from "../home/model/interface";
|
||||
import { MODEL_NOTIFIKASI } from "../notifikasi/model/interface";
|
||||
import {
|
||||
@@ -47,6 +50,7 @@ export function Admin_NewLayout({
|
||||
listNotifikasi: MODEL_NOTIFIKASI[];
|
||||
version: string;
|
||||
}) {
|
||||
const router = useRouter();
|
||||
const matches = useMediaQuery("(min-width: 1024px)");
|
||||
const [dataUser, setDataUser] = useState(user);
|
||||
const userRoleId = dataUser.masterUserRoleId;
|
||||
@@ -72,6 +76,20 @@ export function Admin_NewLayout({
|
||||
setDrawerNotifikasi(true);
|
||||
}
|
||||
|
||||
const [loadingLogout, setLoadingLogout] = useState(false);
|
||||
async function onClickLogout() {
|
||||
setLoadingLogout(true);
|
||||
const res = await fetch(`/api/auth/logout?id=${user.id}`, {
|
||||
method: "GET",
|
||||
});
|
||||
|
||||
const result = await res.json();
|
||||
if (res.status === 200) {
|
||||
ComponentGlobal_NotifikasiBerhasil(result.message);
|
||||
router.push("/", { scroll: false });
|
||||
}
|
||||
}
|
||||
|
||||
return (
|
||||
<>
|
||||
<AppShell
|
||||
@@ -168,6 +186,7 @@ export function Admin_NewLayout({
|
||||
<Title order={4} align="center">
|
||||
View Only Available For Desktop
|
||||
</Title>
|
||||
<Button onClick={() => onClickLogout()}>Logout</Button>
|
||||
</Stack>
|
||||
) : (
|
||||
children
|
||||
|
||||
@@ -2,12 +2,15 @@
|
||||
|
||||
import prisma from "@/app/lib/prisma";
|
||||
|
||||
export async function auth_funDeleteAktivasiKodeOtpById({
|
||||
export async function auth_funDeleteAktivasiKodeOtpByNomor({
|
||||
nomor,
|
||||
}: {
|
||||
nomor: string;
|
||||
}) {
|
||||
// console.log(otpId);
|
||||
|
||||
|
||||
|
||||
const updt = await prisma.kodeOtp.deleteMany({
|
||||
where: {
|
||||
nomor: nomor,
|
||||
|
||||
@@ -2,12 +2,12 @@ import SplashScreen from "./splash/view";
|
||||
import Login from "./login/view";
|
||||
import Validasi from "./validasi/view";
|
||||
import Register from "./register/view";
|
||||
import Component_Logout from "./logout/view";
|
||||
import Component_ButtonLogout from "./logout/view";
|
||||
|
||||
export {
|
||||
SplashScreen,
|
||||
Login,
|
||||
Validasi,
|
||||
Register,
|
||||
Component_Logout as Logout,
|
||||
Component_ButtonLogout as Logout,
|
||||
};
|
||||
|
||||
@@ -1,6 +1,5 @@
|
||||
"use client";
|
||||
|
||||
import { RouterAuth } from "@/app/lib/router_hipmi/router_auth";
|
||||
import {
|
||||
AccentColor,
|
||||
MainColor,
|
||||
@@ -8,10 +7,10 @@ import {
|
||||
import ComponentGlobal_ErrorInput from "@/app_modules/_global/component/error_input";
|
||||
import {
|
||||
ComponentGlobal_NotifikasiBerhasil,
|
||||
ComponentGlobal_NotifikasiGagal,
|
||||
ComponentGlobal_NotifikasiPeringatan,
|
||||
} from "@/app_modules/_global/notif_global";
|
||||
import { UIGlobal_LayoutDefault } from "@/app_modules/_global/ui";
|
||||
import { auth_funLogin } from "@/app_modules/auth/fun/fun_login";
|
||||
import { Box, Button, Center, Stack, Text, Title } from "@mantine/core";
|
||||
import { useRouter } from "next/navigation";
|
||||
import { useState } from "react";
|
||||
@@ -28,23 +27,28 @@ export default function Login({ version }: { version: string }) {
|
||||
const nomor = phone.substring(1);
|
||||
if (nomor.length <= 4) return setError(true);
|
||||
|
||||
const res = await auth_funLogin({ nomor: nomor });
|
||||
if (res.status === 200) {
|
||||
setLoading(true);
|
||||
ComponentGlobal_NotifikasiBerhasil(res.message, 2000);
|
||||
// router.push(RouterAuth.validasi + res.kodeId, { scroll: false });
|
||||
router.push("/validasi/" + res.kodeId, { scroll: false });
|
||||
} else {
|
||||
ComponentGlobal_NotifikasiPeringatan(res.message);
|
||||
}
|
||||
setLoading(true);
|
||||
try {
|
||||
const res = await fetch("/api/auth/login", {
|
||||
method: "POST",
|
||||
body: JSON.stringify({ nomor: nomor }),
|
||||
headers: {
|
||||
"Content-Type": "application/json",
|
||||
},
|
||||
});
|
||||
|
||||
// await fetch(ApiHipmi.login, {
|
||||
// method: "POST",
|
||||
// headers: {
|
||||
// "Content-Type": "application/json",
|
||||
// },
|
||||
// body: JSON.stringify(body),
|
||||
// })
|
||||
const result = await res.json();
|
||||
if (res.status === 200) {
|
||||
localStorage.setItem("hipmi_auth_code_id", result.kodeId);
|
||||
ComponentGlobal_NotifikasiBerhasil(result.message, 2000);
|
||||
router.push("/validasi", { scroll: false });
|
||||
} else {
|
||||
ComponentGlobal_NotifikasiPeringatan(result.message);
|
||||
}
|
||||
} catch (error) {
|
||||
console.error(error);
|
||||
ComponentGlobal_NotifikasiGagal("Terjadi Kesalahan");
|
||||
}
|
||||
}
|
||||
|
||||
return (
|
||||
@@ -96,16 +100,11 @@ export default function Login({ version }: { version: string }) {
|
||||
|
||||
<Box pos={"fixed"} bottom={10}>
|
||||
<Text fw={"bold"} c={"white"} fs={"italic"} fz={"xs"}>
|
||||
V.{version}
|
||||
v {version}
|
||||
</Text>
|
||||
</Box>
|
||||
</Stack>
|
||||
</UIGlobal_LayoutDefault>
|
||||
{/* <BackgroundImage
|
||||
src={"/aset/global/main_background.png"}
|
||||
h={"100vh"}
|
||||
// pos={"static"}
|
||||
></BackgroundImage> */}
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
||||
@@ -11,18 +11,21 @@ import { useState } from "react";
|
||||
import { auth_Logout } from "../fun/fun_logout";
|
||||
import { RouterAuth } from "@/app/lib/router_hipmi/router_auth";
|
||||
|
||||
export default function Component_Logout() {
|
||||
export default function Component_ButtonLogout({userId}: {userId: string}) {
|
||||
const router = useRouter();
|
||||
const [opened, setOpened] = useState(false);
|
||||
const [loading, setLoading] = useState(false);
|
||||
|
||||
async function onClickLogout() {
|
||||
const res = await auth_Logout();
|
||||
setLoading(true);
|
||||
const res = await fetch(`/api/auth/logout?id=${userId}`, {
|
||||
method: "GET",
|
||||
});
|
||||
|
||||
const result = await res.json();
|
||||
if (res.status === 200) {
|
||||
ComponentGlobal_NotifikasiBerhasil(res.message);
|
||||
router.push("/login", { scroll: false });
|
||||
} else {
|
||||
ComponentGlobal_NotifikasiPeringatan(res.message);
|
||||
ComponentGlobal_NotifikasiBerhasil(result.message);
|
||||
router.push("/", { scroll: false });
|
||||
}
|
||||
}
|
||||
|
||||
@@ -49,7 +52,6 @@ export default function Component_Logout() {
|
||||
bg={Warna.merah}
|
||||
color="red"
|
||||
onClick={() => {
|
||||
setLoading(true);
|
||||
onClickLogout();
|
||||
}}
|
||||
>
|
||||
|
||||
19
src/app_modules/auth/register/skeleton.tsx
Normal file
19
src/app_modules/auth/register/skeleton.tsx
Normal file
@@ -0,0 +1,19 @@
|
||||
import { Stack, Skeleton } from "@mantine/core";
|
||||
|
||||
export default function Register_SkeletonView() {
|
||||
return (
|
||||
<>
|
||||
<Stack h={"100vh"} align="center" justify="center" spacing={50}>
|
||||
<Skeleton h={30} w={250} radius={"xl"} />
|
||||
|
||||
<Skeleton h={100} w={100} radius={"50%"} />
|
||||
|
||||
<Stack spacing={"sm"}>
|
||||
<Skeleton h={20} w={300} radius={"xl"} />
|
||||
<Skeleton h={50} w={300} radius={"sm"} />
|
||||
<Skeleton h={50} w={300} radius={"sm"} />
|
||||
</Stack>
|
||||
</Stack>
|
||||
</>
|
||||
);
|
||||
}
|
||||
@@ -1,10 +1,7 @@
|
||||
"use client";
|
||||
|
||||
import { RouterHome } from "@/app/lib/router_hipmi/router_home";
|
||||
import { GlobalEnv } from "@/app/lib/token";
|
||||
import {
|
||||
AccentColor,
|
||||
MainColor,
|
||||
MainColor
|
||||
} from "@/app_modules/_global/color/color_pallet";
|
||||
import ComponentGlobal_ErrorInput from "@/app_modules/_global/component/error_input";
|
||||
import { ComponentGlobal_NotifikasiBerhasil } from "@/app_modules/_global/notif_global/notifikasi_berhasil";
|
||||
@@ -12,65 +9,95 @@ import { ComponentGlobal_NotifikasiPeringatan } from "@/app_modules/_global/noti
|
||||
import { UIGlobal_LayoutDefault } from "@/app_modules/_global/ui";
|
||||
import {
|
||||
Button,
|
||||
Center,
|
||||
Stack,
|
||||
Text,
|
||||
TextInput,
|
||||
Title
|
||||
} from "@mantine/core";
|
||||
import { useFocusTrap } from "@mantine/hooks";
|
||||
import { useFocusTrap, useShallowEffect } from "@mantine/hooks";
|
||||
import { IconUserCircle } from "@tabler/icons-react";
|
||||
import _ from "lodash";
|
||||
import { useRouter } from "next/navigation";
|
||||
import { useState } from "react";
|
||||
import { auth_funDeleteAktivasiKodeOtpById } from "../fun/fun_edit_aktivasi_kode_otp_by_id";
|
||||
import { Auth_funRegister } from "../fun/fun_register";
|
||||
import { auth_funDeleteAktivasiKodeOtpByNomor } from "../fun/fun_edit_aktivasi_kode_otp_by_id";
|
||||
import Register_SkeletonView from "./skeleton";
|
||||
|
||||
export default function Register({ dataOtp }: { dataOtp: any }) {
|
||||
export default function Register() {
|
||||
const router = useRouter();
|
||||
const [nomor, setNomor] = useState(dataOtp.nomor);
|
||||
const [nomor, setNomor] = useState("");
|
||||
const [value, setValue] = useState("");
|
||||
const [isValue, setIsValue] = useState(false);
|
||||
const focusTrapRef = useFocusTrap();
|
||||
const [loading, setLoading] = useState(false);
|
||||
|
||||
useShallowEffect(() => {
|
||||
const kodeId = localStorage.getItem("hipmi_auth_code_id");
|
||||
if (kodeId != null) {
|
||||
onCheckAuthCode({ kodeId: kodeId as string, onSetData: setNomor });
|
||||
} else {
|
||||
console.log("code id not found");
|
||||
}
|
||||
}, [setNomor]);
|
||||
|
||||
async function onCheckAuthCode({
|
||||
kodeId,
|
||||
onSetData,
|
||||
}: {
|
||||
kodeId: string;
|
||||
onSetData: any;
|
||||
}) {
|
||||
const res = await fetch(`/api/auth/check?id=${kodeId}`);
|
||||
const result = await res.json();
|
||||
|
||||
onSetData(result.data.nomor);
|
||||
}
|
||||
|
||||
async function onRegistarsi() {
|
||||
const body = {
|
||||
const data = {
|
||||
username: value,
|
||||
nomor: nomor,
|
||||
};
|
||||
|
||||
if (body.username === "") {
|
||||
setIsValue(true);
|
||||
return null;
|
||||
}
|
||||
if (body.username.length < 5) return null;
|
||||
if (_.values(body.username).includes(" ")) return null;
|
||||
|
||||
const res = await Auth_funRegister({
|
||||
data: body,
|
||||
HIPMI_PWD: GlobalEnv.value?.WIBU_PWD as string,
|
||||
});
|
||||
if (res.status === 200) {
|
||||
await auth_funDeleteAktivasiKodeOtpById({ nomor: nomor }).then((val) => {
|
||||
if (val.status === 200) {
|
||||
ComponentGlobal_NotifikasiBerhasil(res.message);
|
||||
setLoading(true);
|
||||
router.push(RouterHome.main_home, { scroll: false });
|
||||
} else {
|
||||
ComponentGlobal_NotifikasiPeringatan(val.message);
|
||||
}
|
||||
try {
|
||||
setLoading(true);
|
||||
const res = await fetch("/api/auth/register", {
|
||||
method: "POST",
|
||||
body: JSON.stringify({
|
||||
data,
|
||||
}),
|
||||
headers: {
|
||||
"Content-Type": "application/json",
|
||||
},
|
||||
});
|
||||
} else {
|
||||
ComponentGlobal_NotifikasiPeringatan(res.message);
|
||||
|
||||
const result = await res.json();
|
||||
|
||||
if (res.status === 200) {
|
||||
localStorage.removeItem("hipmi_auth_code_id");
|
||||
ComponentGlobal_NotifikasiBerhasil(result.message);
|
||||
router.push("/waiting-room", { scroll: false });
|
||||
|
||||
const resAktivasi = await auth_funDeleteAktivasiKodeOtpByNomor({
|
||||
nomor: data.nomor,
|
||||
});
|
||||
}
|
||||
|
||||
if(res.status === 400){
|
||||
setLoading(false);
|
||||
ComponentGlobal_NotifikasiPeringatan(result.message);
|
||||
}
|
||||
} catch (error) {
|
||||
console.log(error);
|
||||
}
|
||||
}
|
||||
|
||||
return (
|
||||
<>
|
||||
<UIGlobal_LayoutDefault>
|
||||
<Center h={"100vh"}>
|
||||
<Stack h={"100%"} align="center" justify="center" spacing={70}>
|
||||
{nomor == "" ? (
|
||||
<Register_SkeletonView />
|
||||
) : (
|
||||
<Stack h={"100vh"} align="center" justify="center" spacing={50}>
|
||||
<Title order={2} c={MainColor.yellow}>
|
||||
REGISTRASI
|
||||
</Title>
|
||||
@@ -78,7 +105,7 @@ export default function Register({ dataOtp }: { dataOtp: any }) {
|
||||
<IconUserCircle size={100} color="white" />
|
||||
|
||||
<Stack spacing={"sm"} w={300}>
|
||||
<Text fz={10} c={"white"}>
|
||||
<Text align="center" c={"white"}>
|
||||
Anda akan terdaftar dengan nomor berikut{" "}
|
||||
<Text inherit span fw={"bold"}>
|
||||
+{nomor}
|
||||
@@ -109,6 +136,11 @@ export default function Register({ dataOtp }: { dataOtp: any }) {
|
||||
/>
|
||||
<Stack>
|
||||
<Button
|
||||
disabled={
|
||||
value === "" ||
|
||||
value.length < 5 ||
|
||||
_.values(value).includes(" ")
|
||||
}
|
||||
loading={loading ? true : false}
|
||||
loaderPosition="center"
|
||||
radius={"md"}
|
||||
@@ -117,9 +149,6 @@ export default function Register({ dataOtp }: { dataOtp: any }) {
|
||||
c={"black"}
|
||||
bg={MainColor.yellow}
|
||||
color={"yellow"}
|
||||
style={{
|
||||
borderColor: AccentColor.yellow,
|
||||
}}
|
||||
onClick={() => {
|
||||
onRegistarsi();
|
||||
}}
|
||||
@@ -129,7 +158,7 @@ export default function Register({ dataOtp }: { dataOtp: any }) {
|
||||
</Stack>
|
||||
</Stack>
|
||||
</Stack>
|
||||
</Center>
|
||||
)}
|
||||
</UIGlobal_LayoutDefault>
|
||||
</>
|
||||
);
|
||||
|
||||
@@ -10,20 +10,16 @@ import { Avatar, BackgroundImage, Center, Image, Stack } from "@mantine/core";
|
||||
import { useShallowEffect } from "@mantine/hooks";
|
||||
import { useRouter } from "next/navigation";
|
||||
|
||||
export default function SplashScreen({
|
||||
checkCookies,
|
||||
}: {
|
||||
checkCookies: boolean;
|
||||
}) {
|
||||
export default function SplashScreen() {
|
||||
const router = useRouter();
|
||||
|
||||
useShallowEffect(() => {
|
||||
// if (!checkCookies) return router.push(RouterAuth.login, { scroll: false });
|
||||
// onCheckUser();
|
||||
|
||||
// setTimeout(() => {
|
||||
// router.push(RouterAuth.login, { scroll: false });
|
||||
// }, 1000);
|
||||
setTimeout(() => {
|
||||
router.push("/login", { scroll: false });
|
||||
}, 1000);
|
||||
// if (!userLoginId) {
|
||||
// setTimeout(() => {
|
||||
// router.push(RouterAuth.login, { scroll: false });
|
||||
|
||||
25
src/app_modules/auth/validasi/skeleton.tsx
Normal file
25
src/app_modules/auth/validasi/skeleton.tsx
Normal file
@@ -0,0 +1,25 @@
|
||||
import { Stack, Skeleton, Group } from "@mantine/core";
|
||||
|
||||
export default function Validasi_SkeletonView() {
|
||||
return (
|
||||
<>
|
||||
<Stack align="center" justify="center" h={"100vh"} spacing={50}>
|
||||
<Skeleton h={30} w={250} radius={"xl"} />
|
||||
<Stack>
|
||||
<Skeleton h={20} w={250} radius={"xl"} />
|
||||
<Skeleton h={20} w={250} radius={"xl"} />
|
||||
</Stack>
|
||||
|
||||
<Group>
|
||||
{Array.from({ length: 4 }).map((_, i) => (
|
||||
<Skeleton key={i} h={50} w={50} radius={"sm"} />
|
||||
))}
|
||||
</Group>
|
||||
|
||||
<Skeleton h={20} w={250} radius={"xl"} />
|
||||
|
||||
<Skeleton h={50} w={250} radius={"sm"} />
|
||||
</Stack>
|
||||
</>
|
||||
);
|
||||
}
|
||||
@@ -1,9 +1,7 @@
|
||||
"use client";
|
||||
|
||||
import { RouterAdminDashboard } from "@/app/lib/router_hipmi/router_admin";
|
||||
import { RouterAuth } from "@/app/lib/router_hipmi/router_auth";
|
||||
import { RouterHome } from "@/app/lib/router_hipmi/router_home";
|
||||
import { GlobalEnv } from "@/app/lib/token";
|
||||
import {
|
||||
AccentColor,
|
||||
MainColor,
|
||||
@@ -16,103 +14,175 @@ import {
|
||||
Box,
|
||||
Button,
|
||||
Center,
|
||||
Loader,
|
||||
PinInput,
|
||||
Stack,
|
||||
Text,
|
||||
Title,
|
||||
} from "@mantine/core";
|
||||
import { useFocusTrap, useShallowEffect } from "@mantine/hooks";
|
||||
import { Prisma } from "@prisma/client";
|
||||
import { IconChevronLeft } from "@tabler/icons-react";
|
||||
import { useRouter } from "next/navigation";
|
||||
import { useState } from "react";
|
||||
import { auth_funResendCode } from "../fun";
|
||||
import { auth_funDeleteAktivasiKodeOtpById } from "../fun/fun_edit_aktivasi_kode_otp_by_id";
|
||||
import { auth_funValidasi } from "../fun/fun_validasi";
|
||||
import { useEffect, useState } from "react";
|
||||
|
||||
export default function Validasi({
|
||||
dataOtp,
|
||||
}: {
|
||||
dataOtp: Prisma.KodeOtpSelect;
|
||||
}) {
|
||||
import Validasi_SkeletonView from "./skeleton";
|
||||
import { auth_funDeleteAktivasiKodeOtpByNomor } from "../fun/fun_edit_aktivasi_kode_otp_by_id";
|
||||
import { IconChevronLeft } from "@tabler/icons-react";
|
||||
import { ComponentGlobal_NotifikasiGagal } from "@/app_modules/_global/notif_global";
|
||||
import { auth_funResendCode } from "../fun";
|
||||
|
||||
export default function Validasi() {
|
||||
const router = useRouter();
|
||||
const nomor = dataOtp.nomor as any;
|
||||
const code = dataOtp.otp as any;
|
||||
const [inputCode, setInputOtp] = useState("");
|
||||
const focusTrapRef = useFocusTrap();
|
||||
const [loading, setLoading] = useState(false);
|
||||
const [counter, setCounter] = useState(7);
|
||||
const [loadingResend, setLoadingResend] = useState(false);
|
||||
const [triggerOtp, setTriggerOtp] = useState(false);
|
||||
|
||||
const [counter, setCounter] = useState(60);
|
||||
const [data, setData] = useState({
|
||||
nomor: "",
|
||||
code: "",
|
||||
});
|
||||
|
||||
useShallowEffect(() => {
|
||||
const kodeId = localStorage.getItem("hipmi_auth_code_id");
|
||||
if (kodeId != null) {
|
||||
onCheckAuthCode({ kodeId: kodeId as string, onSetData: setData });
|
||||
} else {
|
||||
console.log("code id not found");
|
||||
}
|
||||
|
||||
if (triggerOtp) {
|
||||
const kodeId = localStorage.getItem("hipmi_auth_code_id");
|
||||
if (kodeId != null) {
|
||||
onCheckAuthCode({ kodeId: kodeId as string, onSetData: setData });
|
||||
} else {
|
||||
console.log("code id not found");
|
||||
}
|
||||
setTriggerOtp(false);
|
||||
}
|
||||
}, [triggerOtp, setData, setTriggerOtp]);
|
||||
|
||||
async function onCheckAuthCode({
|
||||
kodeId,
|
||||
onSetData,
|
||||
}: {
|
||||
kodeId: string;
|
||||
onSetData: any;
|
||||
}) {
|
||||
const res = await fetch(`/api/auth/check?id=${kodeId}`);
|
||||
const result = await res.json();
|
||||
|
||||
onSetData({
|
||||
nomor: result.data.nomor,
|
||||
code: result.data.otp,
|
||||
});
|
||||
}
|
||||
|
||||
useEffect(() => {
|
||||
counter > 0 && setTimeout(() => setCounter(counter - 1), 1000);
|
||||
}, [counter]);
|
||||
|
||||
async function onVerifikasi() {
|
||||
if (!inputCode)
|
||||
return ComponentGlobal_NotifikasiPeringatan("Lengkapi Kode");
|
||||
if (code != inputCode)
|
||||
if (data.code != inputCode)
|
||||
return ComponentGlobal_NotifikasiPeringatan("Kode Salah");
|
||||
|
||||
const res = await auth_funValidasi({
|
||||
nomor: nomor,
|
||||
HIPMI_PWD: GlobalEnv.value?.WIBU_PWD as string,
|
||||
});
|
||||
if (res.status === 200) {
|
||||
const resAktivasi = await auth_funDeleteAktivasiKodeOtpById(
|
||||
dataOtp.id as any
|
||||
);
|
||||
if (resAktivasi.status === 200) {
|
||||
if (res.role === "1") {
|
||||
ComponentGlobal_NotifikasiBerhasil(res.message);
|
||||
setLoading(true);
|
||||
router.push(RouterHome.main_home, { scroll: false });
|
||||
try {
|
||||
setLoading(true);
|
||||
const res = await fetch("/api/auth/validasi", {
|
||||
method: "POST",
|
||||
body: JSON.stringify({
|
||||
nomor: data.nomor,
|
||||
}),
|
||||
headers: {
|
||||
"Content-Type": "application/json",
|
||||
},
|
||||
});
|
||||
|
||||
const result = await res.json();
|
||||
|
||||
if (res.status === 200) {
|
||||
localStorage.removeItem("hipmi_auth_code_id");
|
||||
|
||||
if (result.roleId === "1") {
|
||||
if (result.active === true) {
|
||||
ComponentGlobal_NotifikasiBerhasil(result.message);
|
||||
router.push(RouterHome.main_home, { scroll: false });
|
||||
} else {
|
||||
ComponentGlobal_NotifikasiBerhasil(result.message);
|
||||
router.push("/waiting-room", { scroll: false });
|
||||
}
|
||||
} else {
|
||||
ComponentGlobal_NotifikasiBerhasil("Admin Logged in");
|
||||
setLoading(true);
|
||||
router.push(RouterAdminDashboard.splash_admin, { scroll: false });
|
||||
}
|
||||
} else {
|
||||
ComponentGlobal_NotifikasiPeringatan(resAktivasi.message);
|
||||
}
|
||||
}
|
||||
|
||||
if (res.status === 400) {
|
||||
ComponentGlobal_NotifikasiBerhasil(res.message);
|
||||
router.push("/register/" + dataOtp.id, { scroll: false });
|
||||
}
|
||||
|
||||
if (res.status === 401) {
|
||||
const resAktivasi = await auth_funDeleteAktivasiKodeOtpById({
|
||||
nomor: nomor,
|
||||
});
|
||||
if (resAktivasi.status === 200) {
|
||||
ComponentGlobal_NotifikasiPeringatan(res.message);
|
||||
router.push("/login", { scroll: false });
|
||||
const resAktivasi = await auth_funDeleteAktivasiKodeOtpByNomor({
|
||||
nomor: data.nomor,
|
||||
});
|
||||
}
|
||||
|
||||
if (res.status === 404) {
|
||||
ComponentGlobal_NotifikasiBerhasil(result.message);
|
||||
router.push("/register", { scroll: false });
|
||||
}
|
||||
|
||||
if (res.status === 400) {
|
||||
ComponentGlobal_NotifikasiPeringatan(result.message);
|
||||
}
|
||||
} catch (error) {
|
||||
console.error(error);
|
||||
}
|
||||
}
|
||||
|
||||
async function onBack() {
|
||||
await auth_funDeleteAktivasiKodeOtpById({ nomor: nomor });
|
||||
localStorage.removeItem("hipmi_auth_code_id");
|
||||
await auth_funDeleteAktivasiKodeOtpByNomor({ nomor: data.nomor });
|
||||
router.back();
|
||||
}
|
||||
|
||||
async function onResendCode() {
|
||||
const res = await auth_funResendCode({ nomor: nomor });
|
||||
if (res.status === 200) {
|
||||
ComponentGlobal_NotifikasiBerhasil(res.message, 2000);
|
||||
router.push("/validasi/" + res.kodeId, { scroll: false });
|
||||
} else {
|
||||
ComponentGlobal_NotifikasiPeringatan(res.message);
|
||||
setLoadingResend(true);
|
||||
localStorage.removeItem("hipmi_auth_code_id");
|
||||
|
||||
try {
|
||||
const res = await fetch("/api/auth/resend", {
|
||||
method: "POST",
|
||||
body: JSON.stringify({ nomor: data.nomor }),
|
||||
headers: {
|
||||
"Content-Type": "application/json",
|
||||
},
|
||||
});
|
||||
|
||||
const result = await res.json();
|
||||
|
||||
if (res.status === 200) {
|
||||
localStorage.setItem("hipmi_auth_code_id", result.kodeId);
|
||||
ComponentGlobal_NotifikasiBerhasil("Kode Berhasil Dikirim", 2000);
|
||||
setTriggerOtp(true);
|
||||
setCounter(7);
|
||||
setLoadingResend(false);
|
||||
// router.push("/validasi", { scroll: false });
|
||||
} else {
|
||||
setLoadingResend(false);
|
||||
ComponentGlobal_NotifikasiPeringatan(result.message);
|
||||
}
|
||||
} catch (error) {
|
||||
console.error(error);
|
||||
setLoadingResend(false);
|
||||
ComponentGlobal_NotifikasiGagal("Terjadi Kesalahan");
|
||||
}
|
||||
}
|
||||
|
||||
// console.log(data.code);
|
||||
|
||||
return (
|
||||
<>
|
||||
<UIGlobal_LayoutDefault>
|
||||
<Stack h={"100vh"}>
|
||||
<Box
|
||||
{/* <Box
|
||||
pt={"md"}
|
||||
px={"md"}
|
||||
style={{
|
||||
@@ -123,70 +193,84 @@ export default function Validasi({
|
||||
<ActionIcon variant="transparent" onClick={() => onBack()}>
|
||||
<IconChevronLeft color="white" />
|
||||
</ActionIcon>
|
||||
</Box>
|
||||
</Box> */}
|
||||
{data.nomor == "" && data.code == "" ? (
|
||||
<Validasi_SkeletonView />
|
||||
) : (
|
||||
<Stack align="center" justify="center" h={"100vh"} spacing={50}>
|
||||
<Title order={2} color={MainColor.yellow}>
|
||||
Verifikasi Kode OTP
|
||||
</Title>
|
||||
|
||||
<Stack align="center" justify="center" h={"100vh"} spacing={50}>
|
||||
<Title order={2} color={MainColor.yellow}>
|
||||
Verifikasi Kode OTP
|
||||
</Title>
|
||||
|
||||
<Stack spacing={"md"} align="center">
|
||||
<Stack spacing={0} align="center">
|
||||
<Text c={"white"}>Masukan 4 digit kode otp</Text>
|
||||
<Text c={"white"}>
|
||||
Yang dikirim ke{" "}
|
||||
<Text span inherit fw={"bold"}>
|
||||
{" "}
|
||||
+{nomor}
|
||||
<Stack spacing={"md"} align="center">
|
||||
<Stack spacing={0} align="center">
|
||||
<Text c={"white"}>Masukan 4 digit kode otp</Text>
|
||||
<Text c={"white"}>
|
||||
Yang dikirim ke{" "}
|
||||
<Text span inherit fw={"bold"}>
|
||||
{" "}
|
||||
+{data.nomor}
|
||||
</Text>
|
||||
</Text>
|
||||
</Text>
|
||||
</Stack>
|
||||
<Center>
|
||||
<PinInput
|
||||
size="xl"
|
||||
type={"number"}
|
||||
ref={focusTrapRef}
|
||||
spacing={"md"}
|
||||
mt={"md"}
|
||||
onChange={(val) => {
|
||||
setInputOtp(val);
|
||||
}}
|
||||
/>
|
||||
</Center>
|
||||
|
||||
<Stack h={"5vh"} align="center" justify="center">
|
||||
<Text fs="italic" c={"white"} >
|
||||
Tidak menerima kode ?{" "}
|
||||
{counter > 0 ? (
|
||||
<Text fw={"bold"} inherit span>
|
||||
{counter + "s"}
|
||||
</Text>
|
||||
) : loadingResend ? (
|
||||
<Loader ml={"sm"} size={"xs"} color="yellow" />
|
||||
) : (
|
||||
<Text
|
||||
inherit
|
||||
span
|
||||
onClick={() => {
|
||||
onResendCode();
|
||||
}}
|
||||
fw={"bold"}
|
||||
>
|
||||
Kirim ulang
|
||||
</Text>
|
||||
)}
|
||||
</Text>
|
||||
</Stack>
|
||||
</Stack>
|
||||
<Center>
|
||||
<PinInput
|
||||
size="xl"
|
||||
type={"number"}
|
||||
ref={focusTrapRef}
|
||||
spacing={"md"}
|
||||
mt={"md"}
|
||||
onChange={(val) => {
|
||||
setInputOtp(val);
|
||||
}}
|
||||
/>
|
||||
</Center>
|
||||
|
||||
<Text fs="italic" mt={"sm"} c={"white"}>
|
||||
Tidak menerima kode ?{" "}
|
||||
{counter > 0 ? (
|
||||
<Text fw={"bold"} inherit span>
|
||||
{counter + "s"}
|
||||
</Text>
|
||||
) : (
|
||||
<Text inherit span onClick={() => onResendCode()}>
|
||||
Kirim ulang
|
||||
</Text>
|
||||
)}
|
||||
</Text>
|
||||
<Button
|
||||
w={300}
|
||||
loading={loading ? true : false}
|
||||
loaderPosition="center"
|
||||
radius={"md"}
|
||||
compact
|
||||
h={40}
|
||||
c={"black"}
|
||||
bg={MainColor.yellow}
|
||||
color={"yellow"}
|
||||
style={{
|
||||
borderColor: AccentColor.yellow,
|
||||
}}
|
||||
onClick={() => {
|
||||
onVerifikasi();
|
||||
}}
|
||||
>
|
||||
<Text>VERIFIKASI</Text>
|
||||
</Button>
|
||||
</Stack>
|
||||
<Button
|
||||
w={300}
|
||||
loading={loading ? true : false}
|
||||
loaderPosition="center"
|
||||
radius={"md"}
|
||||
compact
|
||||
h={40}
|
||||
c={"black"}
|
||||
bg={MainColor.yellow}
|
||||
color={"yellow"}
|
||||
style={{
|
||||
borderColor: AccentColor.yellow,
|
||||
}}
|
||||
onClick={() => {
|
||||
onVerifikasi();
|
||||
}}
|
||||
>
|
||||
<Text>VERIFIKASI</Text>
|
||||
</Button>
|
||||
</Stack>
|
||||
)}
|
||||
</Stack>
|
||||
</UIGlobal_LayoutDefault>
|
||||
</>
|
||||
|
||||
@@ -1,8 +1,7 @@
|
||||
"use client";
|
||||
|
||||
import { UIGlobal_LayoutDefault } from "@/app_modules/_global/ui";
|
||||
import { Logout } from "@/app_modules/auth";
|
||||
import Component_Logout from "@/app_modules/auth/logout/view";
|
||||
import Component_ButtonLogout from "@/app_modules/auth/logout/view";
|
||||
import { Center, Group, Skeleton, Stack, Text, Title } from "@mantine/core";
|
||||
|
||||
export default function Home_UserNotActive() {
|
||||
@@ -46,7 +45,7 @@ export default function Home_UserNotActive() {
|
||||
<Title order={4} c={"gray"}>
|
||||
Tunggu Konfirmasi Admin !
|
||||
</Title>
|
||||
<Component_Logout />
|
||||
<Component_ButtonLogout userId="" />
|
||||
</Stack>
|
||||
</Center>
|
||||
</UIGlobal_LayoutDefault>
|
||||
|
||||
@@ -32,6 +32,7 @@ export function ComponentKatalog_ButtonHeaderRight({
|
||||
opened={opened}
|
||||
close={() => close()}
|
||||
profileId={profileId}
|
||||
userId={userLoginId}
|
||||
/>
|
||||
</>
|
||||
);
|
||||
|
||||
@@ -4,7 +4,7 @@ import {
|
||||
} from "@/app/lib/router_hipmi/router_katalog";
|
||||
import { AccentColor } from "@/app_modules/_global/color/color_pallet";
|
||||
import ComponentGlobal_Loader from "@/app_modules/_global/component/loader";
|
||||
import Component_Logout from "@/app_modules/auth/logout/view";
|
||||
import Component_ButtonLogout from "@/app_modules/auth/logout/view";
|
||||
import {
|
||||
ActionIcon,
|
||||
Drawer,
|
||||
@@ -27,10 +27,12 @@ export function ComponentKatalog_DrawerKatalog({
|
||||
opened,
|
||||
close,
|
||||
profileId,
|
||||
userId
|
||||
}: {
|
||||
opened: boolean;
|
||||
close: () => void;
|
||||
profileId: string;
|
||||
userId: string
|
||||
}) {
|
||||
const router = useRouter();
|
||||
const [pageId, setPageId] = useState("");
|
||||
@@ -121,7 +123,8 @@ export function ComponentKatalog_DrawerKatalog({
|
||||
</Text>
|
||||
</Stack>
|
||||
))}
|
||||
<Component_Logout />
|
||||
|
||||
<Component_ButtonLogout userId={userId} />
|
||||
</SimpleGrid>
|
||||
</Stack>
|
||||
</Drawer>
|
||||
|
||||
@@ -47,21 +47,27 @@ export function Profile_ComponentCreateNewProfile({
|
||||
"Lengkapi background profile"
|
||||
);
|
||||
|
||||
setLoading(true);
|
||||
|
||||
const uploadPhoto = await funGlobal_UploadToStorage({
|
||||
file: filePP,
|
||||
dirId: DIRECTORY_ID.profile_foto,
|
||||
});
|
||||
if (!uploadPhoto.success)
|
||||
if (!uploadPhoto.success) {
|
||||
setLoading(false);
|
||||
return ComponentGlobal_NotifikasiPeringatan("Gagal upload foto profile");
|
||||
}
|
||||
|
||||
const uploadBackground = await funGlobal_UploadToStorage({
|
||||
file: fileBG,
|
||||
dirId: DIRECTORY_ID.profile_background,
|
||||
});
|
||||
if (!uploadBackground.success)
|
||||
if (!uploadBackground.success) {
|
||||
setLoading(false);
|
||||
return ComponentGlobal_NotifikasiPeringatan(
|
||||
"Gagal upload background profile"
|
||||
);
|
||||
}
|
||||
|
||||
const create = await funCreateNewProfile({
|
||||
data: newData as any,
|
||||
@@ -70,11 +76,11 @@ export function Profile_ComponentCreateNewProfile({
|
||||
});
|
||||
|
||||
if (create.status === 201) {
|
||||
setLoading(true);
|
||||
ComponentGlobal_NotifikasiBerhasil("Berhasil membuat profile", 3000);
|
||||
router.push(RouterHome.main_home, { scroll: false });
|
||||
} else {
|
||||
ComponentGlobal_NotifikasiGagal(create.message);
|
||||
setLoading(false);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
108
src/app_modules/waiting_room/view.tsx
Normal file
108
src/app_modules/waiting_room/view.tsx
Normal file
@@ -0,0 +1,108 @@
|
||||
"use client";
|
||||
|
||||
import { ComponentGlobal_NotifikasiBerhasil } from "@/app_modules/_global/notif_global";
|
||||
import { UIGlobal_LayoutDefault } from "@/app_modules/_global/ui";
|
||||
import {
|
||||
Button,
|
||||
Center,
|
||||
Group,
|
||||
Skeleton,
|
||||
Stack,
|
||||
Text,
|
||||
Title,
|
||||
} from "@mantine/core";
|
||||
import { useShallowEffect } from "@mantine/hooks";
|
||||
import { redirect, useRouter } from "next/navigation";
|
||||
import { useState } from "react";
|
||||
|
||||
export default function WaitingRoom_View({
|
||||
activationUser,
|
||||
userLoginId,
|
||||
}: {
|
||||
activationUser: boolean;
|
||||
userLoginId: string;
|
||||
}) {
|
||||
const router = useRouter();
|
||||
const [loading, setLoading] = useState(false);
|
||||
async function onClickLogout() {
|
||||
setLoading(true);
|
||||
const res = await fetch(`/api/auth/logout?id=${userLoginId}`, {
|
||||
method: "GET",
|
||||
});
|
||||
|
||||
const result = await res.json();
|
||||
if (res.status === 200) {
|
||||
ComponentGlobal_NotifikasiBerhasil(result.message);
|
||||
router.push("/", { scroll: false });
|
||||
}
|
||||
}
|
||||
|
||||
useShallowEffect(() => {
|
||||
if (activationUser == true) {
|
||||
return redirect("/");
|
||||
}
|
||||
}, [activationUser]);
|
||||
|
||||
const listhHuruf = [
|
||||
{
|
||||
huruf: "H",
|
||||
},
|
||||
{
|
||||
huruf: "I",
|
||||
},
|
||||
{
|
||||
huruf: "P",
|
||||
},
|
||||
{
|
||||
huruf: "M",
|
||||
},
|
||||
{
|
||||
huruf: "I",
|
||||
},
|
||||
];
|
||||
const customLOader = (
|
||||
<Center>
|
||||
<Group>
|
||||
{listhHuruf.map((e, i) => (
|
||||
<Center key={i} h={"100%"}>
|
||||
<Skeleton height={50} circle radius={"100%"} />
|
||||
<Text sx={{ position: "absolute" }} c={"gray.5"} fw={"bold"}>
|
||||
{e.huruf}
|
||||
</Text>
|
||||
</Center>
|
||||
))}
|
||||
</Group>
|
||||
</Center>
|
||||
);
|
||||
|
||||
return (
|
||||
<>
|
||||
<UIGlobal_LayoutDefault>
|
||||
<Center h={"100vh"}>
|
||||
<Stack align="center" spacing={50}>
|
||||
{/* {customLOader} */}
|
||||
|
||||
<Stack align="center" spacing={5}>
|
||||
<Title order={3} c={"white"}>
|
||||
Anda telah berhasil mendaftar,
|
||||
</Title>
|
||||
<Title order={3} c={"white"}>
|
||||
Mohon menunggu konfirmansi Admin !
|
||||
</Title>
|
||||
</Stack>
|
||||
|
||||
<Button
|
||||
color="red"
|
||||
loaderPosition="center"
|
||||
loading={loading}
|
||||
radius={"xl"}
|
||||
onClick={() => onClickLogout()}
|
||||
>
|
||||
Keluar
|
||||
</Button>
|
||||
</Stack>
|
||||
</Center>
|
||||
</UIGlobal_LayoutDefault>
|
||||
</>
|
||||
);
|
||||
}
|
||||
55
src/middleware.back.txt
Normal file
55
src/middleware.back.txt
Normal file
@@ -0,0 +1,55 @@
|
||||
|
||||
import { NextResponse } from "next/server";
|
||||
import type { NextRequest } from "next/server";
|
||||
|
||||
// This function can be marked `async` if using `await` inside
|
||||
export const middleware = async (request: NextRequest) => {
|
||||
console.log("middleware");
|
||||
console.log(request.method);
|
||||
console.log(request.url);
|
||||
|
||||
const origin = request.headers.get("origin");
|
||||
console.log(origin);
|
||||
|
||||
const { pathname } = request.nextUrl;
|
||||
|
||||
// CROS
|
||||
const corsRespone = handleCors(request);
|
||||
if (corsRespone) {
|
||||
return setCorsHeaders(
|
||||
NextResponse.redirect(new URL("/login", request.url))
|
||||
);
|
||||
}
|
||||
};
|
||||
|
||||
function handleCors(req: NextRequest): NextResponse | null {
|
||||
if (req.method === "OPTIONS") {
|
||||
return new NextResponse(null, {
|
||||
status: 204,
|
||||
headers: {
|
||||
"Access-Control-Allow-Origin": "*",
|
||||
"Access-Control-Allow-Methods": "GET, POST, PUT, DELETE, OPTIONS",
|
||||
"Access-Control-Allow-Headers": "Content-Type, Authorization",
|
||||
"Access-Control-Max-Age": "86400",
|
||||
},
|
||||
});
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
function setCorsHeaders(res: NextResponse): NextResponse {
|
||||
res.headers.set("Access-Control-Allow-Origin", "*");
|
||||
res.headers.set(
|
||||
"Access-Control-Allow-Methods",
|
||||
"GET, POST, PUT, DELETE, OPTIONS"
|
||||
);
|
||||
res.headers.set(
|
||||
"Access-Control-Allow-Headers",
|
||||
"Content-Type, Authorization"
|
||||
);
|
||||
return res;
|
||||
}
|
||||
|
||||
export const config = {
|
||||
matcher: ["/((?!_next|static|favicon.ico|manifest).*)"],
|
||||
};
|
||||
@@ -1,28 +1,179 @@
|
||||
import { funGetUserIdByToken } from "@/app_modules/_global/fun/get";
|
||||
import { user_getOneByUserId } from "@/app_modules/home/fun/get/get_one_user_by_id";
|
||||
import { unsealData } from "iron-session";
|
||||
import _ from "lodash";
|
||||
import { NextResponse } from "next/server";
|
||||
import type { NextRequest } from "next/server";
|
||||
import { RouterHome } from "./app/lib/router_hipmi/router_home";
|
||||
import { NextRequest, NextResponse } from "next/server";
|
||||
import { jwtVerify } from "jose";
|
||||
import { apies, pages } from "./lib/routes";
|
||||
|
||||
type MiddlewareConfig = {
|
||||
apiPath: string;
|
||||
loginPath: string;
|
||||
userPath: string;
|
||||
publicRoutes: string[];
|
||||
encodedKey: string;
|
||||
sessionKey: string;
|
||||
validationApiRoute: string;
|
||||
log: boolean;
|
||||
};
|
||||
|
||||
// This function can be marked `async` if using `await` inside
|
||||
export function middleware(request: NextRequest) {
|
||||
let c = request.cookies.get("mySession");
|
||||
const middlewareConfig: MiddlewareConfig = {
|
||||
apiPath: "/api",
|
||||
loginPath: "/login",
|
||||
userPath: "/dev/home",
|
||||
publicRoutes: [
|
||||
// "/",
|
||||
"/api/auth/*",
|
||||
"/login",
|
||||
"/register",
|
||||
"/validasi",
|
||||
"/splash",
|
||||
"/auth/login",
|
||||
"/auth/api/login",
|
||||
"/aset/global/main_background.png",
|
||||
"/aset/logo/logo-hipmi.png",
|
||||
],
|
||||
encodedKey: process.env.NEXT_PUBLIC_BASE_TOKEN_KEY!,
|
||||
sessionKey: process.env.NEXT_PUBLIC_BASE_SESSION_KEY!,
|
||||
validationApiRoute: "/api/validation",
|
||||
log: false,
|
||||
};
|
||||
export const middleware = async (req: NextRequest) => {
|
||||
const {
|
||||
apiPath,
|
||||
encodedKey,
|
||||
loginPath,
|
||||
publicRoutes,
|
||||
sessionKey,
|
||||
validationApiRoute,
|
||||
userPath,
|
||||
} = middlewareConfig;
|
||||
const { pathname } = req.nextUrl;
|
||||
|
||||
if (!c || !c?.value || _.isEmpty(c?.value) || _.isUndefined(c?.value)) {
|
||||
console.log("tidak ada user middleware");
|
||||
// CORS handling
|
||||
const corsResponse = handleCors(req);
|
||||
if (corsResponse) {
|
||||
return setCorsHeaders(corsResponse);
|
||||
}
|
||||
|
||||
// Skip authentication for public routes
|
||||
const isPublicRoute = [...publicRoutes, loginPath, validationApiRoute].some(
|
||||
(route) => {
|
||||
const pattern = route.replace(/\*/g, ".*");
|
||||
return new RegExp(`^${pattern}$`).test(pathname);
|
||||
}
|
||||
);
|
||||
|
||||
// return NextResponse.redirect(new URL("/dev/auth/login", request.url));
|
||||
// return NextResponse.redirect(new URL(RouterAuth.login, request.url));
|
||||
} else {
|
||||
console.log("ada user middleware");
|
||||
return NextResponse.redirect(new URL(RouterHome.main_home, request.url));
|
||||
if (isPublicRoute) {
|
||||
return setCorsHeaders(NextResponse.next());
|
||||
}
|
||||
|
||||
const token =
|
||||
req.cookies.get(sessionKey)?.value ||
|
||||
req.headers.get("Authorization")?.split(" ")[1];
|
||||
|
||||
// Token verification
|
||||
const user = await verifyToken({ token, encodedKey });
|
||||
|
||||
if (!user) {
|
||||
if (pathname.startsWith(apiPath)) {
|
||||
return setCorsHeaders(unauthorizedResponse());
|
||||
}
|
||||
|
||||
return setCorsHeaders(NextResponse.redirect(new URL(loginPath, req.url)));
|
||||
}
|
||||
|
||||
// Redirect authenticated user away from login page
|
||||
if (user && pathname === loginPath) {
|
||||
return setCorsHeaders(NextResponse.redirect(new URL(userPath, req.url)));
|
||||
}
|
||||
|
||||
if (req.nextUrl.pathname.startsWith(apiPath)) {
|
||||
const reqToken = req.headers.get("Authorization")?.split(" ")[1];
|
||||
// Validate user access with external API
|
||||
const validationResponse = await fetch(
|
||||
new URL(validationApiRoute, req.url),
|
||||
{
|
||||
headers: {
|
||||
"Content-Type": "application/json",
|
||||
Authorization: `Bearer ${reqToken}`,
|
||||
},
|
||||
}
|
||||
);
|
||||
|
||||
if (!validationResponse.ok) {
|
||||
return setCorsHeaders(unauthorizedResponse());
|
||||
}
|
||||
}
|
||||
|
||||
// Proceed with the request
|
||||
return setCorsHeaders(NextResponse.next());
|
||||
};
|
||||
|
||||
function unauthorizedResponse(): NextResponse {
|
||||
return new NextResponse(JSON.stringify({ error: "Unauthorized" }), {
|
||||
status: 401,
|
||||
headers: { "Content-Type": "application/json" },
|
||||
});
|
||||
}
|
||||
|
||||
function setCorsHeaders(res: NextResponse): NextResponse {
|
||||
res.headers.set("Access-Control-Allow-Origin", "*");
|
||||
res.headers.set(
|
||||
"Access-Control-Allow-Methods",
|
||||
"GET, POST, PUT, DELETE, OPTIONS"
|
||||
);
|
||||
res.headers.set(
|
||||
"Access-Control-Allow-Headers",
|
||||
"Content-Type, Authorization"
|
||||
);
|
||||
return res;
|
||||
}
|
||||
|
||||
function handleCors(req: NextRequest): NextResponse | null {
|
||||
if (req.method === "OPTIONS") {
|
||||
return new NextResponse(null, {
|
||||
status: 204,
|
||||
headers: {
|
||||
"Access-Control-Allow-Origin": "*",
|
||||
"Access-Control-Allow-Methods": "GET, POST, PUT, DELETE, OPTIONS",
|
||||
"Access-Control-Allow-Headers": "Content-Type, Authorization",
|
||||
"Access-Control-Max-Age": "86400",
|
||||
},
|
||||
});
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
async function verifyToken({
|
||||
token,
|
||||
encodedKey,
|
||||
}: {
|
||||
token: string | undefined;
|
||||
encodedKey: string;
|
||||
}): Promise<Record<string, unknown> | null> {
|
||||
if (!token) return null;
|
||||
|
||||
return await decrypt({ token, encodedKey });
|
||||
}
|
||||
|
||||
async function decrypt({
|
||||
token,
|
||||
encodedKey,
|
||||
}: {
|
||||
token: string;
|
||||
encodedKey: string;
|
||||
}): Promise<Record<string, any> | null> {
|
||||
try {
|
||||
const enc = new TextEncoder().encode(encodedKey);
|
||||
const { payload } = await jwtVerify(token, enc, {
|
||||
algorithms: ["HS256"],
|
||||
});
|
||||
return (payload.user as Record<string, any>) || null;
|
||||
} catch (error) {
|
||||
console.error("Gagal verifikasi session", error);
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
export const config = {
|
||||
matcher: ["/((?!_next|static|favicon.ico|manifest).*)"],
|
||||
};
|
||||
|
||||
// wibu:0.2.82
|
||||
|
||||
Reference in New Issue
Block a user