From 5875b640693a4ecdb345fd68e8e7080a3ba0f905 Mon Sep 17 00:00:00 2001 From: Anang Yusman Date: Mon, 16 Jun 2025 16:07:58 +0800 Subject: [PATCH 1/3] feat: menu sidebar,emergency issue --- .../results/component/column.tsx | 12 +-- .../communication/questions-reply-form.tsx | 6 +- lib/menus.ts | 80 +++++++++---------- 3 files changed, 49 insertions(+), 49 deletions(-) diff --git a/app/[locale]/(protected)/admin/media-tracking/results/component/column.tsx b/app/[locale]/(protected)/admin/media-tracking/results/component/column.tsx index 69d40134..895c7df0 100644 --- a/app/[locale]/(protected)/admin/media-tracking/results/component/column.tsx +++ b/app/[locale]/(protected)/admin/media-tracking/results/component/column.tsx @@ -49,11 +49,11 @@ const columns: ColumnDef[] = [ header: "Jumlah Amplifikasi", cell: ({ row }) => {row.getValue("link")}, }, - // { - // accessorKey: "status", - // header: "Status", - // cell: ({ row }) => {row.getValue("status")}, - // }, + { + accessorKey: "status", + header: "Status", + cell: ({ row }) => {row.getValue("status")}, + }, { accessorKey: "date", header: "Tanggal Penarikan", @@ -85,7 +85,7 @@ const columns: ColumnDef[] = [ > - View{" "} + View {row.original.mediaUpload.fileType.secondaryName && row.original.mediaUpload.fileType.secondaryName.toLowerCase()} diff --git a/components/form/communication/questions-reply-form.tsx b/components/form/communication/questions-reply-form.tsx index b684de96..e8c2a54d 100644 --- a/components/form/communication/questions-reply-form.tsx +++ b/components/form/communication/questions-reply-form.tsx @@ -51,7 +51,7 @@ import { ChevronDownIcon } from "lucide-react"; import { getOperatorUser } from "@/service/management-user/management-user"; const taskSchema = z.object({ - message: z.string().optional(), + title: z.string().optional(), description: z.string().optional(), }); @@ -275,7 +275,7 @@ export default function FormQuestionsReply() { title: data.title, description: data.description, priorityId: selectedPriority, - statusId: selectedStatus, + statusId: 1, typeId: detailTickets?.typeId, parentCommentId: detailTickets?.feedId, operatorTeam: selectedOperator.join(","), @@ -507,7 +507,7 @@ export default function FormQuestionsReply() { ( Date: Wed, 18 Jun 2025 14:19:30 +0800 Subject: [PATCH 2/3] feat:update create content rewrite --- components/form/content/audio-form.tsx | 269 ++++- components/form/content/image-form.tsx | 236 ++++- components/form/content/spit-convert-form.tsx | 939 +++++++++--------- components/form/content/teks-form.tsx | 271 ++++- components/form/content/video-form.tsx | 275 ++++- 5 files changed, 1316 insertions(+), 674 deletions(-) diff --git a/components/form/content/audio-form.tsx b/components/form/content/audio-form.tsx index 8da158ab..0d9edd39 100644 --- a/components/form/content/audio-form.tsx +++ b/components/form/content/audio-form.tsx @@ -40,6 +40,7 @@ import { uploadThumbnailBlog } from "@/service/blog/blog"; import { Textarea } from "@/components/ui/textarea"; import { generateDataArticle, + generateDataRewrite, getDetailArticle, getGenerateKeywords, getGenerateTitle, @@ -55,6 +56,7 @@ import dynamic from "next/dynamic"; import { getCsrfToken } from "@/service/auth"; import { Link } from "@/i18n/routing"; import { useTranslations } from "next-intl"; +import { useParams } from "next/navigation"; interface FileWithPreview extends File { preview: string; @@ -82,6 +84,10 @@ export default function FormAudio() { const router = useRouter(); const editor = useRef(null); type AudioSchema = z.infer; + const params = useParams(); + const locale = params?.locale; + + const [selectedFileType, setSelectedFileType] = useState("original"); const [selectedFiles, setSelectedFiles] = useState([]); const taskId = Cookies.get("taskId"); @@ -97,6 +103,11 @@ export default function FormAudio() { const [preview, setPreview] = useState(null); const [selectedLanguage, setSelectedLanguage] = useState(""); + const [selectedWritingStyle, setSelectedWritingStyle] = + useState("professional"); + const [editorContent, setEditorContent] = useState(""); // Untuk original editor + const [rewriteEditorContent, setRewriteEditorContent] = useState(""); + const [selectedSEO, setSelectedSEO] = useState(""); const [title, setTitle] = useState(""); const [selectedAdvConfig, setSelectedAdvConfig] = useState(""); @@ -111,7 +122,6 @@ export default function FormAudio() { null ); const [selectedMainKeyword, setSelectedMainKeyword] = useState(""); - const [selectedWritingStyle, setSelectedWritingStyle] = useState(""); const [selectedSize, setSelectedSize] = useState(""); const [detailData, setDetailData] = useState(null); const [articleImages, setArticleImages] = useState([]); @@ -133,6 +143,8 @@ export default function FormAudio() { const [isStartUpload, setIsStartUpload] = useState(false); const [counterProgress, setCounterProgress] = useState(0); + const [isContentRewriteClicked, setIsContentRewriteClicked] = useState(false); + const [showRewriteEditor, setShowRewriteEditor] = useState(false); const [files, setFiles] = useState([]); const [publishedFor, setPublishedFor] = useState([]); @@ -155,15 +167,11 @@ export default function FormAudio() { const audioSchema = z.object({ title: z.string().min(1, { message: "Judul diperlukan" }), - description: z - .string() - .min(2, { message: "Narasi Penugasan harus lebih dari 2 karakter." }) - .or( - z.literal(articleBody || "").refine((val) => val.length > 0, { - message: "Deskripsi diperlukan.", - }) - ), + description: z.string().optional(), + descriptionOri: z.string().optional(), // Original editor + rewriteDescription: z.string().optional(), // Rewrite editor creatorName: z.string().min(1, { message: "Creator diperlukan" }), + // tags: z.string().min(1, { message: "Judul diperlukan" }), }); @@ -175,6 +183,11 @@ export default function FormAudio() { formState: { errors }, } = useForm({ resolver: zodResolver(audioSchema), + defaultValues: { + description: "", + descriptionOri: "", + rewriteDescription: "", + }, }); const doGenerateMainKeyword = async () => { @@ -437,12 +450,24 @@ export default function FormAudio() { } }; + useEffect(() => { + if (articleBody) { + // Set ke dua field jika rewrite juga aktif + setValue("description", articleBody); + setValue("rewriteDescription", articleBody); + } + }, [articleBody, setValue]); + const save = async (data: AudioSchema) => { loading(); const finalTags = tags.join(", "); const finalTitle = isSwitchOn ? title : data.title; - const finalDescription = articleBody || data.description; - if (!finalDescription.trim()) { + const finalDescription = isSwitchOn + ? data.description + : selectedFileType === "rewrite" + ? data.rewriteDescription + : data.descriptionOri; + if (!finalDescription?.trim()) { MySwal.fire("Error", "Deskripsi tidak boleh kosong.", "error"); return; } @@ -719,6 +744,45 @@ export default function FormAudio() { } }, [title, getValues, setValue]); + const handleRewriteClick = async () => { + setIsContentRewriteClicked(true); + + const request = { + style: selectedWritingStyle, + lang: "id", + contextType: "text", + urlContext: null, + context: editorContent, // Ambil isi editor original + createdBy: roleId, + sentiment: "Humorous", + clientId: "7QTW8cMojyayt6qnhqTOeJaBI70W4EaQ", + }; + + const res = await generateDataRewrite(request); + close(); + + if (res?.error) { + console.error(res.message); + return false; + } + + const newArticleId = res?.data?.data?.id; + setIsGeneratedArticle(true); + + setArticleIds((prevIds: string[]) => { + if (prevIds.length < 3) { + return [...prevIds, newArticleId]; + } else { + const updatedIds = [...prevIds]; + updatedIds[2] = newArticleId; + return updatedIds; + } + }); + + Cookies.set("nulisAIArticleIdTemp", JSON.stringify(articleIds)); + setShowRewriteEditor(true); + }; + return (
@@ -861,7 +925,7 @@ export default function FormAudio() { placeholder="Enter Main Keyword" /> {/* )} - /> */} + /> */}
@@ -911,7 +975,7 @@ export default function FormAudio() {
- +
{isGeneratedArticle && ( -
+
{articleIds.map((id: string, index: number) => (

{selectedArticleId && ( - { + const url = `/${locale}/contributor/content/image/update-seo/${selectedArticleId}`; + window.open(url, "_blank", "noopener,noreferrer"); + }} > - - + {t("update")} + )}
+
+ + + isLoadingData ? ( +
+

+ Loading Proses Data... +

+
+ ) : ( + { + onChange(value); + setEditorContent(value); + }} + initialData={articleBody || value} + /> + ) + } + /> + {errors.description?.message && ( +

+ {errors.description.message} +

+ )} +
)} -
- - - isLoadingData ? ( -
-

Loading Proses Data...

-
- ) : ( - + setSelectedFileType(value)} + value={selectedFileType} + className=" grid-cols-1" + > +
+ + +
+
+ + ( + { + onChange(value); + setEditorContent(value); + }} + initialData={value} + /> + )} /> - ) - } - /> - {errors.description?.message && ( -

- {errors.description.message} -

- )} -
+ {errors.description?.message && ( +

+ {errors.description.message} +

+ )} +
+ +

