news added and update bug fix

This commit is contained in:
Samandar Turgunboyev
2025-11-18 15:06:04 +05:00
parent 0f650ad15a
commit 11f88d1edf
6 changed files with 71 additions and 35 deletions

View File

@@ -40,7 +40,7 @@ export default function FinancePage({ user }: { user: Role }) {
const [searchParams, setSearchParams] = useSearchParams(); const [searchParams, setSearchParams] = useSearchParams();
const tabParam = searchParams.get("tab") as "bookings" | "agencies" | null; const tabParam = searchParams.get("tab") as "bookings" | "agencies" | null;
const pageParam = Number(searchParams.get("page")) || 1; const pageParam = Number(searchParams.get("page")) || 1;
const filterParam = String(searchParams.get("filter")) || ""; const filterParam = searchParams.get("filter") ?? "";
const pageAgencyParam = Number(searchParams.get("page_agency")) || 1; const pageAgencyParam = Number(searchParams.get("page_agency")) || 1;
const [currentPage, setCurrentPage] = useState(pageParam); const [currentPage, setCurrentPage] = useState(pageParam);
const [currentPageAgency, setCurrentPageAgency] = useState(pageAgencyParam); const [currentPageAgency, setCurrentPageAgency] = useState(pageAgencyParam);
@@ -64,6 +64,12 @@ export default function FinancePage({ user }: { user: Role }) {
} }
}, [tabParam]); }, [tabParam]);
useEffect(() => {
if (filterParam === "null") {
setFilterStatus("");
}
}, [filterParam]);
const { data, isLoading, isError, refetch } = useQuery({ const { data, isLoading, isError, refetch } = useQuery({
queryKey: ["list_order_user", currentPage, filterStatus], queryKey: ["list_order_user", currentPage, filterStatus],
queryFn: () => queryFn: () =>

View File

@@ -37,6 +37,7 @@ export const newsPostForm = z.object({
sections: z sections: z
.array( .array(
z.object({ z.object({
id: z.number().optional(),
image: z.union([z.instanceof(File), z.string()]).optional(), image: z.union([z.instanceof(File), z.string()]).optional(),
text: z.string().optional(), text: z.string().optional(),
text_ru: z.string().optional(), text_ru: z.string().optional(),

View File

@@ -48,6 +48,7 @@ export interface NewsAll {
name_ru: string; name_ru: string;
}[]; }[];
post_images: { post_images: {
id: number;
image: string; image: string;
text: string; text: string;
text_ru: string; text_ru: string;
@@ -109,6 +110,7 @@ export interface NewsDetail {
]; ];
post_images: [ post_images: [
{ {
id: number;
image: string; image: string;
text: string; text: string;
text_ru: string; text_ru: string;

View File

@@ -45,6 +45,7 @@ interface Data {
name_uz: string; name_uz: string;
}>; }>;
post_images: Array<{ post_images: Array<{
id: number;
image: string; image: string;
text: string; text: string;
text_ru: string; text_ru: string;
@@ -65,6 +66,7 @@ const StepTwo = ({
const navigate = useNavigate(); const navigate = useNavigate();
const { stepOneData, resetStepOneData } = useNewsStore(); const { stepOneData, resetStepOneData } = useNewsStore();
const queryClient = useQueryClient(); const queryClient = useQueryClient();
const deletedSections = useRef<number[]>([]);
const form = useForm<NewsPostFormType>({ const form = useForm<NewsPostFormType>({
resolver: zodResolver(newsPostForm), resolver: zodResolver(newsPostForm),
@@ -79,13 +81,6 @@ const StepTwo = ({
useEffect(() => { useEffect(() => {
if (detail && !hasReset.current) { if (detail && !hasReset.current) {
const mappedSections =
detail.post_images?.map((img) => ({
image: img.image,
text: img.text_uz,
text_ru: img.text_ru,
})) ?? [];
const mappedTags = const mappedTags =
detail.post_tags?.map((t) => ({ detail.post_tags?.map((t) => ({
name: t.name_uz, name: t.name_uz,
@@ -99,15 +94,29 @@ const StepTwo = ({
post_tags: post_tags:
mappedTags.length > 0 ? mappedTags : [{ name: "", name_ru: "" }], mappedTags.length > 0 ? mappedTags : [{ name: "", name_ru: "" }],
sections: sections:
mappedSections.length > 0 detail.post_images?.map((img) => ({
? mappedSections id: img.id,
: [{ image: "", text: "", text_ru: "" }], image: img.image,
text: img.text_uz,
text_ru: img.text_ru,
})) ?? [],
}); });
hasReset.current = true; hasReset.current = true;
} }
}, [detail, form]); }, [detail, form]);
const handleRemoveSection = (index: number) => {
const section = form.getValues(`sections.${index}`);
if (section?.id) {
deletedSections.current.push(section.id);
}
// Formdan o'chiramiz
removeSection(index);
};
const { const {
fields: sectionFields, fields: sectionFields,
append: appendSection, append: appendSection,
@@ -172,8 +181,8 @@ const StepTwo = ({
formData.append("title", stepOneData.title); formData.append("title", stepOneData.title);
formData.append("title_ru", stepOneData.title_ru); formData.append("title_ru", stepOneData.title_ru);
formData.append("text", stepOneData.desc); formData.append("text", values.desc);
formData.append("text_ru", stepOneData.desc_ru); formData.append("text_ru", values.desc_ru);
formData.append("is_public", values.is_public === "no" ? "false" : "true"); formData.append("is_public", values.is_public === "no" ? "false" : "true");
formData.append("category", String(stepOneData.category)); formData.append("category", String(stepOneData.category));
@@ -181,27 +190,44 @@ const StepTwo = ({
formData.append("image", stepOneData.banner); formData.append("image", stepOneData.banner);
} }
// Sections
values.sections?.forEach((section, i) => { values.sections?.forEach((section, i) => {
if (section.image instanceof File) if (section.id) {
formData.append(`post_images[${i}]`, section.image); formData.append(`updates[${i}]id`, String(section.id));
if (section.text) formData.append(`post_text[${i}]`, section.text);
if (section.text_ru) if (section.text) formData.append(`updates[${i}]text`, section.text);
formData.append(`post_text_ru[${i}]`, section.text_ru);
if (section.text_ru)
formData.append(`updates[${i}]text_ru`, section.text_ru);
if (section.image instanceof File) {
formData.append(`updates[${i}]image`, section.image);
}
} else {
if (section.image instanceof File)
formData.append(`post_images`, section.image);
if (section.text) formData.append(`post_text`, section.text);
if (section.text_ru) formData.append(`post_text_ru`, section.text_ru);
}
});
deletedSections.current.forEach((id) => {
formData.append(`delete_list`, String(id));
}); });
// Post Tags
values.post_tags.forEach((tag, i) => { values.post_tags.forEach((tag, i) => {
formData.append(`post_tags[${i}]name`, tag.name); formData.append(`post_tags[${i}]name`, tag.name);
formData.append(`post_tags[${i}]name_ru`, tag.name_ru); formData.append(`post_tags[${i}]name_ru`, tag.name_ru);
}); });
if (id) update({ body: formData, id: Number(id) }); if (id) {
else added(formData); update({ body: formData, id: Number(id) });
} else {
added(formData);
}
}; };
console.log(form.formState.errors);
return ( return (
<Form {...form}> <Form {...form}>
<form <form
@@ -276,7 +302,7 @@ const StepTwo = ({
<button <button
type="button" type="button"
onClick={() => removeTag(i)} onClick={() => removeTag(i)}
className="text-red-400 hover:text-red-500 mt-1" className="text-red-400 hover:text-red-500"
> >
<Trash2 className="size-4" /> <Trash2 className="size-4" />
</button> </button>
@@ -305,7 +331,7 @@ const StepTwo = ({
</p> </p>
<button <button
type="button" type="button"
onClick={() => removeSection(index)} onClick={() => handleRemoveSection(index)}
className="text-red-400 hover:text-red-500" className="text-red-400 hover:text-red-500"
> >
<Trash2 className="size-4" /> <Trash2 className="size-4" />

View File

@@ -133,7 +133,6 @@ const StepOne = ({
transport: t.transport.id, transport: t.transport.id,
price: t.price ?? 0, price: t.price ?? 0,
})) ?? []; })) ?? [];
console.log("transport", transports);
setTransportPrices(transports.map((t) => formatPrice(t.price ?? 0))); setTransportPrices(transports.map((t) => formatPrice(t.price ?? 0)));
@@ -241,6 +240,8 @@ const StepOne = ({
onSuccess: (res) => { onSuccess: (res) => {
queryClient.refetchQueries({ queryKey: ["popular_tours"] }); queryClient.refetchQueries({ queryKey: ["popular_tours"] });
queryClient.refetchQueries({ queryKey: ["all_tours"] }); queryClient.refetchQueries({ queryKey: ["all_tours"] });
queryClient.refetchQueries({ queryKey: ["tours_detail"] });
queryClient.refetchQueries({ queryKey: ["hotel_detail"] });
setId(res.data.data.id); setId(res.data.data.id);
setStep(2); setStep(2);
}, },
@@ -257,8 +258,10 @@ const StepOne = ({
return updateTours({ body, id }); return updateTours({ body, id });
}, },
onSuccess: (res) => { onSuccess: (res) => {
queryClient.refetchQueries({ queryKey: ["all_tours"] });
queryClient.refetchQueries({ queryKey: ["popular_tours"] }); queryClient.refetchQueries({ queryKey: ["popular_tours"] });
queryClient.refetchQueries({ queryKey: ["all_tours"] });
queryClient.refetchQueries({ queryKey: ["tours_detail"] });
queryClient.refetchQueries({ queryKey: ["hotel_detail"] });
setId(res.data.data.id); setId(res.data.data.id);
setStep(2); setStep(2);
}, },
@@ -320,7 +323,6 @@ const StepOne = ({
if (value.banner instanceof File) { if (value.banner instanceof File) {
formData.append("image_banner", value.banner); formData.append("image_banner", value.banner);
} }
console.log(value.banner, "value.banner");
// Tarif va transport // Tarif va transport
// value.tarif?.forEach((e, i) => { // value.tarif?.forEach((e, i) => {
@@ -491,8 +493,6 @@ const StepOne = ({
queryFn: () => hotelTransport({ page: 1, page_size: 10 }), queryFn: () => hotelTransport({ page: 1, page_size: 10 }),
}); });
console.log(form.formState.errors);
return ( return (
<Form {...form}> <Form {...form}>
<form onSubmit={form.handleSubmit(onSubmit)} className="space-y-6"> <form onSubmit={form.handleSubmit(onSubmit)} className="space-y-6">

View File

@@ -111,7 +111,6 @@ const StepTwo = ({
? "Full Board" ? "Full Board"
: "all_inclusive"; : "all_inclusive";
// ✅ SetValue faqat backenddan qiymat kelganda chaqiriladi
form.setValue("mealPlan", mealPlan); form.setValue("mealPlan", mealPlan);
form.setValue( form.setValue(
@@ -126,7 +125,7 @@ const StepTwo = ({
...new Set(hotel.hotel_features?.map((f) => String(f.id)) ?? []), ...new Set(hotel.hotel_features?.map((f) => String(f.id)) ?? []),
]); ]);
} }
}, [isEditMode, hotelDetail, form]); }, [isEditMode, hotelDetail, form, data]);
// 🧩 Select ma'lumotlari // 🧩 Select ma'lumotlari
const [allHotelTypes, setAllHotelTypes] = useState<Type[]>([]); const [allHotelTypes, setAllHotelTypes] = useState<Type[]>([]);
@@ -231,9 +230,10 @@ const StepTwo = ({
const { mutate, isPending } = useMutation({ const { mutate, isPending } = useMutation({
mutationFn: (body: FormData) => createHotel({ body }), mutationFn: (body: FormData) => createHotel({ body }),
onSuccess: () => { onSuccess: () => {
queryClient.refetchQueries({ queryKey: ["hotel_detail"] });
queryClient.refetchQueries({ queryKey: ["popular_tours"] }); queryClient.refetchQueries({ queryKey: ["popular_tours"] });
queryClient.refetchQueries({ queryKey: ["all_tours"] }); queryClient.refetchQueries({ queryKey: ["all_tours"] });
queryClient.refetchQueries({ queryKey: ["tours_detail"] });
queryClient.refetchQueries({ queryKey: ["hotel_detail"] });
toast.success(t("Muvaffaqiyatli saqlandi")); toast.success(t("Muvaffaqiyatli saqlandi"));
navigate("/tours"); navigate("/tours");
setStep(1); setStep(1);
@@ -249,9 +249,10 @@ const StepTwo = ({
mutationFn: ({ body, id }: { id: number; body: FormData }) => mutationFn: ({ body, id }: { id: number; body: FormData }) =>
editHotel({ body, id }), editHotel({ body, id }),
onSuccess: () => { onSuccess: () => {
queryClient.refetchQueries({ queryKey: ["hotel_detail"] });
queryClient.refetchQueries({ queryKey: ["popular_tours"] }); queryClient.refetchQueries({ queryKey: ["popular_tours"] });
queryClient.refetchQueries({ queryKey: ["all_tours"] }); queryClient.refetchQueries({ queryKey: ["all_tours"] });
queryClient.refetchQueries({ queryKey: ["tours_detail"] });
queryClient.refetchQueries({ queryKey: ["hotel_detail"] });
toast.success(t("Muvaffaqiyatli saqlandi")); toast.success(t("Muvaffaqiyatli saqlandi"));
navigate("/tours"); navigate("/tours");
setStep(1); setStep(1);