# fix
- authentication
- profile
- pencarian user
- forum
## No issue
This commit is contained in:
2024-05-20 10:55:13 +08:00
parent 66b9902d97
commit dbeb740d1f
58 changed files with 1374 additions and 386 deletions

Binary file not shown.

Before

Width:  |  Height:  |  Size: 2.4 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 6.4 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 6.5 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 4.2 KiB

View File

Before

Width:  |  Height:  |  Size: 3.7 KiB

After

Width:  |  Height:  |  Size: 3.7 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 5.1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 7.4 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 5.5 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 7.4 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.3 KiB

View File

@@ -8,5 +8,5 @@ export async function GET(req: Request) {
skip: +page * 5 - 5,
});
return Response.json(res);
// return Response.json(res);
}

View File

@@ -17,23 +17,19 @@ export default async function Page({ params }: { params: { id: string } }) {
]);
let listMsg = await colab_getMessageByRoomId({ roomId: roomId, page: 1 });
// const listMessage = await colab_V2getListMessageByRoomId({
// roomId: roomId,
// page: 1,
// });
return (
<>
{/* <ColabViewChat
<ColabViewChat
listMsg={listMsg as any}
dataRoom={dataRoom as any}
userLoginId={userLoginId}
/> */}
<Colab_GroupChatView
/>
{/* <Colab_GroupChatView
userLoginId={userLoginId}
listMsg={listMsg}
selectRoom={dataRoom as any}
/>
/> */}
</>
);
}

View File

@@ -8,9 +8,13 @@ export default async function Page({
children: React.ReactNode;
params: { id: string };
}) {
let eventId = params.id
let eventId = params.id;
return <>
<LayoutEvent_DetailDraft eventId={eventId}>{children}</LayoutEvent_DetailDraft>;
</>
return (
<>
<LayoutEvent_DetailDraft eventId={eventId}>
{children}
</LayoutEvent_DetailDraft>
</>
);
}

View File