Content Rewrite

+
+ +
+ + {showRewriteEditor && ( +
+ {isGeneratedArticle && ( +
+ {articleIds.map((id: string, index: number) => ( + + ))} +
+ )} +
+ + +
+
+ + + isLoadingData ? ( +
+

+ Loading Proses Data... +

+
+ ) : ( + { + onChange(value); + setRewriteEditorContent(value); + }} + initialData={articleBody || value} + /> + ) + } + /> +
+
+ )} + + + )}
{/* ([]); const [selectedCategory, setSelectedCategory] = useState(); @@ -116,7 +118,10 @@ export default function FormImage() { null ); const [selectedMainKeyword, setSelectedMainKeyword] = useState(""); - const [selectedWritingStyle, setSelectedWritingStyle] = useState(""); + const [selectedWritingStyle, setSelectedWritingStyle] = + useState("professional"); + const [editorContent, setEditorContent] = useState(""); // Untuk original editor + const [rewriteEditorContent, setRewriteEditorContent] = useState(""); const [selectedSize, setSelectedSize] = useState(""); const [detailData, setDetailData] = useState(null); const [articleImages, setArticleImages] = useState([]); @@ -125,6 +130,8 @@ export default function FormImage() { const [content, setContent] = useState(""); + const [isContentRewriteClicked, setIsContentRewriteClicked] = useState(false); + const [selectedTarget, setSelectedTarget] = useState(""); const [unitSelection, setUnitSelection] = useState({ allUnit: false, @@ -140,6 +147,7 @@ export default function FormImage() { let uploadPersen = 0; const [isStartUpload, setIsStartUpload] = useState(false); const [counterProgress, setCounterProgress] = useState(0); + const [showRewriteEditor, setShowRewriteEditor] = useState(false); const [files, setFiles] = useState([]); const [filesTemp, setFilesTemp] = useState([]); @@ -164,16 +172,10 @@ export default function FormImage() { const imageSchema = z.object({ title: z.string().min(1, { message: "Judul diperlukan" }), - description: z - .string() - .min(2, { message: "Narasi Penugasan harus lebih dari 2 karakter." }) - .or( - z.literal(articleBody || "").refine((val) => val.length > 0, { - message: "Deskripsi diperlukan.", - }) - ), + description: z.string().optional(), + descriptionOri: z.string().optional(), + rewriteDescription: z.string().optional(), creatorName: z.string().min(1, { message: "Creator diperlukan" }), - // tags: z.string().min(1, { message: "Judul diperlukan" }), }); const { @@ -184,6 +186,11 @@ export default function FormImage() { formState: { errors }, } = useForm({ resolver: zodResolver(imageSchema), + defaultValues: { + description: "", + descriptionOri: "", + rewriteDescription: "", + }, }); const doGenerateMainKeyword = async () => { @@ -446,13 +453,25 @@ export default function FormImage() { } }; + useEffect(() => { + if (articleBody) { + setValue("description", articleBody); + setValue("rewriteDescription", articleBody); + } + }, [articleBody, setValue]); + const save = async (data: ImageSchema) => { loading(); const finalTags = tags.join(", "); const finalTitle = isSwitchOn ? title : data.title; - const finalDescription = articleBody || data.description; + // const finalDescription = articleBody || data.description; + const finalDescription = isSwitchOn + ? data.description + : selectedFileType === "rewrite" + ? data.rewriteDescription + : data.descriptionOri; - if (!finalDescription.trim()) { + if (!finalDescription?.trim()) { MySwal.fire("Error", "Deskripsi tidak boleh kosong.", "error"); return; } @@ -716,6 +735,45 @@ export default function FormImage() { } }, [title, getValues, setValue]); + const handleRewriteClick = async () => { + setIsContentRewriteClicked(true); + + const request = { + style: selectedWritingStyle, + lang: "id", + contextType: "text", + urlContext: null, + context: editorContent, // Ambil isi editor original + createdBy: roleId, + sentiment: "Humorous", + clientId: "7QTW8cMojyayt6qnhqTOeJaBI70W4EaQ", + }; + + const res = await generateDataRewrite(request); + close(); + + if (res?.error) { + console.error(res.message); + return false; + } + + const newArticleId = res?.data?.data?.id; + setIsGeneratedArticle(true); + + setArticleIds((prevIds: string[]) => { + if (prevIds.length < 3) { + return [...prevIds, newArticleId]; + } else { + const updatedIds = [...prevIds]; + updatedIds[2] = newArticleId; + return updatedIds; + } + }); + + Cookies.set("nulisAIArticleIdTemp", JSON.stringify(articleIds)); + setShowRewriteEditor(true); + }; + return (
@@ -930,6 +988,7 @@ export default function FormImage() { color="primary" onClick={handleGenerateArtikel} size="sm" + type="button" > Generate Article @@ -972,32 +1031,139 @@ export default function FormImage() {
+
+ + + isLoadingData ? ( +
+

+ Loading Proses Data... +

+
+ ) : ( + { + onChange(value); + setEditorContent(value); + }} + initialData={articleBody || value} + /> + ) + } + /> + {errors.description?.message && ( +

+ {errors.description.message} +

+ )} +
)} -
- - - isLoadingData ? ( -
-

Loading Proses Data...

-
- ) : ( - + setSelectedFileType(value)} + value={selectedFileType} + className=" grid-cols-1" + > +
+ + +
+
+ + ( + { + onChange(value); + setEditorContent(value); + }} + initialData={value} + /> + )} /> - ) - } - /> - {errors.description?.message && ( -

- {errors.description.message} -

- )} -
+ {errors.description?.message && ( +

+ {errors.description.message} +

+ )} +
+ +

Content Rewrite

+
+ +
+ + {showRewriteEditor && ( +
+ {isGeneratedArticle && ( +
+ {articleIds.map((id: string, index: number) => ( + + ))} +
+ )} +
+ + +
+
+ + + isLoadingData ? ( +
+

+ Loading Proses Data... +

+
+ ) : ( + { + onChange(value); + setRewriteEditorContent(value); + }} + initialData={articleBody || value} + /> + ) + } + /> +
+
+ )} + + + )}
{/* ; + type ImageSchema = z.infer; const [selectedFiles, setSelectedFiles] = useState([]); const taskId = Cookies.get("taskId"); @@ -165,24 +165,10 @@ export default function FormConvertSPIT() { const imageSchema = z.object({ contentTitle: z.string().min(1, { message: "Judul diperlukan" }), - contentDescription: z - .string() - .min(2, { message: "Narasi Penugasan harus lebih dari 2 karakter." }), - contentCreator: z.string().min(1, { message: "Creator diperlukan" }), + contentDescription: z.string().optional(), contentRewriteDescription: z.string().optional(), + contentCreator: z.string().min(1, { message: "Creator diperlukan" }), }); - // .refine( - // (data) => { - // if (isContentRewriteClicked) { - // return detail?.contentRewriteDescription?.trim().length > 0; - // } - // return true; - // }, - // { - // path: ["contentRewriteDescription"], - // message: "File hasil rewrite wajib diisi", - // } - // ); const options: Option[] = [ { id: "all", label: "SEMUA" }, @@ -194,33 +180,39 @@ export default function FormConvertSPIT() { let fileTypeId = "1"; - // const { - // control, - // handleSubmit, - // setValue, - // formState: { errors }, - // } = useForm({ - // resolver: zodResolver(imageSchema), - // defaultValues: { - // contentTitle: detail?.contentTitle || "", - // contentDescription: detail?.contentDescription || "", - // contentCreator: detail?.contentCreator || "", - // contentRewriteDescription: detail?.contentRewriteDescription || "", - // // dll - // }, - // }); - - const form = useForm>({ + const { + control, + handleSubmit, + setValue, + formState: { errors }, + } = useForm({ resolver: zodResolver(imageSchema), defaultValues: { contentTitle: detail?.contentTitle || "", contentDescription: detail?.contentDescription || "", contentCreator: detail?.contentCreator || "", - + contentRewriteDescription: detail?.contentRewriteDescription || "", // dll }, }); + // const form = useForm>({ + // resolver: zodResolver(imageSchema), + // defaultValues: { + // contentTitle: detail?.contentTitle || "", + // contentDescription: detail?.contentDescription || "", + // contentCreator: detail?.contentCreator || "", + + // // dll + // }, + // }); + + useEffect(() => { + if (articleBody) { + setValue("contentRewriteDescription", articleBody); + } + }, [articleBody, setValue]); + const handleRemoveTag = (index: any) => { setTags((prevTags) => prevTags.filter((_, i) => i !== index)); }; @@ -237,10 +229,10 @@ export default function FormConvertSPIT() { setSelectedFiles((prevImages) => prevImages.filter((_, i) => i !== index)); }; - const handleDirectSave = () => { - const values = form.getValues(); - onSubmit(values); - }; + // const handleDirectSave = () => { + // const values = form.getValues(); + // onSubmit(values); + // }; useEffect(() => { async function initState() { @@ -346,10 +338,10 @@ export default function FormConvertSPIT() { setDetail(details); setFiles(details?.contentList); setupPlacementCheck(details?.contentList?.length); - form.setValue("contentTitle", details?.contentTitle || ""); - form.setValue("contentDescription", details?.contentDescription || ""); - form.setValue("contentCreator", details?.contentCreator || ""); - form.setValue( + setValue("contentTitle", details?.contentTitle || ""); + setValue("contentDescription", details?.contentDescription || ""); + setValue("contentCreator", details?.contentCreator || ""); + setValue( "contentRewriteDescription", details?.contentRewriteDescription || "" ); @@ -471,12 +463,7 @@ export default function FormConvertSPIT() { ); }; - const save = async (data: { - contentTitle: string; - contentDescription: string; - contentRewriteDescription?: string; - contentCreator: string; - }): Promise => { + const save = async (data: ImageSchema) => { const temp = []; for (const element of detail.contentList) { temp.push([]); @@ -514,7 +501,7 @@ export default function FormConvertSPIT() { }); }; - const onSubmit = async (data: z.infer) => { + const onSubmit = (data: ImageSchema) => { MySwal.fire({ title: "Simpan Data", text: "Apakah Anda yakin ingin menyimpan data ini?", @@ -671,480 +658,458 @@ export default function FormConvertSPIT() { return ( <> - - - {detail !== undefined ? ( -
- -
-

{t("form-spit")}

-
- {/* Input Title */} -
- - ( - - )} - /> + + {detail !== undefined ? ( +
+ +
+

{t("form-spit")}

+
+ {/* Input Title */} +
+ + ( + + )} + /> +
+
+
+ +
-
-
- +
+
+ setSelectedFileType(value)} + value={selectedFileType} + className=" grid-cols-1" + > +
+ + +
+
+ + ( + + )} + /> +
+

Content Rewrite

+
+
-
-
- setSelectedFileType(value)} - value={selectedFileType} - className=" grid-cols-1" - > -
- - -
-
- - ( - // - - )} - /> -
-

Content Rewrite

-
- - -
-
- -
- {showRewriteEditor && ( -
- {isGeneratedArticle && ( -
- {articleIds.map((id: string, index: number) => ( - - ))} -
- )} -
- - -
-
- - - isLoadingData ? ( -
-

- Loading Proses Data... -

-
- ) : ( - - ) - } - /> +
+ +
+ {showRewriteEditor && ( +
+ {isGeneratedArticle && ( +
+ {articleIds.map((id: string, index: number) => ( + + ))}
+ )} +
+ +
- )} - -
-
- -
+
+ + + isLoadingData ? ( +
+

+ Loading Proses Data... +

+
+ ) : ( + + ) + } + /> +
+
+ )} + +
+
+ +
+ + {detailThumb?.map((data: any) => ( + + {` + + ))} + +
{detailThumb?.map((data: any) => ( {` ))} -
- - {detailThumb?.map((data: any) => ( - - {` - - ))} - -
-
- -
- {files?.length > 1 && ( -
-
- - handleSelectAll("all", Boolean(e)) - } - /> - -
-
- - handleSelectAll("mabes", Boolean(e)) - } - /> - -
-
- - handleSelectAll("polda", Boolean(e)) - } - /> - -
-
- - handleSelectAll("international", Boolean(e)) - } - /> - -
-
- )} - {files?.map((file, index) => ( -
- +
+ +
+ {files?.length > 1 && ( +
+
+ + handleSelectAll("all", Boolean(e)) + } /> -
-
- {file.fileName} + +
+
+ + handleSelectAll("mabes", Boolean(e)) + } + /> + +
+
+ + handleSelectAll("polda", Boolean(e)) + } + /> + +
+
+ + handleSelectAll("international", Boolean(e)) + } + /> + +
+
+ )} + {files?.map((file, index) => ( +
+ +
+
+ {file.fileName} +
+
+
+ + setupPlacement(index, "all", Boolean(e)) + } + /> + +
+
+ + setupPlacement(index, "mabes", Boolean(e)) + } + /> + +
+
+ + setupPlacement(index, "polda", Boolean(e)) + } + /> +
-
-
- - setupPlacement(index, "all", Boolean(e)) - } - /> - -
-
- - setupPlacement(index, "mabes", Boolean(e)) - } - /> - -
-
- - setupPlacement(index, "polda", Boolean(e)) - } - /> - -
-
- - setupPlacement( - index, - "international", - Boolean(e) - ) - } - /> - -
+
+ + setupPlacement( + index, + "international", + Boolean(e) + ) + } + /> +
+
+ ))} +
+
+ +
+ +
+
+ + ( + + )} + /> +
+
+
+ + + Thumbnail Gambar Utama + +
+
+
+ + +
+ {tags.map((tag, index) => ( + + {tag} + + ))} +
+
+
+
+
+ + {options.map((option) => ( +
+ opt.id !== "all") + .length + : publishedFor.includes(option.id) + } + onCheckedChange={() => + handleCheckboxChange(option.id) + } + /> + +
))}
-
- -
-
- - ( - - )} - /> -
-
-
- - - Thumbnail Gambar Utama - -
-
-
- - -
- {tags.map((tag, index) => ( - - {tag} - - ))} -
-
-
-
-
- - {options.map((option) => ( -
- opt.id !== "all") - .length - : publishedFor.includes(option.id) - } - onCheckedChange={() => - handleCheckboxChange(option.id) - } - /> - -
- ))} -
-
-
-
-
- -
-
- -
+
+
+ +
+
+
- ) : ( - "" - )} - - +
+ ) : ( + "" + )} + ); } diff --git a/components/form/content/teks-form.tsx b/components/form/content/teks-form.tsx index c9a9ce4e..7353d0bf 100644 --- a/components/form/content/teks-form.tsx +++ b/components/form/content/teks-form.tsx @@ -16,7 +16,7 @@ import * as z from "zod"; import { Upload } from "tus-js-client"; import Swal from "sweetalert2"; import withReactContent from "sweetalert2-react-content"; -import { redirect, useRouter } from "next/navigation"; +import { redirect, useParams, useRouter } from "next/navigation"; import { Select, SelectContent, @@ -40,6 +40,7 @@ import { uploadThumbnailBlog } from "@/service/blog/blog"; import { Textarea } from "@/components/ui/textarea"; import { generateDataArticle, + generateDataRewrite, getDetailArticle, getGenerateKeywords, getGenerateTitle, @@ -83,11 +84,15 @@ export default function FormTeks() { const editor = useRef(null); type TeksSchema = z.infer; + const params = useParams(); + const locale = params?.locale; + const [selectedFiles, setSelectedFiles] = useState([]); const taskId = Cookies.get("taskId"); const scheduleId = Cookies.get("scheduleId"); const scheduleType = Cookies.get("scheduleType"); const roleId = getCookiesDecrypt("urie"); + const [selectedFileType, setSelectedFileType] = useState("original"); const [categories, setCategories] = useState([]); const [selectedCategory, setSelectedCategory] = useState(); @@ -102,6 +107,10 @@ export default function FormTeks() { const [editingArticleId, setEditingArticleId] = useState(null); const [isLoading, setIsLoading] = useState(false); const [isLoadingData, setIsLoadingData] = useState(false); + const [selectedWritingStyle, setSelectedWritingStyle] = + useState("professional"); + const [editorContent, setEditorContent] = useState(""); // Untuk original editor + const [rewriteEditorContent, setRewriteEditorContent] = useState(""); const [articleIds, setArticleIds] = useState([]); const [isGeneratedArticle, setIsGeneratedArticle] = useState(false); @@ -109,8 +118,9 @@ export default function FormTeks() { const [selectedArticleId, setSelectedArticleId] = useState( null ); + const [isContentRewriteClicked, setIsContentRewriteClicked] = useState(false); + const [showRewriteEditor, setShowRewriteEditor] = useState(false); const [selectedMainKeyword, setSelectedMainKeyword] = useState(""); - const [selectedWritingStyle, setSelectedWritingStyle] = useState(""); const [selectedSize, setSelectedSize] = useState(""); const [detailData, setDetailData] = useState(null); const [articleImages, setArticleImages] = useState([]); @@ -157,14 +167,9 @@ export default function FormTeks() { const teksSchema = z.object({ title: z.string().min(1, { message: "Judul diperlukan" }), - description: z - .string() - .min(2, { message: "Narasi Penugasan harus lebih dari 2 karakter." }) - .or( - z.literal(articleBody || "").refine((val) => val.length > 0, { - message: "Deskripsi diperlukan.", - }) - ), + description: z.string().optional(), + descriptionOri: z.string().optional(), // Original editor + rewriteDescription: z.string().optional(), creatorName: z.string().min(1, { message: "Creator diperlukan" }), // tags: z.string().min(1, { message: "Judul diperlukan" }), }); @@ -177,6 +182,11 @@ export default function FormTeks() { formState: { errors }, } = useForm({ resolver: zodResolver(teksSchema), + defaultValues: { + description: "", + descriptionOri: "", + rewriteDescription: "", + }, }); const doGenerateMainKeyword = async () => { @@ -439,12 +449,26 @@ export default function FormTeks() { } }; + useEffect(() => { + if (articleBody) { + // Set ke dua field jika rewrite juga aktif + setValue("description", articleBody); + setValue("rewriteDescription", articleBody); + } + }, [articleBody, setValue]); + const save = async (data: TeksSchema) => { loading(); const finalTags = tags.join(", "); const finalTitle = isSwitchOn ? title : data.title; - const finalDescription = articleBody || data.description; - if (!finalDescription.trim()) { + + const finalDescription = isSwitchOn + ? data.description + : selectedFileType === "rewrite" + ? data.rewriteDescription + : data.descriptionOri; + + if (!finalDescription?.trim()) { MySwal.fire("Error", "Deskripsi tidak boleh kosong.", "error"); return; } @@ -709,6 +733,45 @@ export default function FormTeks() { } }, [title, getValues, setValue]); + const handleRewriteClick = async () => { + setIsContentRewriteClicked(true); + + const request = { + style: selectedWritingStyle, + lang: "id", + contextType: "text", + urlContext: null, + context: editorContent, // Ambil isi editor original + createdBy: roleId, + sentiment: "Humorous", + clientId: "7QTW8cMojyayt6qnhqTOeJaBI70W4EaQ", + }; + + const res = await generateDataRewrite(request); + close(); + + if (res?.error) { + console.error(res.message); + return false; + } + + const newArticleId = res?.data?.data?.id; + setIsGeneratedArticle(true); + + setArticleIds((prevIds: string[]) => { + if (prevIds.length < 3) { + return [...prevIds, newArticleId]; + } else { + const updatedIds = [...prevIds]; + updatedIds[2] = newArticleId; + return updatedIds; + } + }); + + Cookies.set("nulisAIArticleIdTemp", JSON.stringify(articleIds)); + setShowRewriteEditor(true); + }; + return (
@@ -851,7 +914,7 @@ export default function FormTeks() { placeholder="Enter Main Keyword" /> {/* )} - /> */} + /> */}
@@ -901,7 +964,7 @@ export default function FormTeks() {
- +
Generate Article
{isGeneratedArticle && ( -
+
{articleIds.map((id: string, index: number) => (

{selectedArticleId && ( - { + const url = `/${locale}/contributor/content/image/update-seo/${selectedArticleId}`; + window.open(url, "_blank", "noopener,noreferrer"); + }} > - - + {t("update")} + )}
+
+ + + isLoadingData ? ( +
+

+ Loading Proses Data... +

+
+ ) : ( + { + onChange(value); + setEditorContent(value); + }} + initialData={articleBody || value} + /> + ) + } + /> + {errors.description?.message && ( +

+ {errors.description.message} +

+ )} +
)} -
- - - isLoadingData ? ( -
-

Loading Proses Data...

-
- ) : ( - + setSelectedFileType(value)} + value={selectedFileType} + className=" grid-cols-1" + > +
+ + +
+
+ + ( + { + onChange(value); + setEditorContent(value); + }} + initialData={value} + /> + )} /> - ) - } - /> - {errors.description?.message && ( -

- {errors.description.message} -

- )} -
+ {errors.description?.message && ( +

+ {errors.description.message} +

+ )} +
+ +

Content Rewrite

+
+ +
+ + {showRewriteEditor && ( +
+ {isGeneratedArticle && ( +
+ {articleIds.map((id: string, index: number) => ( + + ))} +
+ )} +
+ + +
+
+ + + isLoadingData ? ( +
+

+ Loading Proses Data... +

+
+ ) : ( + { + onChange(value); + setRewriteEditorContent(value); + }} + initialData={articleBody || value} + /> + ) + } + /> +
+
+ )} + + + )}
{/* ; + const params = useParams(); + const locale = params?.locale; const [selectedFiles, setSelectedFiles] = useState([]); const taskId = Cookies.get("taskId"); const scheduleId = Cookies.get("scheduleId"); const scheduleType = Cookies.get("scheduleType"); const roleId = getCookiesDecrypt("urie"); + const [selectedFileType, setSelectedFileType] = useState("original"); const t = useTranslations("Form"); const [categories, setCategories] = useState([]); @@ -97,6 +101,11 @@ export default function FormVideo() { const [preview, setPreview] = useState(null); const [selectedLanguage, setSelectedLanguage] = useState(""); + const [selectedWritingStyle, setSelectedWritingStyle] = + useState("professional"); + const [editorContent, setEditorContent] = useState(""); // Untuk original editor + const [rewriteEditorContent, setRewriteEditorContent] = useState(""); + const [selectedSEO, setSelectedSEO] = useState(""); const [title, setTitle] = useState(""); const [selectedAdvConfig, setSelectedAdvConfig] = useState(""); @@ -111,13 +120,17 @@ export default function FormVideo() { null ); const [selectedMainKeyword, setSelectedMainKeyword] = useState(""); - const [selectedWritingStyle, setSelectedWritingStyle] = useState(""); + // const [selectedWritingStyle, setSelectedWritingStyle] = useState(""); const [selectedSize, setSelectedSize] = useState(""); const [detailData, setDetailData] = useState(null); const [articleImages, setArticleImages] = useState([]); const [isSwitchOn, setIsSwitchOn] = useState(false); const inputRef = useRef(null); + const [showRewriteEditor, setShowRewriteEditor] = useState(false); + + const [isContentRewriteClicked, setIsContentRewriteClicked] = useState(false); + const [selectedTarget, setSelectedTarget] = useState(""); const [unitSelection, setUnitSelection] = useState({ allUnit: false, @@ -155,14 +168,9 @@ export default function FormVideo() { const videoSchema = z.object({ title: z.string().min(1, { message: "Judul diperlukan" }), - description: z - .string() - .min(2, { message: "Narasi Penugasan harus lebih dari 2 karakter." }) - .or( - z.literal(articleBody || "").refine((val) => val.length > 0, { - message: "Deskripsi diperlukan.", - }) - ), + description: z.string().optional(), + descriptionOri: z.string().optional(), // Original editor + rewriteDescription: z.string().optional(), creatorName: z.string().min(1, { message: "Creator diperlukan" }), // tags: z.string().min(1, { message: "Judul diperlukan" }), }); @@ -175,6 +183,11 @@ export default function FormVideo() { formState: { errors }, } = useForm({ resolver: zodResolver(videoSchema), + defaultValues: { + description: "", + descriptionOri: "", + rewriteDescription: "", + }, }); const doGenerateMainKeyword = async () => { @@ -437,15 +450,30 @@ export default function FormVideo() { } }; + useEffect(() => { + if (articleBody) { + // Set ke dua field jika rewrite juga aktif + setValue("description", articleBody); + setValue("rewriteDescription", articleBody); + } + }, [articleBody, setValue]); + const save = async (data: VideoSchema) => { loading(); const finalTags = tags.join(", "); const finalTitle = isSwitchOn ? title : data.title; - const finalDescription = articleBody || data.description; - if (!finalDescription.trim()) { + // const finalDescription = articleBody || data.description; + const finalDescription = isSwitchOn + ? data.description + : selectedFileType === "rewrite" + ? data.rewriteDescription + : data.descriptionOri; + + if (!finalDescription?.trim()) { MySwal.fire("Error", "Deskripsi tidak boleh kosong.", "error"); return; } + let requestData: { title: string; description: string; @@ -726,6 +754,45 @@ export default function FormVideo() { } }, [title, getValues, setValue]); + const handleRewriteClick = async () => { + setIsContentRewriteClicked(true); + + const request = { + style: selectedWritingStyle, + lang: "id", + contextType: "text", + urlContext: null, + context: editorContent, // Ambil isi editor original + createdBy: roleId, + sentiment: "Humorous", + clientId: "7QTW8cMojyayt6qnhqTOeJaBI70W4EaQ", + }; + + const res = await generateDataRewrite(request); + close(); + + if (res?.error) { + console.error(res.message); + return false; + } + + const newArticleId = res?.data?.data?.id; + setIsGeneratedArticle(true); + + setArticleIds((prevIds: string[]) => { + if (prevIds.length < 3) { + return [...prevIds, newArticleId]; + } else { + const updatedIds = [...prevIds]; + updatedIds[2] = newArticleId; + return updatedIds; + } + }); + + Cookies.set("nulisAIArticleIdTemp", JSON.stringify(articleIds)); + setShowRewriteEditor(true); + }; + return (
@@ -867,7 +934,7 @@ export default function FormVideo() { placeholder="Enter Main Keyword" /> {/* )} - /> */} + /> */}
@@ -917,7 +984,7 @@ export default function FormVideo() {
- +
Generate Article
{isGeneratedArticle && ( -
+
{articleIds.map((id: string, index: number) => (

{selectedArticleId && ( - { + const url = `/${locale}/contributor/content/image/update-seo/${selectedArticleId}`; + window.open(url, "_blank", "noopener,noreferrer"); + }} > - - + {t("update")} + )}
+
+ + + isLoadingData ? ( +
+

+ Loading Proses Data... +

+
+ ) : ( + { + onChange(value); + setEditorContent(value); + }} + initialData={articleBody || value} + /> + ) + } + /> + {errors.description?.message && ( +

+ {errors.description.message} +

+ )} +
)} -
- - - isLoadingData ? ( -
-

Loading Proses Data...

-
- ) : ( - + setSelectedFileType(value)} + value={selectedFileType} + className=" grid-cols-1" + > +
+ + +
+
+ + ( + { + onChange(value); + setEditorContent(value); + }} + initialData={value} + /> + )} /> - ) - } - /> - {errors.description?.message && ( -

- {errors.description.message} -

- )} -
+ {errors.description?.message && ( +

+ {errors.description.message} +

+ )} +
+ +

Content Rewrite

+
+ +
+ + {showRewriteEditor && ( +
+ {isGeneratedArticle && ( +
+ {articleIds.map((id: string, index: number) => ( + + ))} +
+ )} +
+ + +
+
+ + + isLoadingData ? ( +
+

+ Loading Proses Data... +

+
+ ) : ( + { + onChange(value); + setRewriteEditorContent(value); + }} + initialData={articleBody || value} + /> + ) + } + /> +
+
+ )} + + + )}
{/* Date: Wed, 18 Jun 2025 19:12:37 +0800 Subject: [PATCH 3/3] category spit --- components/form/content/spit-convert-form.tsx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/components/form/content/spit-convert-form.tsx b/components/form/content/spit-convert-form.tsx index cddea0be..ecd0a7bb 100644 --- a/components/form/content/spit-convert-form.tsx +++ b/components/form/content/spit-convert-form.tsx @@ -266,7 +266,7 @@ export default function FormConvertSPIT() { const getCategories = async () => { try { - const category = await listCategory(fileTypeId); + const category = await listEnableCategory(fileTypeId); const resCategory: Category[] = category?.data?.data?.content; setCategories(resCategory);