@@ -1,8 +1,8 @@
import { Event_DetailDraft } from "@/app_modules/event";
import { Event_getOneById } from "@/app_modules/event/fun/get/get_one_by_id";
import { Event_DetailDraft } from "@/app_modules/event"
import { Event_getOneById } from "@/app_modules/event/fun/get/get_one_by_id"
export default async function Page({params}: {params: {id: string}}) {
export default async function Page({ params }: { params: { id: string } }) {
let eventId = params.id
const dataEvent = await Event_getOneById(eventId)
return <Event_DetailDraft dataEvent={dataEvent as any} />;
return <Event_DetailDraft dataEvent={dataEvent as any} />
}

View File

@@ -8,7 +8,7 @@ import { forum_countPostingByAuthorId } from "@/app_modules/forum/fun/count/coun
export default async function Page({ params }: { params: { id: string } }) {
const authorId = params.id;
const userLoginId = await user_getOneUserId()
const userLoginId = await user_getOneUserId();
const dataAuthor = await user_getOneByUserId(authorId);
const auhtorSelectedData = _.omit(dataAuthor, [
"Profile.email",
@@ -25,14 +25,11 @@ export default async function Page({ params }: { params: { id: string } }) {
// setTimeout(a, 1000);
// });
const dataPosting = await forum_getListPostingByAuhtorId(authorId);
const totalPosting = await forum_countPostingByAuthorId(authorId);
return (
<>
<Forum_Forumku
auhtorSelectedData={auhtorSelectedData as any}
dataPosting={dataPosting as any}

View File

@@ -1,11 +1,15 @@
import MqttLoader from '@/util/mqtt_loader';
import RootStyleRegistry from './emotion';
import MqttLoader from "@/util/mqtt_loader";
import RootStyleRegistry from "./emotion";
export default function RootLayout({ children }: { children: React.ReactNode }) {
export default function RootLayout({
children,
}: {
children: React.ReactNode;
}) {
return (
<RootStyleRegistry>
<MqttLoader />
{children}</RootStyleRegistry>
{children}
</RootStyleRegistry>
);
}

View File

@@ -27,11 +27,13 @@ import { ComponentGlobal_NotifikasiBerhasil } from "@/app_modules/component_glob
import { IconPencilCheck } from "@tabler/icons-react";
import { RouterHome } from "@/app/lib/router_hipmi/router_home";
import { auth_funEditAktivasiKodeOtpById } from "../fun/fun_edit_aktivasi_kode_otp_by_id";
import ComponentGlobal_ErrorInput from "@/app_modules/component_global/error_input";
export default function Register({ dataOtp }: { dataOtp: any }) {
const router = useRouter();
const [nomor, setNomor] = useState(dataOtp.nomor);
const [value, setValue] = useState("");
const [isValue, setIsValue] = useState(false);
const focusTrapRef = useFocusTrap();
const [loading, setLoading] = useState(false);
@@ -42,17 +44,12 @@ export default function Register({ dataOtp }: { dataOtp: any }) {
};
// console.log(body);
if (body.username === "")
return ComponentGlobal_NotifikasiPeringatan("Lengkapi Username");
if (body.username.length < 5)
return ComponentGlobal_NotifikasiPeringatan("Username tidak sesuai");
if (_.values(body.username).includes(" "))
return ComponentGlobal_NotifikasiPeringatan(
"Username tidak sesuai",
3000
);
if (body.username === "") {
setIsValue(true);
return null;
}
if (body.username.length < 5) return null;
if (_.values(body.username).includes(" ")) return null;
await Auth_funRegister(body).then(async (res) => {
if (res.status === 200) {
@@ -92,23 +89,27 @@ export default function Register({ dataOtp }: { dataOtp: any }) {
<Title order={4}>REGISTRASI</Title>
<Text fz={"xs"}>Masukan username anda !</Text>
</Stack>
<Stack spacing={0}>
<Stack spacing={"sm"}>
<TextInput
ref={focusTrapRef}
placeholder="Masukan Username"
maxLength={50}
error={
value.length > 0 && value.length < 5 ? (
<Text>Minimal 5 karakter</Text>
<ComponentGlobal_ErrorInput text="Minimal 5 karakter !" />
) : _.values(value).includes(" ") ? (
<Stack spacing={0}>
<Text>- Tidak boleh ada space</Text>
<Text>- Sambungkan huruf meggunakan karakter _</Text>
<Stack spacing={5}>
<ComponentGlobal_ErrorInput text="Tidak boleh ada space" />
<ComponentGlobal_ErrorInput text="Sambungkan huruf meggunakan karakter _" />
</Stack>
) : isValue ? (
<ComponentGlobal_ErrorInput text="Masukan username anda" />
) : (
""
)
}
onChange={(val) => {
val.currentTarget.value.length > 0 ? setIsValue(false) : "";
setValue(val.currentTarget.value);
}}
/>

View File

@@ -46,6 +46,7 @@ import useInfiniteScroll, {
import toast from "react-simple-toasts";
import colab_getOneMessageById from "../../fun/get/room_chat/get_one_message_by_id";
import { List } from "react-virtualized";
import { evnPesan } from "@/util/evn";
const list = Array(100).fill(0);
export default function ColabViewChat({
@@ -74,23 +75,53 @@ export default function ColabViewChat({
down: false,
});
const [topik, setTopic] = useState("")
useShallowEffect(() => {
evnPesan.on(topik, (msgg) => {
let dd: any[] = _.clone(data);
const a = [...dd, JSON.parse(msgg)];
// console.log(dd.length);
setData(a);
});
}, [data]);
// Kirim pesan
async function onSend() {
await colab_funCreateMessageByUserId(msg, dataRoom.id).then(async (res) => {
if (res.status === 200) {
const newData = await colab_getMessageByRoomId({
roomId: dataRoom?.id,
page: 1,
});
setData(newData as any);
setHasMore({ up: true });
// console.log(JSON.stringify(data[0], null, 2));
const kiriman = {
id: "clw8glvt4000j12efrecoubug",
createdAt: "2024-05-15T23:35:05.032Z",
isActive: true,
message: msg,
isFile: false,
User: {
id: "clvag8xt10007134j8sapm46n",
Profile: {
id: "clvajdger000g134jhhhg21c4",
name: "malikkurosaki",
},
},
};
mqtt_client.publish("pesan", JSON.stringify(kiriman));
// await colab_funCreateMessageByUserId(msg, dataRoom.id).then(async (res) => {
// if (res.status === 200) {
// const newData = await colab_getMessageByRoomId({
// roomId: dataRoom?.id,
// page: 1,
// });
// setData(newData as any);
// setHasMore({ up: true });
setMsg("");
} else {
ComponentGlobal_NotifikasiGagal(res.message);
}
});
// } else {
// ComponentGlobal_NotifikasiGagal(res.message);
// }
// });
}
const next = async (direction: ScrollDirection) => {
@@ -220,19 +251,19 @@ export default function ColabViewChat({
dangerouslySetInnerHTML={{ __html: e?.message }}
/>
{/* <Group spacing={"xs"}>
<Group spacing={"xs"}>
<Text fz={7}>
{new Intl.DateTimeFormat("id-ID", {
{/* {new Intl.DateTimeFormat("id-ID", {
timeStyle: "medium",
}).format(e.createdAt)}
}).format(e.createdAt)} */}
</Text>
<IconCircle size={3} />
<Text fz={7}>
{new Intl.DateTimeFormat("id-ID", {
{/* {new Intl.DateTimeFormat("id-ID", {
dateStyle: "medium",
}).format(e.createdAt)}
}).format(e.createdAt)} */}
</Text>
</Group> */}
</Group>
</Stack>
</Paper>
</Group>
@@ -246,19 +277,19 @@ export default function ColabViewChat({
<div
dangerouslySetInnerHTML={{ __html: e?.message }}
/>
{/* <Group spacing={"xs"}>
<Group spacing={"xs"}>
<Text fz={7}>
{new Intl.DateTimeFormat("id-ID", {
{/* {new Intl.DateTimeFormat("id-ID", {
timeStyle: "medium",
}).format(e.createdAt)}
}).format(e.createdAt)} */}
</Text>
<IconCircle size={3} />
<Text fz={7}>
{new Intl.DateTimeFormat("id-ID", {
{/* {new Intl.DateTimeFormat("id-ID", {
dateStyle: "medium",
}).format(e.createdAt)}
}).format(e.createdAt)} */}
</Text>
</Group> */}
</Group>
</Stack>
</Paper>
</Group>

View File

@@ -103,9 +103,6 @@ export default function Colab_GroupChatView({
mqtt_client.publish(selectRoom.id, msg);
setMsg("");
// const d = JSON.parse(JSON.stringify(res.data));
// setData([...data, ...[d]]);
await colab_getOneMessageById({
messageId: res.data?.id as any,
}).then((res) => {
@@ -114,9 +111,9 @@ export default function Colab_GroupChatView({
// const d = JSON.parse(JSON.stringify(res));
// setData([...data, ...[d]]);
mqtt_client.on("message", (a,b) => {
setData([...data, ...[res]])
})
mqtt_client.on("message", (a, b) => {
setData([...data, ...[res]]);
});
});
} else {
ComponentGlobal_NotifikasiGagal(res.message);

View File

@@ -12,8 +12,8 @@ export default async function colab_getMessageByRoomId({
roomId: string;
page: number;
}) {
const lewat = page * 10 - 10;
const ambil = 10;
const lewat = page * 6 - 6;
const ambil = 6;
const getList = await prisma.projectCollaboration_Message.findMany({
orderBy: {

View File

@@ -0,0 +1,25 @@
"use client";
import { Group, Text } from "@mantine/core";
import { IconAlertTriangle } from "@tabler/icons-react";
export default function ComponentGlobal_ErrorInput({
max,
text,
color,
}: {
max?: number;
text?: string;
color?: string;
}) {
return (
<>
<Group spacing={"xs"}>
<IconAlertTriangle size={15} color={color ? color : "red"} />
<Text fz={10} fs={"italic"} color={color ? color : "red"}>
{text ? text : ` Maksimal ${max ? max : "-"} karakter !`}
</Text>
</Group>
</>
);
}

View File

@@ -0,0 +1,23 @@
"use client";
import { Text } from "@mantine/core";
import { useState } from "react";
export default function ComponentGlobal_InputCountDown({
maxInput,
lengthInput,
}: {
maxInput: number;
lengthInput: number;
}) {
return (
<>
<Text fz={"xs"} fs={"italic"} color="gray">
{maxInput - lengthInput < 0 ? 0 : maxInput - lengthInput} /{" "}
<Text span inherit c={maxInput - lengthInput < 0 ? "red" : ""} style={{transition: "0.5s"}}>
{maxInput}
</Text>
</Text>
</>
);
}

View File

@@ -15,14 +15,14 @@ export default function ComponentEvent_DetailData({
const jam = tgl.toLocaleTimeString([], {
hour: "2-digit",
minute: "2-digit",
hour12: false,
});
return (
<>
{/* <pre>{JSON.stringify(jam)}</pre> */}
<Paper withBorder p={"md"} shadow="lg">
<Stack px={"sm"}>
<Title order={4}>{data ? data?.title : null}</Title>
<Title w={"100%"} order={4}>{data ? data?.title : null}</Title>
<Grid>
<Grid.Col span={4}>
<Text fw={"bold"} fz={"sm"}>
@@ -52,7 +52,7 @@ export default function ComponentEvent_DetailData({
</Text>
</Grid.Col>
<Grid.Col span={1}>:</Grid.Col>
<Grid.Col span={"auto"}>{hari}</Grid.Col>
<Grid.Col span={"auto"}>{hari ? hari : ""}</Grid.Col>
</Grid>
<Grid>
<Grid.Col span={4}>
@@ -61,7 +61,7 @@ export default function ComponentEvent_DetailData({
</Text>
</Grid.Col>
<Grid.Col span={1}>:</Grid.Col>
<Grid.Col span={"auto"}>{jam}</Grid.Col>
<Grid.Col span={"auto"}>{jam ? jam : ""}</Grid.Col>
</Grid>
<Stack spacing={2}>
<Text fw={"bold"} fz={"sm"}>

View File

@@ -1,17 +1,23 @@
"use client"
"use client";
import { Group, Text } from "@mantine/core";
import { IconAlertTriangle } from "@tabler/icons-react";
export default function ComponentEvent_ErrorMaximalInput({max}:{max: number}){
return (
<>
<Group spacing={"xs"}>
<IconAlertTriangle size={15} />
<Text fz={10} fs={"italic"}>
Maksimal {max} karakter !
</Text>
</Group>
</>
);
}
export default function ComponentEvent_ErrorMaximalInput({
max,
text,
}: {
max?: number;
text?: string;
}) {
return (
<>
<Group spacing={"xs"}>
<IconAlertTriangle size={15} />
<Text fz={10} fs={"italic"}>
{text ? text : ` Maksimal ${max} karakter !`}
</Text>
</Group>
</>
);
}

View File

@@ -15,7 +15,7 @@ export default function ComponentEvent_HeaderTamplate({
bg,
}: {
hideBack?: boolean;
changeIconBack?: any
changeIconBack?: any;
route?: any;
route2?: any;
title: string;
@@ -23,6 +23,8 @@ export default function ComponentEvent_HeaderTamplate({
bg?: any;
}) {
const router = useRouter();
const [isLoadingBack, setLoadingBack] = useState(false);
const [isLoadingOtherIcon, setLoadingOtherIcon] = useState(false);
return (
<>
<Header
@@ -35,8 +37,10 @@ export default function ComponentEvent_HeaderTamplate({
<ActionIcon variant="transparent" disabled></ActionIcon>
) : (
<ActionIcon
loading={isLoadingBack ? true : false}
variant="transparent"
onClick={() => {
setLoadingBack(true);
if (route === null || route === undefined) {
return router.back();
} else {
@@ -44,7 +48,7 @@ export default function ComponentEvent_HeaderTamplate({
}
}}
>
{changeIconBack ? changeIconBack: <IconChevronLeft />}
{changeIconBack ? changeIconBack : <IconChevronLeft />}
</ActionIcon>
)}
<Title order={5}>{title}</Title>
@@ -54,8 +58,12 @@ export default function ComponentEvent_HeaderTamplate({
} else {
return (
<ActionIcon
loading={isLoadingOtherIcon ? true : false}
variant="transparent"
onClick={() => router.push(route2)}
onClick={() => {
setLoadingOtherIcon(true);
router.push(route2);
}}
>
{icon}
</ActionIcon>

View File

@@ -0,0 +1,13 @@
"use client";
import { Center } from "@mantine/core";
export default function ComponentEvent_IsEmptyData({ text }: { text: string }) {
return (
<>
<Center h={"50vh"} fz={"sm"} c="gray" fw={"bold"} style={{zIndex: 1}}>
{text}
</Center>
</>
);
}

View File

@@ -48,23 +48,21 @@ export default function Event_Create({
const [tabsStatus, setTabsStatus] = useAtom(gs_event_status);
const [listTipe, setListTipe] = useState(listTipeAcara);
const [hotMenu, setHotMenu] = useAtom(gs_event_hotMenu);
// Masimal karakter state
const [maxTitle, setMaxTitle] = useState("");
const [maxLokasi, setMaxLokasi] = useState("");
const [maxDeskripsi, setMaxDeskripsi] = useState("");
const [isTime, setIsTime] = useState(false);
const [isLoading, setLoading] = useState(false);
const [value, setValue] = useState({
title: "",
lokasi: "",
deskripsi: "",
tanggal: Date,
tanggal: Date.toString(),
eventMaster_TipeAcaraId: 0,
authorId: authorId,
});
return (
<>
{/* <pre>{JSON.stringify(value, null, 2)}</pre> */}
<Stack px={"sm"}>
<TextInput
label="Judul"
@@ -72,21 +70,19 @@ export default function Event_Create({
withAsterisk
maxLength={100}
error={
maxTitle.length >= 100 ? (
value.title.length >= 100 ? (
<ComponentEvent_ErrorMaximalInput max={100} />
) : (
""
)
}
onChange={(val) => {
setMaxTitle(val.target.value);
setValue({
...value,
title: val.target.value,
});
}}
/>
<Select
withAsterisk
label="Tipe Acara"
@@ -107,16 +103,15 @@ export default function Event_Create({
label="Lokasi"
placeholder="Masukan lokasi acara"
withAsterisk
maxLength={200}
maxLength={100}
error={
maxLokasi.length >= 200 ? (
<ComponentEvent_ErrorMaximalInput max={200} />
value.lokasi.length >= 100 ? (
<ComponentEvent_ErrorMaximalInput max={100} />
) : (
""
)
}
onChange={(val) => {
setMaxLokasi(val.target.value);
setValue({
...value,
lokasi: val.target.value,
@@ -124,48 +119,68 @@ export default function Event_Create({
}}
/>
<DateTimePicker
// onClick={() => {
// console.log(moment().diff(moment("2024-02-01"), "days"));
// }}
excludeDate={(date) => {
return moment(date).diff(Date.now(), "days") < 0;
}}
withAsterisk
label="Tanggal & Waktu "
placeholder="Masukan tangal dan waktu acara"
onChange={(val: any) =>
error={
isTime ? (
<ComponentEvent_ErrorMaximalInput text="Invalid Time !" />
) : (
""
)
}
onChange={(val) => {
// console.log(
// moment(val?.toISOString().toString()).diff(moment(), "minutes" )
// );
moment(val?.toISOString().toString()).diff(moment(), "minutes") < 0
? setIsTime(true)
: setIsTime(false);
setValue({
...value,
tanggal: val,
})
}
tanggal: val as any,
});
}}
/>
<Textarea
label="Deskripsi"
placeholder="Deskripsikan acara yang akan di selenggarakan"
withAsterisk
autosize
maxLength={500}
maxLength={200}
error={
maxDeskripsi.length >= 500 ? (
<ComponentEvent_ErrorMaximalInput max={500} />
value.deskripsi.length >= 200 ? (
<ComponentEvent_ErrorMaximalInput max={200} />
) : (
""
)
}
onChange={(val) => {
setMaxDeskripsi(val.target.value);
setValue({
...value,
deskripsi: val.target.value,
});
}}
/>
<Button
disabled={
value.title === "" ||
value.lokasi === "" ||
value.deskripsi === "" ||
value.eventMaster_TipeAcaraId === 0 ||
value.tanggal === "function Date() { [native code] }"
}
loaderPosition="center"
loading={isLoading ? true : false}
radius={"xl"}
mt={"xl"}
onClick={() => onSave(router, setTabsStatus, value, setHotMenu)}
onClick={() =>
onSave(router, setTabsStatus, value, setHotMenu, setLoading)
}
>
Simpan
</Button>
@@ -178,19 +193,30 @@ async function onSave(
router: AppRouterInstance,
setTabsStatus: any,
value: any,
setHotMenu: any
setHotMenu: any,
setLoading: any
) {
if (_.values(value).includes(""))
return ComponentGlobal_NotifikasiPeringatan("Lengkapi Data");
if (value.title.length >= 100) return null;
if (value.lokasi.length >= 100) return null;
if (value.eventMaster_TipeAcaraId === 0)
return ComponentGlobal_NotifikasiPeringatan("Pilih Tipe Acara");
if (moment(value.tanggal).format() === "Invalid date")
return ComponentGlobal_NotifikasiPeringatan("Lengkapi Tanggal");
if (
moment(value.tanggal.toISOString().toString()).diff(moment(), "minutes") < 0
)
return null;
if (value.deskripsi.length >= 200) return null;
await Event_funCreate(value).then((res) => {
if (res.status === 201) {
ComponentGlobal_NotifikasiBerhasil(res.message);
setTabsStatus("Review");
setHotMenu(1);
setLoading(true);
router.push(RouterEvent.status_page);
} else {
ComponentGlobal_NotifikasiGagal(res.message);

View File

@@ -1,8 +1,8 @@
"use client";
import { Button, Stack } from "@mantine/core";
import { Button, Group, Stack } from "@mantine/core";
import ComponentEvent_DetailData from "../../component/detail/detail_data";
import { useRouter } from "next/navigation";
import { AppRouterInstance } from "next/dist/shared/lib/app-router-context.shared-runtime";
import { useAtom } from "jotai";
import { gs_event_status } from "../../global_state";
@@ -10,52 +10,73 @@ import { ComponentGlobal_NotifikasiBerhasil } from "@/app_modules/component_glob
import { MODEL_EVENT } from "../../model/interface";
import { Event_funEditStatusById } from "../../fun/edit/fun_edit_status_by_id";
import { ComponentGlobal_NotifikasiGagal } from "@/app_modules/component_global/notif_global/notifikasi_gagal";
import { useState } from "react";
import React, { useState } from "react";
import ComponentEvent_CatatanReject from "../../component/catatan_reject";
import { useRouter } from "next/navigation";
export default function Event_DetailDraft({
dataEvent,
}: {
dataEvent: MODEL_EVENT;
}) {
const router = useRouter();
const [tabsStatus, setTabsStatus] = useAtom(gs_event_status);
return (
<>
{/* <pre>{JSON.stringify(dataEvent.catatan)}</pre> */}
{/* <pre>{JSON.stringify(dataEvent.catatan)}</pre> */}
<Stack spacing={"lg"}>
{dataEvent.catatan ? (
<ComponentEvent_CatatanReject catatan={dataEvent.catatan} />
{dataEvent?.catatan ? (
<ComponentEvent_CatatanReject catatan={dataEvent?.catatan} />
) : (
""
)}
<ComponentEvent_DetailData data={dataEvent} />
<Button
radius={"xl"}
color="yellow"
onClick={() => {
onClick(router, setTabsStatus, dataEvent.id);
}}
>
Ajukan Review
</Button>
<ButtonAction eventId={dataEvent?.id} />
</Stack>
</>
);
}
async function onClick(
router: AppRouterInstance,
setTabsStatus: any,
eventId: string
) {
await Event_funEditStatusById("2", eventId).then((res) => {
if (res.status === 200) {
ComponentGlobal_NotifikasiBerhasil(res.message, 1500);
setTabsStatus("Review");
router.back();
} else {
ComponentGlobal_NotifikasiGagal(res.message);
}
});
function ButtonAction({ eventId }: { eventId: string }) {
const router = useRouter();
const [tabsStatus, setTabsStatus] = useAtom(gs_event_status);
async function onDelete() {
console.log(eventId);
}
async function onAjukan() {
await Event_funEditStatusById("2", eventId).then((res) => {
if (res.status === 200) {
ComponentGlobal_NotifikasiBerhasil(res.message, 2000);
setTabsStatus("Review");
router.back();
} else {
ComponentGlobal_NotifikasiGagal(res.message);
}
});
}
return (
<>
<Group grow>
<Button
radius={"xl"}
color="yellow"
onClick={() => {
onAjukan();
}}
>
Ajukan Review
</Button>
<Button
radius={"xl"}
color="red"
onClick={() => {
// onClick(router, setTabsStatus, dataEvent.id);
}}
>
Hapus
</Button>
</Group>
</>
);
}

View File

@@ -22,5 +22,5 @@ export default function LayoutEvent_DetailDraft({
{children}
</AppComponentGlobal_LayoutTamplate>
</>
);
)
}

View File

@@ -11,6 +11,7 @@ import { MODEL_EVENT } from "../../model/interface";
import { Event_funEditStatusById } from "../../fun/edit/fun_edit_status_by_id";
import { ComponentGlobal_NotifikasiGagal } from "@/app_modules/component_global/notif_global/notifikasi_gagal";
import ComponentEvent_CatatanReject from "../../component/catatan_reject";
import { useState } from "react";
export default function Event_DetailReview({
dataEvent,
@@ -19,15 +20,20 @@ export default function Event_DetailReview({
}) {
const router = useRouter();
const [tabsStatus, setTabsStatus] = useAtom(gs_event_status);
const [isLoading, setLoading] = useState(false);
return (
<>
<Stack spacing={"xl"}>
<ComponentEvent_DetailData data={dataEvent} />
<Button
loaderPosition="center"
loading={isLoading ? true : false}
radius={"xl"}
color={"red"}
onClick={() => onClick(router, setTabsStatus, dataEvent.id)}
color={"orange"}
onClick={() =>
onClick(router, setTabsStatus, dataEvent.id, setLoading)
}
>
Batalkan Review
</Button>
@@ -39,12 +45,14 @@ export default function Event_DetailReview({
async function onClick(
router: AppRouterInstance,
setTabsStatus: any,
eventId: string
eventId: string,
setLoading: any
) {
await Event_funEditStatusById("3", eventId).then((res) => {
if (res.status === 200) {
ComponentGlobal_NotifikasiBerhasil(res.message, 1500);
setTabsStatus("Draft");
setLoading(true);
router.back();
} else {
ComponentGlobal_NotifikasiGagal(res.message);

View File

@@ -9,6 +9,7 @@ export async function Event_getByStatusId(statusId: string, authorId: string) {
tanggal: "desc",
},
where: {
active: true,
eventMaster_StatusId: "1",
authorId: authorId,
tanggal: {
@@ -27,9 +28,10 @@ export async function Event_getByStatusId(statusId: string, authorId: string) {
if (statusId === "2") {
const data = await prisma.event.findMany({
orderBy: {
createdAt: "desc",
updatedAt: "desc",
},
where: {
active: true,
eventMaster_StatusId: "2",
authorId: authorId,
},
@@ -44,7 +46,11 @@ export async function Event_getByStatusId(statusId: string, authorId: string) {
}
if (statusId === "3") {
const data = await prisma.event.findMany({
orderBy: {
updatedAt: "desc",
},
where: {
active: true,
eventMaster_StatusId: "3",
authorId: authorId,
},
@@ -59,7 +65,11 @@ export async function Event_getByStatusId(statusId: string, authorId: string) {
}
if (statusId === "4") {
const data = await prisma.event.findMany({
orderBy: {
updatedAt: "desc",
},
where: {
active: true,
eventMaster_StatusId: "4",
authorId: authorId,
},

View File

@@ -9,6 +9,7 @@ export async function Event_getListAllPublish() {
tanggal: "desc",
},
where: {
active: true,
eventMaster_StatusId: "1",
tanggal: {
gte: new Date(),

View File

@@ -30,6 +30,8 @@ import { RouterProfile } from "@/app/lib/router_hipmi/router_katalog";
import ComponentGlobal_AuthorNameOnHeader from "@/app_modules/component_global/author_name_on_header";
import _ from "lodash";
import { IconCirclePlus } from "@tabler/icons-react";
import ComponentEvent_IsEmptyData from "../component/is_empty_data";
import { useWindowScroll } from "@mantine/hooks";
export default function Event_Beranda({
dataEvent,
@@ -37,21 +39,18 @@ export default function Event_Beranda({
dataEvent: MODEL_EVENT[];
}) {
const router = useRouter();
const [loading, setLoading] = useState(false);
const [isLoading, setLoading] = useState(false);
const [scroll, scrollTo] = useWindowScroll();
// if (_.isEmpty(dataEvent))
// return (
// <Center h={"80vh"}>
// <Text fw={"bold"} fz={"sm"}>
// Tidak Ada Event
// </Text>
// </Center>
// );
return (
<>
<Affix position={{ bottom: rem(150), right: rem(30) }}>
<Affix position={{ bottom: rem(150), right: rem(30) }} zIndex={99}>
<ActionIcon
loading={loading ? true : false}
loading={isLoading ? true : false}
opacity={scroll.y > 0 ? 0.5 : ""}
style={{
transition: "0.5s",
}}
size={"xl"}
radius={"xl"}
variant="transparent"
@@ -64,49 +63,46 @@ export default function Event_Beranda({
<IconCirclePlus color="white" size={40} />
</ActionIcon>
</Affix>
{_.isEmpty(dataEvent) ? (
<Center h={"80vh"}>
<Text fw={"bold"} fz={"sm"}>
Tidak Ada Event
</Text>
</Center>
<ComponentEvent_IsEmptyData text="Tidak ada data" />
) : (
<Box>
{dataEvent.map((e, i) => (
<Card key={e.id} shadow="lg" radius={"md"} withBorder mb={"sm"}>
<Card.Section px={"sm"} pt={"sm"}>
<ComponentGlobal_AuthorNameOnHeader
profileId={e.Author.Profile.id}
imagesId={e.Author.Profile.imagesId}
authorName={e.Author.Profile.name}
/>
</Card.Section>
<Card.Section
p={"sm"}
onClick={() => router.push(RouterEvent.detail_main + e.id)}
>
<Stack>
<Grid>
<Grid.Col span={8}>
<Title order={6} truncate>
{e.title}
</Title>
</Grid.Col>
<Grid.Col span={4}>
<Text fz={"sm"} truncate>
{moment(e.tanggal).format("ll")}
</Text>
</Grid.Col>
</Grid>
{Array(10)
.fill(0)
.map((e, i) => (
<Card key={i} shadow="lg" radius={"md"} withBorder mb={"sm"}>
<Card.Section px={"sm"} pt={"sm"}>
<ComponentGlobal_AuthorNameOnHeader
profileId={e?.Author.Profile.id}
imagesId={e?.Author.Profile.imagesId}
authorName={e?.Author.Profile.name}
/>
</Card.Section>
<Card.Section
p={"sm"}
onClick={() => router.push(RouterEvent.detail_main + e?.id)}
>
<Stack>
<Grid>
<Grid.Col span={8}>
<Title order={6} truncate>
{e?.title}
</Title>
</Grid.Col>
<Grid.Col span={4}>
<Text fz={"sm"} truncate>
{moment(e?.tanggal).format("ll")}
</Text>
</Grid.Col>
</Grid>
<Text fz={"sm"} lineClamp={2}>
{e.deskripsi}
</Text>
</Stack>
</Card.Section>
</Card>
))}
<Text fz={"sm"} lineClamp={2}>
{e?.deskripsi}
</Text>
</Stack>
</Card.Section>
</Card>
))}
</Box>
)}
</>

View File

@@ -0,0 +1,156 @@
"use client";
import { RouterProfile } from "@/app/lib/router_hipmi/router_katalog";
import {
Stack,
Grid,
Avatar,
Divider,
Text,
Group,
Badge,
Loader,
} from "@mantine/core";
import { useRouter } from "next/navigation";
import moment from "moment";
import { ComponentGlobal_NotifikasiPeringatan } from "@/app_modules/component_global/notif_global/notifikasi_peringatan";
import { RouterForum } from "@/app/lib/router_hipmi/router_forum";
import {
IconCircleFilled,
IconDots,
IconEdit,
IconFlag3,
IconMessageCircle,
IconTrash,
} from "@tabler/icons-react";
import { IconCircle } from "@tabler/icons-react";
import { IoIosMore } from "react-icons/io";
import { useDisclosure } from "@mantine/hooks";
import { useState } from "react";
import ComponentForum_PostingButtonMore from "../more_button/posting_button_more";
import ComponentGlobal_V2_LoadingPage from "@/app_modules/component_global/loading_page_v2";
import { data } from "autoprefixer";
import ComponentForum_BerandaButtonMore from "./beranda_button_more";
export default function ComponentForum_BerandaAuthorNameOnHeader({
authorId,
postingId,
imagesId,
authorName,
tglPublish,
isPembatas,
isMoreButton,
statusId,
userLoginId,
setData,
}: {
authorId?: string;
postingId?: string;
imagesId?: string;
authorName?: string;
tglPublish?: Date;
isPembatas?: boolean;
isMoreButton?: boolean;
statusId?: string;
userLoginId: string;
setData?: any;
}) {
const router = useRouter();
const [loading, setLoading] = useState(false);
return (
<>
<Stack spacing={"xs"}>
<Grid>
<Grid.Col
span={"content"}
onClick={() => {
if (authorId) {
setLoading(true);
router.push(RouterForum.forumku + authorId);
} else {
ComponentGlobal_NotifikasiPeringatan("Id tidak ditemukan");
}
}}
>
{loading ? (
<Loader color="gray" variant="dots" />
) : (
<Avatar
size={40}
sx={{ borderStyle: "solid", borderWidth: "0.5px" }}
radius={"xl"}
bg={"gray.1"}
src={
imagesId
? RouterProfile.api_foto_profile + imagesId
: "/aset/global/avatar.png"
}
/>
)}
</Grid.Col>
<Grid.Col span={"auto"}>
<Stack justify="center" h={"100%"} spacing={0}>
<Grid>
<Grid.Col span={"auto"}>
<Text lineClamp={1} fz={"sm"} fw={"bold"}>
{authorName ? authorName : "Nama author "}
</Text>
</Grid.Col>
<Grid.Col span={"content"}></Grid.Col>
</Grid>
<Badge
w={70}
variant="light"
color={(statusId as any) === 1 ? "green" : "red"}
>
<Text fz={10}>
{(statusId as any) === 1 ? "Open" : "Close"}
</Text>
</Badge>
</Stack>
</Grid.Col>
<Grid.Col span={"content"}>
<Group position="center" spacing={"xs"}>
<Group spacing={3}>
<Text c={"gray"} fz={"sm"}>
{tglPublish
? tglPublish.toLocaleDateString(["id-ID"], {
day: "numeric",
month: "short",
})
: new Date().toLocaleDateString(["id-ID"], {
day: "numeric",
month: "short",
})}
<IconCircle
size={5}
color="gray"
style={{ marginLeft: "5px" }}
/>
</Text>
</Group>
{isMoreButton ? (
<Group position="right">
<ComponentForum_BerandaButtonMore
authorId={authorId}
postingId={postingId as any}
statusId={statusId}
userLoginId={userLoginId}
setData={setData}
/>
</Group>
) : (
""
)}
</Group>
</Grid.Col>
</Grid>
{isPembatas ? <Divider /> : ""}
</Stack>
</>
);
}

View File

@@ -0,0 +1,352 @@
"use client";
import { RouterForum } from "@/app/lib/router_hipmi/router_forum";
import { ComponentGlobal_NotifikasiBerhasil } from "@/app_modules/component_global/notif_global/notifikasi_berhasil";
import {
Drawer,
Stack,
Grid,
Button,
Modal,
Title,
Group,
ActionIcon,
Text,
Box,
Center,
Loader,
} from "@mantine/core";
import { useDisclosure, useShallowEffect } from "@mantine/hooks";
import {
IconTrash,
IconEdit,
IconFlag3,
IconDots,
IconSquareRoundedX,
IconSquareCheck,
} from "@tabler/icons-react";
import { useRouter } from "next/navigation";
import { useState } from "react";
import { createStyles } from "@mantine/core";
import ComponentGlobal_V2_LoadingPage from "@/app_modules/component_global/loading_page_v2";
import { useAtom } from "jotai";
import { gs_forum_loading_edit_posting } from "../../global_state";
import ComponentForum_LoadingDrawer from "../loading_drawer";
import { user_getOneUserId } from "@/app_modules/fun_global/get_user_token";
import { forum_funDeletePostingById } from "../../fun/delete/fun_delete_posting_by_id";
import { ComponentGlobal_NotifikasiGagal } from "@/app_modules/component_global/notif_global/notifikasi_gagal";
import { forum_funEditStatusPostingById } from "../../fun/edit/fun_edit_status_posting_by_id";
import { forum_getListAllPosting } from "../../fun/get/get_list_all_posting";
import { forum_getListPostingByAuhtorId } from "../../fun/get/get_list_posting_by_author_id";
export default function ComponentForum_BerandaButtonMore({
authorId,
postingId,
statusId,
userLoginId,
setData,
}: {
authorId: any;
postingId?: any;
statusId?: any;
userLoginId: any;
setData: any;
}) {
const router = useRouter();
// modal & drawer
const [opened, { open, close }] = useDisclosure(false);
const [openDel, setOpenDel] = useState(false);
const [openStatusClose, setOpenStatusClose] = useState(false);
// loading
const [loadingEdit, setLoadingEdit] = useState(false);
const [loadingReport, setLoadingReport] = useState(false);
// if (loadingEdit) return <ComponentGlobal_V2_LoadingPage />;
return (
<>
<Drawer
// className={classes.radiusCustom}
opened={opened}
onClose={close}
withCloseButton={false}
overlayProps={{ opacity: 0.1, blur: 1 }}
position="bottom"
size={"auto"}
>
<Stack>
{userLoginId != authorId ? (
""
) : (
<Stack>
<Grid
onClick={() => {
close();
setOpenStatusClose(true);
}}
>
<Grid.Col span={"content"}>
{statusId === 1 ? (
<IconSquareRoundedX color="red" />
) : (
<IconSquareCheck />
)}
</Grid.Col>
<Grid.Col span={"auto"}>
{statusId === 1 ? (
<Text c={"red"}>Tutup forum</Text>
) : (
<Text>Buka forum</Text>
)}
</Grid.Col>
</Grid>
<Grid
onClick={() => {
close();
setOpenDel(true);
}}
>
<Grid.Col span={"content"}>
<IconTrash color="red" />
</Grid.Col>
<Grid.Col span={"auto"}>
<Text c={"red"}>Hapus</Text>
</Grid.Col>
</Grid>
<Grid
onClick={() => {
setLoadingEdit(true);
router.push(RouterForum.edit_posting + postingId);
}}
>
<Grid.Col span={"content"}>
<IconEdit color={loadingEdit ? "gray" : "black"} />
</Grid.Col>
<Grid.Col span={"auto"}>
<Group>
<Text c={loadingEdit ? "gray" : "black"}>Edit posting</Text>{" "}
{loadingEdit ? <Loader size={"sm"} /> : ""}
</Group>
</Grid.Col>
</Grid>
</Stack>
)}
{userLoginId == authorId ? (
""
) : (
<Grid
onClick={() => {
setLoadingReport(true);
router.push(RouterForum.report_posting + postingId);
}}
>
<Grid.Col span={"content"}>
<IconFlag3 color={loadingReport ? "gray" : "black"} />
</Grid.Col>
<Grid.Col span={"auto"}>
<Group>
<Text c={loadingReport ? "gray" : "black"}>
Laporkan posting
</Text>{" "}
{loadingReport ? <Loader size={"sm"} /> : ""}
</Group>
</Grid.Col>
</Grid>
)}
<Button variant="outline" radius={"xl"} onClick={close}>
Batal
</Button>
</Stack>
</Drawer>
<Modal
opened={openDel}
onClose={() => {
setOpenDel(false);
}}
centered
withCloseButton={false}
>
<ButtonDelete
postingId={postingId}
setOpenDel={setOpenDel}
setData={setData}
/>
</Modal>
<Modal
opened={openStatusClose}
onClose={() => setOpenStatusClose(false)}
centered
withCloseButton={false}
>
<ButtonStatus
postingId={postingId}
setOpenStatus={setOpenStatusClose}
statusId={statusId}
setData={setData}
userLoginId={userLoginId}
authorId={authorId}
/>
</Modal>
<ActionIcon variant="transparent" onClick={() => open()}>
<IconDots size={20} />
</ActionIcon>
</>
);
}
function ButtonDelete({
postingId,
setOpenDel,
setData,
}: {
postingId?: string;
setOpenDel: any;
setData: any;
}) {
const [loading, setLoading] = useState(false);
async function onDelete() {
setOpenDel(false);
await forum_funDeletePostingById(postingId as any).then(async (res) => {
if (res.status === 200) {
ComponentGlobal_NotifikasiBerhasil(`Postingan Terhapus`, 2000);
setLoading(true);
const listForum = await forum_getListAllPosting();
setData(listForum);
} else {
ComponentGlobal_NotifikasiGagal(res.message);
}
});
}
return (
<>
<Stack>
<Title order={6}>Yakin menghapus posting ini ?</Title>
<Group position="center">
<Button radius={"xl"} onClick={() => setOpenDel(false)}>
Batal
</Button>
<Button
loaderPosition="center"
loading={loading ? true : false}
color="red"
radius={"xl"}
onClick={() => {
onDelete();
}}
>
Hapus
</Button>
</Group>
</Stack>
</>
);
}
function ButtonStatus({
postingId,
setOpenStatus,
statusId,
setData,
userLoginId,
authorId,
}: {
postingId?: string;
setOpenStatus: any;
statusId?: any;
setData: any;
userLoginId: string;
authorId: string;
}) {
const [loading, setLoading] = useState(false);
async function onTutupForum() {
setOpenStatus(false);
await forum_funEditStatusPostingById(postingId as any, 2).then(
async (res) => {
if (res.status === 200) {
await forum_getListAllPosting().then((val) => {
setData(val as any);
ComponentGlobal_NotifikasiBerhasil(`Forum Ditutup`, 2000);
setLoading(true);
});
} else {
ComponentGlobal_NotifikasiGagal(res.message);
}
}
);
}
async function onBukaForum() {
setOpenStatus(false);
await forum_funEditStatusPostingById(postingId as any, 1).then(
async (res) => {
if (res.status === 200) {
await forum_getListAllPosting().then((val) => {
setData(val as any);
ComponentGlobal_NotifikasiBerhasil(`Forum Dibuka`, 2000);
setLoading(true);
});
} else {
ComponentGlobal_NotifikasiGagal(res.message);
}
}
);
}
return (
<>
<Stack>
{statusId === 1 ? (
<Title order={6}>Yakin menutup forum ini ?</Title>
) : (
<Title order={6}>Yakin membuka forum ini ?</Title>
)}
<Group position="center">
<Button radius={"xl"} onClick={() => setOpenStatus(false)}>
Batal
</Button>
{statusId === 1 ? (
<Button
loaderPosition="center"
loading={loading ? true : false}
color="orange"
radius={"xl"}
onClick={() => {
onTutupForum();
}}
>
Tutup
</Button>
) : (
<Button
loaderPosition="center"
loading={loading ? true : false}
color="green"
radius={"xl"}
onClick={() => {
onBukaForum();
}}
>
Buka
</Button>
)}
</Group>
</Stack>
</>
);
}

View File

@@ -0,0 +1,101 @@
"use client";
import { RouterForum } from "@/app/lib/router_hipmi/router_forum";
import { Stack, Card, Group, ActionIcon, Divider, Text } from "@mantine/core";
import { IconMessageCircle, IconMessageCircleOff } from "@tabler/icons-react";
import { useState } from "react";
import { useShallowEffect } from "@mantine/hooks";
import { useRouter } from "next/navigation";
import { useAtom } from "jotai";
import { ComponentGlobal_NotifikasiPeringatan } from "@/app_modules/component_global/notif_global/notifikasi_peringatan";
import { IconMessageCircleX } from "@tabler/icons-react";
import { MODEL_FORUM_POSTING } from "../../model/interface";
import ComponentForum_BerandaAuthorNameOnHeader from "./beranda_author_header";
export default function ComponentForum_BerandaCardView({
data,
setData,
setLoadingKomen,
setLoadingDetail,
userLoginId,
}: {
data: MODEL_FORUM_POSTING[];
setData: any;
setLoadingKomen: any;
setLoadingDetail: any;
userLoginId: any;
}) {
const router = useRouter();
return (
<>
<Stack spacing={"xl"}>
{data.map((e, i) => (
<Card key={i}>
<Card.Section>
{/* <pre>{JSON.stringify(e.Author.id, null, 2)}</pre>
<pre>{JSON.stringify(userLoginId, null, 2)}</pre> */}
<ComponentForum_BerandaAuthorNameOnHeader
authorName={e?.Author?.Profile?.name}
imagesId={e?.Author?.Profile?.imagesId}
tglPublish={e?.createdAt}
isMoreButton={true}
authorId={e?.Author?.id}
postingId={e?.id}
statusId={e?.ForumMaster_StatusPosting?.id}
userLoginId={userLoginId}
setData={setData}
/>
</Card.Section>
<Card.Section
sx={{ zIndex: 0 }}
p={"lg"}
onClick={() => {
// console.log("halaman forum");
setLoadingDetail(true);
router.push(RouterForum.main_detail + e.id);
}}
>
<Text fz={"sm"} lineClamp={4}>
<div dangerouslySetInnerHTML={{ __html: e.diskusi }} />
</Text>
</Card.Section>
<Card.Section>
<Stack>
<Group spacing={"xs"} px={"sm"}>
<ActionIcon
// loading={loadingKomen ? true : false}
variant="transparent"
sx={{ zIndex: 1 }}
onClick={() => {
(e?.ForumMaster_StatusPosting.id as any) === 1
? (router.push(RouterForum.komentar + e?.id),
setLoadingKomen(true))
: router.push(RouterForum.main_detail + e?.id);
}}
>
{(e?.ForumMaster_StatusPosting?.id as any) === 1 ? (
<IconMessageCircle color="gray" size={25} />
) : (
<IconMessageCircleX color="gray" size={25} />
)}
</ActionIcon>
{/* <TotalKomentar postingId={e?.id} /> */}
<Text c={"gray"}>{e?._count}</Text>
</Group>
<Divider />
</Stack>
</Card.Section>
</Card>
))}
</Stack>
</>
);
}

View File

@@ -32,9 +32,8 @@ export default function ComponentForum_HeaderTamplate({
bg?: any;
}) {
const router = useRouter();
const [loading, setLoading] = useState(false);
if (loading) return <ComponentGlobal_V2_LoadingPage />;
const [isLoading, setLoading] = useState(false);
return (
<>
<Header
@@ -47,6 +46,7 @@ export default function ComponentForum_HeaderTamplate({
<ActionIcon variant="transparent" disabled></ActionIcon>
) : (
<ActionIcon
loading={isLoading ? true : false}
variant="transparent"
onClick={() => {
setLoading(true);

View File

@@ -29,6 +29,7 @@ import { useDisclosure } from "@mantine/hooks";
import { useState } from "react";
import ComponentForum_PostingButtonMore from "../more_button/posting_button_more";
import ComponentGlobal_V2_LoadingPage from "@/app_modules/component_global/loading_page_v2";
import { data } from "autoprefixer";
export default function ComponentForum_PostingAuthorNameOnHeader({
authorId,
@@ -40,6 +41,7 @@ export default function ComponentForum_PostingAuthorNameOnHeader({
isMoreButton,
statusId,
userLoginId,
setData,
}: {
authorId?: string;
postingId?: string;
@@ -50,6 +52,7 @@ export default function ComponentForum_PostingAuthorNameOnHeader({
isMoreButton?: boolean;
statusId?: string;
userLoginId: string;
setData?:any
}) {
const router = useRouter();
const [loading, setLoading] = useState(false);
@@ -128,6 +131,7 @@ export default function ComponentForum_PostingAuthorNameOnHeader({
/>
</Text>
</Group>
{isMoreButton ? (
<Group position="right">
<ComponentForum_PostingButtonMore
@@ -135,6 +139,7 @@ export default function ComponentForum_PostingAuthorNameOnHeader({
postingId={postingId as any}
statusId={statusId}
userLoginId={userLoginId}
setData={setData}
/>
</Group>
) : (

View File

@@ -17,14 +17,16 @@ import { IconMessageCircleX } from "@tabler/icons-react";
export default function ComponentForum_MainCardView({
data,
setData,
setLoadingKomen,
setLoadingDetail,
userLoginId,
}: {
data: MODEL_FORUM_POSTING[];
setData: any,
setLoadingKomen: any;
setLoadingDetail: any;
userLoginId: any
userLoginId: any;
}) {
const router = useRouter();
return (
@@ -33,7 +35,9 @@ export default function ComponentForum_MainCardView({
{data.map((e, i) => (
<Card key={i}>
<Card.Section>
{/* <pre>{JSON.stringify( typeof e.ForumMaster_StatusPosting.id)}</pre> */}
{/* <pre>{JSON.stringify(e.Author.id, null, 2)}</pre>
<pre>{JSON.stringify(userLoginId, null, 2)}</pre> */}
<ComponentForum_PostingAuthorNameOnHeader
authorName={e?.Author?.Profile?.name}
imagesId={e?.Author?.Profile?.imagesId}
@@ -43,6 +47,7 @@ export default function ComponentForum_MainCardView({
postingId={e?.id}
statusId={e?.ForumMaster_StatusPosting?.id}
userLoginId={userLoginId}
setData={setData}
/>
</Card.Section>
<Card.Section

View File

@@ -37,17 +37,21 @@ import { user_getOneUserId } from "@/app_modules/fun_global/get_user_token";
import { forum_funDeletePostingById } from "../../fun/delete/fun_delete_posting_by_id";
import { ComponentGlobal_NotifikasiGagal } from "@/app_modules/component_global/notif_global/notifikasi_gagal";
import { forum_funEditStatusPostingById } from "../../fun/edit/fun_edit_status_posting_by_id";
import { forum_getListAllPosting } from "../../fun/get/get_list_all_posting";
import { forum_getListPostingByAuhtorId } from "../../fun/get/get_list_posting_by_author_id";
export default function ComponentForum_PostingButtonMore({
authorId,
postingId,
statusId,
userLoginId,
setData,
}: {
authorId: any;
postingId?: any;
statusId?: any;
userLoginId: any;
setData: any;
}) {
const router = useRouter();
@@ -170,7 +174,11 @@ export default function ComponentForum_PostingButtonMore({
centered
withCloseButton={false}
>
<ButtonDelete postingId={postingId} setOpenDel={setOpenDel} />
<ButtonDelete
postingId={postingId}
setOpenDel={setOpenDel}
setData={setData}
/>
</Modal>
<Modal
@@ -183,6 +191,9 @@ export default function ComponentForum_PostingButtonMore({
postingId={postingId}
setOpenStatus={setOpenStatusClose}
statusId={statusId}
setData={setData}
userLoginId={userLoginId}
authorId={authorId}
/>
</Modal>
@@ -196,18 +207,22 @@ export default function ComponentForum_PostingButtonMore({
function ButtonDelete({
postingId,
setOpenDel,
setData,
}: {
postingId?: string;
setOpenDel: any;
setData: any;
}) {
const [loading, setLoading] = useState(false);
async function onDelete() {
setOpenDel(false);
await forum_funDeletePostingById(postingId as any).then((res) => {
await forum_funDeletePostingById(postingId as any).then(async (res) => {
if (res.status === 200) {
ComponentGlobal_NotifikasiBerhasil(`Postingan Terhapus`, 2000);
setLoading(true);
const listForum = await forum_getListAllPosting();
setData(listForum);
} else {
ComponentGlobal_NotifikasiGagal(res.message);
}
@@ -242,37 +257,61 @@ function ButtonStatus({
postingId,
setOpenStatus,
statusId,
setData,
userLoginId,
authorId,
}: {
postingId?: string;
setOpenStatus: any;
statusId?: any;
setData: any;
userLoginId: string;
authorId: string;
}) {
const [loading, setLoading] = useState(false);
async function onTutupForum() {
setOpenStatus(false);
await forum_funEditStatusPostingById(postingId as any, 2).then((res) => {
if (res.status === 200) {
ComponentGlobal_NotifikasiBerhasil(`Forum Ditutup`, 2000);
setLoading(true);
} else {
ComponentGlobal_NotifikasiGagal(res.message);
await forum_funEditStatusPostingById(postingId as any, 2).then(
async (res) => {
if (res.status === 200) {
if (userLoginId === authorId) {
await forum_getListPostingByAuhtorId(authorId).then((val: any) =>
setData(val)
);
} else {
await forum_getListAllPosting().then((val) => setData(val as any));
}
ComponentGlobal_NotifikasiBerhasil(`Forum Ditutup`, 2000);
setLoading(true);
} else {
ComponentGlobal_NotifikasiGagal(res.message);
}
}
});
);
}
async function onBukaForum() {
setOpenStatus(false);
await forum_funEditStatusPostingById(postingId as any, 1).then((res) => {
if (res.status === 200) {
ComponentGlobal_NotifikasiBerhasil(`Forum Dibuka`, 2000);
setLoading(true);
} else {
ComponentGlobal_NotifikasiGagal(res.message);
await forum_funEditStatusPostingById(postingId as any, 1).then(
async (res) => {
if (res.status === 200) {
if (userLoginId === authorId) {
await forum_getListPostingByAuhtorId(authorId).then((val: any) =>
setData(val)
);
} else {
await forum_getListAllPosting().then((val) => setData(val as any));
}
ComponentGlobal_NotifikasiBerhasil(`Forum Dibuka`, 2000);
setLoading(true);
} else {
ComponentGlobal_NotifikasiGagal(res.message);
}
}
});
);
}
return (

View File

@@ -2,12 +2,14 @@
import {
ActionIcon,
Box,
Button,
Center,
Group,
Loader,
Paper,
Stack,
Text,
} from "@mantine/core";
import "react-quill/dist/quill.snow.css";
import "react-quill/dist/quill.bubble.css";
@@ -23,6 +25,9 @@ import { ComponentGlobal_NotifikasiBerhasil } from "@/app_modules/component_glob
import { ComponentGlobal_NotifikasiGagal } from "@/app_modules/component_global/notif_global/notifikasi_gagal";
import { ComponentGlobal_NotifikasiPeringatan } from "@/app_modules/component_global/notif_global/notifikasi_peringatan";
import { RouterForum } from "@/app/lib/router_hipmi/router_forum";
import ComponentGlobal_ErrorInput from "@/app_modules/component_global/error_input";
import ComponentGlobal_InputCountDown from "@/app_modules/component_global/input_countdown";
import _ from "lodash";
const ReactQuill = dynamic(
() => {
return import("react-quill");
@@ -32,7 +37,8 @@ const ReactQuill = dynamic(
export default function Forum_Create() {
const [value, setValue] = useState("");
const [maxForum, setMaxForum] = useState(0);
const [totalLength, setTotalLength] = useState(0);
const [reload, setReload] = useState(false);
useShallowEffect(() => {
if (window && window.document) setReload(true);
@@ -48,27 +54,27 @@ export default function Forum_Create() {
return (
<>
<Stack>
<Paper withBorder shadow="lg">
<Paper withBorder shadow="lg" p={"xs"}>
<ReactQuill
theme="bubble"
placeholder="Apa yang sedang hangat dibicarakan ?"
placeholder="Apa yang sedang ingin dibahas ?"
style={{ height: 150 }}
onChange={(val) => {
// if (val.length > 300) {
// setMaxForum(val.length);
// }
setValue(val);
}}
/>
</Paper>
<Group position="right">
{/* <ActionIcon>
<IconPhotoUp />
</ActionIcon> */}
<ComponentGlobal_InputCountDown
maxInput={500}
lengthInput={value.length}
/>
</Group>
<Group position="right">
<ButtonAction value={value} />
</Group>
</Stack>
{/* <div dangerouslySetInnerHTML={{ __html: value }} /> */}
{/* <pre> {JSON.stringify(value, null, 2)}</pre> */}
</>
);
}
@@ -78,6 +84,10 @@ function ButtonAction({ value }: { value: string }) {
const [loading, setLoading] = useState(false);
async function onCreate() {
if (value.length > 500) {
return null;
}
await forum_funCreate(value).then((res) => {
if (res.status === 201) {
setLoading(true);
@@ -91,6 +101,14 @@ function ButtonAction({ value }: { value: string }) {
return (
<>
<Button
style={{
transition: "0.5s",
}}
disabled={
value === "<p><br></p>" || value === "" || value.length > 500
? true
: false
}
radius={"xl"}
loading={loading ? true : false}
loaderPosition="center"

View File

@@ -10,6 +10,7 @@ import {
Divider,
Group,
Paper,
Spoiler,
Stack,
Text,
} from "@mantine/core";
@@ -34,6 +35,7 @@ const ReactQuill = dynamic(
);
import "react-quill/dist/quill.bubble.css";
import { forum_getKomentarById } from "../fun/get/get_komentar_by_id";
import ComponentGlobal_InputCountDown from "@/app_modules/component_global/input_countdown";
export default function Forum_Detail({
dataPosting,
@@ -162,14 +164,20 @@ function CreateKomentar({
const router = useRouter();
const [value, setValue] = useState("");
const [loading, setLoading] = useState(false);
const [isEmpty, setIsEmpty] = useState(false);
async function onComment() {
if (value.length > 500) {
return null;
}
await forum_funCreateKomentar(postingId, value).then(async (res) => {
if (res.status === 201) {
await forum_getKomentarById(postingId).then((val) => {
setKomentar(val);
// setLoading(true);
setValue("");
setIsEmpty(true);
ComponentGlobal_NotifikasiBerhasil(res.message, 2000);
});
// router.replace(RouterForum.main_detail + postingId, { scroll: false });
@@ -192,8 +200,22 @@ function CreateKomentar({
}}
/>
</Paper>
<Group position="right">
<ComponentGlobal_InputCountDown
maxInput={500}
lengthInput={value.length}
/>
</Group>
<Group position="right">
<Button
style={{
transition: "0.5s",
}}
disabled={
value === "" || value === "<p><br></p>" || value.length > 500
? true
: false
}
loaderPosition="center"
loading={loading ? true : false}
radius={"xl"}
@@ -248,7 +270,13 @@ function KomentarView({
<Stack spacing={"xs"}>
<Text fz={"sm"} lineClamp={4}>
{e.komentar ? (
<div dangerouslySetInnerHTML={{ __html: e.komentar }} />
<Spoiler
hideLabel="sembunyikan"
maxHeight={100}
showLabel="tampilkan"
>
<div dangerouslySetInnerHTML={{ __html: e.komentar }} />
</Spoiler>
) : (
""
)}

View File

@@ -1,4 +1,4 @@
"use client"
"use client";
import {
ActionIcon,
@@ -16,7 +16,6 @@ import { useShallowEffect } from "@mantine/hooks";
import { useRouter } from "next/navigation";
import ComponentGlobal_V2_LoadingPage from "@/app_modules/component_global/loading_page_v2";
import dynamic from "next/dynamic";
import React, { useState } from "react";
import { useAtom } from "jotai";
@@ -73,10 +72,12 @@ function ButtonAction() {
return (
<>
<Button radius={"xl"} onClick={() => {
router.back()
}}>
<Button
radius={"xl"}
onClick={() => {
router.back();
}}
>
Update
</Button>
</>

View File

@@ -24,6 +24,8 @@ import { MODEL_FORUM_POSTING } from "../../model/interface";
import { forum_funEditPostingById } from "../../fun/edit/fun_edit_posting_by_id";
import { ComponentGlobal_NotifikasiBerhasil } from "@/app_modules/component_global/notif_global/notifikasi_berhasil";
import { ComponentGlobal_NotifikasiGagal } from "@/app_modules/component_global/notif_global/notifikasi_gagal";
import { ComponentGlobal_NotifikasiPeringatan } from "@/app_modules/component_global/notif_global/notifikasi_peringatan";
import ComponentGlobal_InputCountDown from "@/app_modules/component_global/input_countdown";
const ReactQuill = dynamic(
() => {
return import("react-quill");
@@ -52,10 +54,10 @@ export default function Forum_EditPosting({
return (
<>
<Stack>
<Paper withBorder shadow="lg">
<Paper withBorder shadow="lg" p={"xs"}>
<ReactQuill
theme="bubble"
placeholder="Apa yang sedang hangat dibicarakan ?"
placeholder="Apa yang sedang ingin dibahas ?"
style={{ height: 150 }}
value={value.diskusi}
onChange={(val) => {
@@ -66,6 +68,12 @@ export default function Forum_EditPosting({
}}
/>
</Paper>
<Group position="right">
<ComponentGlobal_InputCountDown
maxInput={500}
lengthInput={value.diskusi.length}
/>
</Group>
<Group position="right">
{/* <ActionIcon>
<IconPhotoUp />
@@ -73,7 +81,7 @@ export default function Forum_EditPosting({
<ButtonAction diskusi={value.diskusi as any} postingId={value.id} />
</Group>
</Stack>
{/* <div dangerouslySetInnerHTML={{ __html: value }} /> */}
{/* <div dangerouslySetInnerHTML={{ __html: value.diskusi }} /> */}
</>
);
}
@@ -89,11 +97,14 @@ function ButtonAction({
const [loading, setLoading] = useState(false);
async function onUpdate() {
if (diskusi === "<p><br></p>" || diskusi === "")
return ComponentGlobal_NotifikasiPeringatan("Masukan postingan anda");
await forum_funEditPostingById(postingId, diskusi).then((res) => {
if (res.status === 200) {
setLoading(true);
ComponentGlobal_NotifikasiBerhasil(res.message);
setTimeout(() => router.back(), 1000)
setTimeout(() => router.back(), 1000);
} else {
ComponentGlobal_NotifikasiGagal(res.message);
}
@@ -103,9 +114,17 @@ function ButtonAction({
return (
<>
<Button
disabled={
diskusi === "<p><br></p>" || diskusi === "" || diskusi.length > 500
? true
: false
}
loaderPosition="center"
loading={loading ? true : false}
radius={"xl"}
style={{
transition: "0.5s",
}}
onClick={() => {
onUpdate();
}}

View File

@@ -177,7 +177,7 @@ function ForumPosting({
userLoginId: any;
}) {
const router = useRouter();
const [data, setData] = useState(dataPosting);
const [loadingDetail, setLoadingDetail] = useState(false);
const [loadingKomen, setLoadingKomen] = useState(false);
@@ -185,11 +185,15 @@ function ForumPosting({
if (loadingKomen) return <ComponentGlobal_V2_LoadingPage />;
return (
<>
<ComponentForum_MainCardView
data={dataPosting}
data={data}
setLoadingKomen={setLoadingKomen}
setLoadingDetail={setLoadingDetail}
userLoginId={userLoginId}
setData={setData}
/>
{/* <Stack>

View File

@@ -37,11 +37,6 @@ export async function forum_getListAllPosting() {
},
},
ForumMaster_StatusPosting: true,
// _count: {
// select: {
// Forum_Komentar: true,
// },
// },
},
});

View File

@@ -1,50 +1,51 @@
"use server"
"use server";
import prisma from "@/app/lib/prisma";
import _ from "lodash"
import _ from "lodash";
export async function forum_funSearchListPosting(text:string) {
const get = await prisma.forum_Posting.findMany({
orderBy: [
// {
// forumMaster_StatusPostingId: "asc",
// },
{
createdAt: "desc",
},
],
take: 10,
where: {
diskusi: {
contains: text,
mode: "insensitive",
},
},
select: {
id: true,
diskusi: true,
createdAt: true,
isActive: true,
authorId: true,
Author: {
select: {
id: true,
Profile: true,
},
},
Forum_Komentar: {
where: {
isActive: true,
},
},
ForumMaster_StatusPosting: true,
},
});
export async function forum_funSearchListPosting(text: string) {
const get = await prisma.forum_Posting.findMany({
orderBy: [
// {
// forumMaster_StatusPostingId: "asc",
// },
{
createdAt: "desc",
},
],
take: 10,
where: {
isActive: true,
diskusi: {
contains: text,
mode: "insensitive",
},
},
select: {
id: true,
diskusi: true,
createdAt: true,
isActive: true,
authorId: true,
Author: {
select: {
id: true,
Profile: true,
},
},
Forum_Komentar: {
where: {
isActive: true,
},
},
ForumMaster_StatusPosting: true,
},
});
const data = get.map((val) => ({
..._.omit(val, ["Forum_Komentar"]),
_count: val.Forum_Komentar.length,
}));
const data = get.map((val) => ({
..._.omit(val, ["Forum_Komentar"]),
_count: val.Forum_Komentar.length,
}));
return data;
}
return data;
}

View File

@@ -27,13 +27,14 @@ import { MODEL_FORUM_POSTING } from "../model/interface";
import { forum_funCreateKomentar } from "../fun/create/fun_create_komentar";
import { ComponentGlobal_NotifikasiBerhasil } from "@/app_modules/component_global/notif_global/notifikasi_berhasil";
import { ComponentGlobal_NotifikasiGagal } from "@/app_modules/component_global/notif_global/notifikasi_gagal";
import ComponentGlobal_InputCountDown from "@/app_modules/component_global/input_countdown";
export default function Forum_Komentar({
dataPosting,
userLoginId,
}: {
dataPosting: MODEL_FORUM_POSTING;
userLoginId: any
userLoginId: any;
}) {
return (
<>
@@ -77,11 +78,15 @@ function CreateKomentar({ postingId }: { postingId: string }) {
const [loading, setLoading] = useState(false);
async function onComment() {
if (value.length > 500) {
return null;
}
await forum_funCreateKomentar(postingId, value).then((res) => {
if (res.status === 201) {
setLoading(true);
ComponentGlobal_NotifikasiBerhasil(res.message);
router.replace(RouterForum.main_detail + postingId, { scroll: false });
setLoading(true);
router.refresh();
} else {
ComponentGlobal_NotifikasiGagal(res.message);
@@ -102,11 +107,25 @@ function CreateKomentar({ postingId }: { postingId: string }) {
}}
/>
</Paper>
<Group position="right">
<ComponentGlobal_InputCountDown
maxInput={500}
lengthInput={value.length}
/>
</Group>
<Group position="right">
<Button
disabled={
value === "" || value === "<p><br></p>" || value.length > 500
? true
: false
}
loaderPosition="center"
loading={loading ? true : false}
radius={"xl"}
style={{
transition: "0.5s",
}}
onClick={() => onComment()}
>
Balas

View File

@@ -36,6 +36,7 @@ import ComponentForum_MainCardView from "../component/main_card_view";
import { forum_getListAllPosting } from "../fun/get/get_list_all_posting";
import { forum_funSearchListPosting } from "../fun/search/fun_search_list_posting";
import _ from "lodash";
import ComponentForum_BerandaCardView from "../component/beranda/beranda_card";
export default function Forum_Beranda({
listForum,
@@ -105,8 +106,9 @@ export default function Forum_Beranda({
</Stack>
</Stack>
) : (
<ComponentForum_MainCardView
<ComponentForum_BerandaCardView
data={data}
setData={setData}
setLoadingKomen={setLoadingKomen}
setLoadingDetail={setLoadingDetail}
userLoginId={userLoginId}

View File

@@ -16,6 +16,7 @@ import {
Paper,
Select,
Stack,
Text,
TextInput,
Textarea,
Title,
@@ -32,6 +33,8 @@ import { NotifPeringatan } from "@/app_modules/donasi/component/notifikasi/notif
import { ComponentGlobal_NotifikasiBerhasil } from "@/app_modules/component_global/notif_global/notifikasi_berhasil";
import { ComponentGlobal_NotifikasiGagal } from "@/app_modules/component_global/notif_global/notifikasi_gagal";
import { ComponentGlobal_NotifikasiPeringatan } from "@/app_modules/component_global/notif_global/notifikasi_peringatan";
import ComponentGlobal_ErrorInput from "@/app_modules/component_global/error_input";
import ComponentGlobal_InputCountDown from "@/app_modules/component_global/input_countdown";
export default function CreatePortofolio({
bidangBisnis,
@@ -60,6 +63,7 @@ export default function CreatePortofolio({
const [file, setFile] = useState<File | any>(null);
const [img, setImg] = useState<any | null>(null);
const [isFile, setIsFile] = useState(false);
return (
<>
@@ -72,7 +76,7 @@ export default function CreatePortofolio({
withAsterisk
label="Nama Bisnis"
placeholder="Nama bisnis"
error={value.namaBisnis.length > 100 ? "Maksimal 100 karakter" : ""}
maxLength={100}
onChange={(val) => {
setValue({
...value,
@@ -99,9 +103,7 @@ export default function CreatePortofolio({
withAsterisk
label="Alamat Kantor"
placeholder="Alamat kantor"
error={
value.alamatKantor.length > 100 ? "Maksimal 100 karakter" : ""
}
maxLength={100}
onChange={(val) => {
setValue({
...value,
@@ -121,21 +123,27 @@ export default function CreatePortofolio({
});
}}
/>
<Textarea
autosize
minRows={2}
maxRows={5}
withAsterisk
label="Deskripsi"
placeholder="Deskripsi singkat mengenai usaha"
error={value.deskripsi.length > 150 ? "Maksimal 150 karakter" : ""}
onChange={(val) => {
setValue({
...value,
deskripsi: val.target.value,
});
}}
/>
<Stack spacing={5}>
<Textarea
maxLength={150}
autosize
minRows={2}
maxRows={5}
withAsterisk
label="Deskripsi"
placeholder="Deskripsi singkat mengenai usaha"
onChange={(val) => {
setValue({
...value,
deskripsi: val.target.value,
});
}}
/>
<ComponentGlobal_InputCountDown
maxInput={150}
lengthInput={value.deskripsi.length}
/>
</Stack>
</Stack>
<Stack>
@@ -145,6 +153,8 @@ export default function CreatePortofolio({
<Image alt="Foto" src={img ? img : "/aset/no-img.png"} />
</Paper>
</AspectRatio>
{isFile ? <ComponentGlobal_ErrorInput text="Upload gambar" /> : ""}
<Center>
<FileButton
onChange={async (files: any | null) => {
@@ -160,6 +170,7 @@ export default function CreatePortofolio({
} else {
setImg(buffer);
setFile(files);
setIsFile(false);
}
} catch (error) {
console.log(error);
@@ -187,6 +198,7 @@ export default function CreatePortofolio({
<ComponentKatalog_NotedBox informasi="Isi hanya pada sosial media yang anda miliki" />
<TextInput
label="Facebook"
maxLength={100}
placeholder="Facebook"
onChange={(val) => {
setMedsos({
@@ -197,6 +209,7 @@ export default function CreatePortofolio({
/>
<TextInput
label="Instagram"
maxLength={100}
placeholder="Instagram"
onChange={(val) => {
setMedsos({
@@ -207,6 +220,7 @@ export default function CreatePortofolio({
/>
<TextInput
label="Tiktok"
maxLength={100}
placeholder="Tiktok"
onChange={(val) => {
setMedsos({
@@ -217,6 +231,7 @@ export default function CreatePortofolio({
/>
<TextInput
label="Twitter"
maxLength={100}
placeholder="Twitter"
onChange={(val) => {
setMedsos({
@@ -227,6 +242,7 @@ export default function CreatePortofolio({
/>
<TextInput
label="Youtube"
maxLength={100}
placeholder="Youtube"
onChange={(val) => {
setMedsos({
@@ -245,7 +261,15 @@ export default function CreatePortofolio({
loading={loading ? true : false}
loaderPosition="center"
onClick={() => {
onSubmit(router, profileId, value as any, file, medsos, setLoading);
onSubmit(
router,
profileId,
value as any,
file,
medsos,
setLoading,
setIsFile
);
}}
>
Simpan
@@ -263,7 +287,8 @@ async function onSubmit(
dataPorto: MODEL_PORTOFOLIO_OLD,
file: FormData,
dataMedsos: any,
setLoading: any
setLoading: any,
setIsFile: any
) {
const porto = {
namaBisnis: dataPorto.namaBisnis,
@@ -272,14 +297,13 @@ async function onSubmit(
tlpn: dataPorto.tlpn,
deskripsi: dataPorto.deskripsi,
};
if (_.values(porto).includes(""))
return ComponentGlobal_NotifikasiPeringatan("Lengkapi Data");
if (!file)
return ComponentGlobal_NotifikasiPeringatan("Lengkapi logo bisnis");
if (porto.namaBisnis.length > 100) return null;
if (porto.alamatKantor.length > 100) return null;
if (porto.deskripsi.length > 150) return null;
if (file === null) {
setIsFile(true);
return null;
}
const gambar = new FormData();
gambar.append("file", file as any);

View File

@@ -13,6 +13,8 @@ import { Portofolio_funEditDataBisnis } from "../../fun/edit/fun_edit_data_bisni
import { ComponentGlobal_NotifikasiBerhasil } from "@/app_modules/component_global/notif_global/notifikasi_berhasil";
import { ComponentGlobal_NotifikasiGagal } from "@/app_modules/component_global/notif_global/notifikasi_gagal";
import { ComponentGlobal_NotifikasiPeringatan } from "@/app_modules/component_global/notif_global/notifikasi_peringatan";
import ComponentGlobal_ErrorInput from "@/app_modules/component_global/error_input";
import ComponentGlobal_InputCountDown from "@/app_modules/component_global/input_countdown";
export default function Portofolio_EditDataBisnis({
dataPorto,
@@ -35,7 +37,14 @@ export default function Portofolio_EditDataBisnis({
value={value.namaBisnis}
label="Nama Bisnis"
placeholder="Nama bisnis"
error={value.namaBisnis.length > 100 ? "Maksimal 100 karakter" : ""}
maxLength={100}
error={
value.namaBisnis === "" ? (
<ComponentGlobal_ErrorInput text="Masukan nama bisnis" />
) : (
""
)
}
onChange={(val) => {
setValue({
...value,
@@ -66,8 +75,13 @@ export default function Portofolio_EditDataBisnis({
value={value.alamatKantor}
label="Alamat Kantor"
placeholder="Alamat kantor"
maxLength={100}
error={
value.alamatKantor.length > 100 ? "Maksimal 100 karakter" : ""
value.alamatKantor === "" ? (
<ComponentGlobal_ErrorInput text="Masukan alamat kantor" />
) : (
""
)
}
onChange={(val) => {
setValue({
@@ -80,8 +94,16 @@ export default function Portofolio_EditDataBisnis({
withAsterisk
value={value.tlpn}
label="Nomor Telepon Kantor"
placeholder="62 xxx xxx xxx"
placeholder="Nomor telepon kantor"
type="number"
maxLength={15}
error={
value.tlpn === "" ? (
<ComponentGlobal_ErrorInput text="Masukan nomor telepon kantor" />
) : (
""
)
}
onChange={(val) => {
setValue({
...value,
@@ -89,22 +111,35 @@ export default function Portofolio_EditDataBisnis({
});
}}
/>
<Textarea
autosize
minRows={2}
maxRows={5}
withAsterisk
value={value.deskripsi}
label="Deskripsi"
placeholder="Deskripsi singkat mengenai usaha"
error={value.deskripsi.length > 150 ? "Maksimal 150 karakter" : ""}
onChange={(val) => {
setValue({
...value,
deskripsi: val.target.value,
});
}}
/>
<Stack spacing={5}>
<Textarea
autosize
minRows={2}
maxRows={5}
withAsterisk
value={value.deskripsi}
label="Deskripsi"
placeholder="Deskripsi singkat mengenai usaha"
maxLength={150}
error={
value.deskripsi === "" ? (
<ComponentGlobal_ErrorInput text="Masukan deskripsi" />
) : (
""
)
}
onChange={(val) => {
setValue({
...value,
deskripsi: val.target.value,
});
}}
/>
<ComponentGlobal_InputCountDown
maxInput={150}
lengthInput={value.deskripsi.length}
/>
</Stack>
</Stack>
<Button
radius={"xl"}
@@ -126,12 +161,13 @@ async function onUpdate(
data: MODEL_PORTOFOLIO,
setLoading: any
) {
if (_.values(data).includes(""))
return ComponentGlobal_NotifikasiPeringatan("Lengkapi Data");
if (_.values(data).includes("")) {
return null;
}
if (data.namaBisnis.length > 100) return null;
if (data.alamatKantor.length > 100) return null;
if (data.deskripsi.length > 150) return null;
// if (data.namaBisnis.length > 100) return null;
// if (data.alamatKantor.length > 100) return null;
// if (data.deskripsi.length > 150) return null;
await Portofolio_funEditDataBisnis(data).then((res) => {
if (res.status === 200) {

View File

@@ -185,7 +185,7 @@ export default function ViewPortofolio({
</Grid>
</Stack>
</Paper>
{userLoginId === dataPorto.Profile.User.id ? (
{userLoginId === dataPorto?.Profile?.User?.id ? (
<Button
radius={"xl"}
bg={"red"}
@@ -233,7 +233,7 @@ async function onDelete(
if (res.status === 200) {
setLoadingDel(true);
ComponentGlobal_NotifikasiBerhasil(res.message);
router.push(RouterProfile.katalog + `${dataPorto.profileId}`);
router.back();
} else {
ComponentGlobal_NotifikasiGagal(res.message);
}

View File

@@ -128,17 +128,7 @@ export default function CreateProfile({ userId }: { userId: any }) {
<Stack>
<ComponentKatalog_NotedBox informasi="Upload foto latar belakang profile anda." />
<AspectRatio ratio={16 / 9}>
<Paper
radius={"md"}
withBorder
shadow="lg"
bg={"gray.2"}
// sx={{
// borderStyle: "solid",
// borderColor: "black",
// borderWidth: "1px",
// }}
>
<Paper radius={"md"} withBorder shadow="lg" bg={"gray.2"}>
{imgBG ? (
<Image alt="Foto" src={imgBG ? imgBG : "/aset/no-img.png"} />
) : (
@@ -197,6 +187,7 @@ export default function CreateProfile({ userId }: { userId: any }) {
<TextInput
withAsterisk
label="Nama"
maxLength={50}
placeholder="Nama lengkap"
onChange={(val) => {
setValue({
@@ -209,6 +200,7 @@ export default function CreateProfile({ userId }: { userId: any }) {
withAsterisk
icon={<IconAt size={15} />}
label="Email"
maxLength={100}
placeholder="Contoh: User@gmail.com"
error={
value.email.length > 0 && !value.email.match(validRegex)
@@ -225,8 +217,8 @@ export default function CreateProfile({ userId }: { userId: any }) {
<TextInput
withAsterisk
label="Alamat"
maxLength={100}
placeholder="Alamat lengkap"
error={value.alamat.length > 100 ? "Max 100 karakter" : ""}
onChange={(val) => {
setValue({
...value,
@@ -288,7 +280,6 @@ function ButtonAction({
if (_.values(body).includes(""))
return ComponentGlobal_NotifikasiPeringatan("Lengkapi Data");
if (!body.email.match(validRegex)) return null;
if (body.alamat.length > 100) return null;
const gambarPP = new FormData();
gambarPP.append("filePP", filePP as any);

View File

@@ -19,6 +19,7 @@ import { Profile_funEditById } from "../fun/update/fun_edit_profile_by_id";
import { RouterProfile } from "@/app/lib/router_hipmi/router_katalog";
import { validRegex } from "../../component/regular_expressions";
import { ComponentGlobal_NotifikasiPeringatan } from "@/app_modules/component_global/notif_global/notifikasi_peringatan";
import ComponentGlobal_ErrorInput from "@/app_modules/component_global/error_input";
export default function EditProfile({ data }: { data: MODEL_PROFILE }) {
const router = useRouter();
@@ -31,10 +32,8 @@ export default function EditProfile({ data }: { data: MODEL_PROFILE }) {
const body = dataProfile;
// console.log(body)
if (_.values(body).includes(""))
return ComponentGlobal_NotifikasiPeringatan("Lengkapi data");
if (_.values(body).includes("")) return null;
if (!body.email.match(validRegex)) return null;
if (body.alamat.length > 100) return null;
await Profile_funEditById(body).then((res) => {
if (res.status === 200) {
@@ -77,7 +76,6 @@ export default function EditProfile({ data }: { data: MODEL_PROFILE }) {
value={dataProfile?.User?.username}
onChange={(val) => {
// const dataUsername = _.clone(dataProfile)
setDataProfile({
...(dataProfile as any),
User: {
@@ -90,7 +88,15 @@ export default function EditProfile({ data }: { data: MODEL_PROFILE }) {
<TextInput
withAsterisk
label="Nama"
placeholder="Nama"
placeholder="nama"
maxLength={50}
error={
dataProfile?.name === "" ? (
<ComponentGlobal_ErrorInput text="Masukan nama" />
) : (
""
)
}
value={dataProfile?.name}
onChange={(val) => {
setDataProfile({
@@ -105,10 +111,14 @@ export default function EditProfile({ data }: { data: MODEL_PROFILE }) {
label="Email"
placeholder="email"
error={
dataProfile?.email?.length > 0 &&
!dataProfile?.email.match(validRegex)
? "Invalid email"
: ""
dataProfile?.email === "" ? (
<ComponentGlobal_ErrorInput text="Masukan email " />
) : dataProfile?.email?.length > 0 &&
!dataProfile?.email.match(validRegex) ? (
<ComponentGlobal_ErrorInput text="Invalid email" />
) : (
""
)
}
value={dataProfile?.email}
onChange={(val) => {
@@ -124,7 +134,14 @@ export default function EditProfile({ data }: { data: MODEL_PROFILE }) {
label="Alamat"
placeholder="alamat"
value={dataProfile.alamat}
error={dataProfile.alamat.length > 100 ? "Max 100 karakter" : ""}
maxLength={100}
error={
dataProfile?.alamat === "" ? (
<ComponentGlobal_ErrorInput text="Masukan alamat " />
) : (
""
)
}
onChange={(val) => {
setDataProfile({
...dataProfile,

3
src/util/evn.ts Normal file
View File

@@ -0,0 +1,3 @@
import { EventEmitter } from "events";
export const evnPesan = new EventEmitter();

View File

@@ -4,17 +4,22 @@ import { useEffect, useState } from "react";
import mqtt_client from "./mqtt_client";
import { useAtom } from "jotai";
import { gs_coba_chat } from "@/app/makuro/gs_coba";
import { evnPesan } from "./evn";
export default function MqttLoader() {
useEffect(() => {
mqtt_client.on("connect", () => {
console.log("connected");
// mqtt_client.subscribe("server12");
mqtt_client.subscribe("pesan");
// fetch("").then((res) => {
// mqtt_client.subscribe("pesan");
// });
});
// mqtt_client.on("message", (apa) => {
// console.log("Ini yang di utils");
// });
mqtt_client.on("message", (apa: any, itu: any) => {
console.log(itu)
evnPesan.emit("pesan", itu);
});
}, []);
return null;
}