dashboard api integration

This commit is contained in:
Meenadeveloper 2026-03-12 18:25:29 +05:30
parent ccf638f7f3
commit cd880e10e5
6 changed files with 71 additions and 34 deletions

View File

@ -58,4 +58,8 @@ PROFILES_FILTER_LIST:"profiles/lists",
PROFILES_FILTER_MASTER:"profiles/filter/masters",
DASHBOARD_API:"dashboard",
HEADER_API:"header_data",
SHORTLIST_API:"shortlist_profile",
};

7
src/api/dashboard.api.js Normal file
View File

@ -0,0 +1,7 @@
import axiosInstance from "./axiosInstance";
import { API_ENDPOINTS } from "./apiEndpoints";
export const getDashboardDetails = async () => {
const res = await axiosInstance.get(API_ENDPOINTS.DASHBOARD_API);
return res.data;
};

View File

@ -9,8 +9,7 @@ import { useNavigate } from "react-router-dom";
import AstroChatUI from "./AstroChatUI";
import MembershipCard from "./MembershipCard";
const ProfileCompletion = () => {
const [completeness, setCompleteness] = useState(30);
const ProfileCompletion = ({ percentage = 0, missingDetails }) => {
const navigate = useNavigate();
const cards = [
@ -95,7 +94,7 @@ const ProfileCompletion = () => {
transition={{ delay: 0.6, type: "spring", stiffness: 200 }}
className="text-lg sm:text-xl font-bold text-gray-900"
>
{completeness}%
{percentage}%
</motion.span>
</div>
@ -103,7 +102,7 @@ const ProfileCompletion = () => {
<div className="relative h-3 bg-gray-200 rounded-full overflow-hidden">
<motion.div
initial={{ width: 0 }}
animate={{ width: `${completeness}%` }}
animate={{ width: `${percentage}%` }}
transition={{ delay: 0.8, duration: 1, ease: "easeOut" }}
className="absolute top-0 left-0 h-full bg-gradient-to-r from-red-500 to-red-600 rounded-full"
/>
@ -123,6 +122,7 @@ const ProfileCompletion = () => {
</Box> */}
<AstroChatUI/>
<div className="my-4 rounded-2xl bg-green-50 border border-1 border-green-200 p-4 ">
<motion.div
variants={container}
@ -130,15 +130,16 @@ const ProfileCompletion = () => {
animate="show"
className="grid grid-cols-1 sm:grid-cols-2 lg:grid-cols-3 gap-4 sm:gap-6"
>
{/* NOTE: The cards are static for now. To make them dynamic,
the `missingDetails` prop should be an array of objects to map over. */}
{cards.map((card, index) => (
<div
key={card.id}
onClick={() => navigate(card.url)}
className=" border border-1 border-red-50 bg-white rounded-3xl hover:bg-red-50 hover:border-2
flex flex-col items-center space-x-2 h-32 justify-center transition-colors duration-500
cursor-pointer ">
cursor-pointer "
>
{/* Icon Container */}
<motion.div
initial={{ rotate: -180, opacity: 0 }}
@ -163,15 +164,12 @@ const ProfileCompletion = () => {
{card.title}
</motion.h3>
</div>
))}
</motion.div>
<MembershipCard />
</div>
</div>
{/* Additional Info Section */}
{/* <motion.div

View File

@ -84,6 +84,7 @@ export default function ProfileCard() {
</h1>
<p className="text-gray-900 text-[12px]">
Find your perfect match today
</p>
</motion.div>

View File

@ -0,0 +1,14 @@
import { useQuery } from "@tanstack/react-query";
import { getDashboardDetails } from "../api/dashboard.api";
export const useDashboardQuery = () => {
return useQuery({
queryKey: ["dashboardDetails"],
queryFn: getDashboardDetails,
// Performance settings:
staleTime: 1000 * 60 * 5, // Data is considered fresh for 5 minutes (reduces API calls)
gcTime: 1000 * 60 * 10, // Unused data is garbage collected after 10 minutes
refetchOnWindowFocus: false, // Prevents refetching when user switches tabs
retry: 1, // Retry failed requests once
});
};

View File

@ -11,6 +11,7 @@ import weddingpromo2 from "../assets/images/weddingpromo2.jpg";
import weddingpromo3 from "../assets/images/weddingpromo3.jpg";
import weddingpromo4 from "../assets/images/weddingpromo4.jpg";
import { useDashboardQuery } from "../hooks/useDashboardQuery";
const ProfileCompletion = lazy(() => import("../components/profiledashboard/ProfileCompletion"));
const MatrimonyArticles = lazy(() => import("../components/profiledashboard/MatrimonyArticles"));
@ -48,6 +49,15 @@ const SectionFallback = ({ height = 280 }) => (
const UserDashboardHome = () => {
const { data, isLoading } = useDashboardQuery();
const dashboardData = data?.data;
const sliderImages = dashboardData?.image_sliders?.length > 0
? dashboardData.image_sliders
: images.map((img, index) => ({ id: index, image: img }));
if (isLoading) return <SectionFallback height={600} />;
return (
<>
<div className="custom-swiper-hero flex items-center justify-center p-4">
@ -92,11 +102,11 @@ const UserDashboardHome = () => {
},
}}
>
{images.map((img, idx) => (
<SwiperSlide key={idx}>
{sliderImages.map((slide, idx) => (
<SwiperSlide key={slide.id || idx}>
<div className="relative overflow-hidden rounded-3xl w-[100%]">
<img
src={img}
src={slide.image}
alt={`Slide ${idx + 1}`}
className="w-full h-full object-cover"
loading={idx === 0 ? "eager" : "lazy"}
@ -206,28 +216,31 @@ const UserDashboardHome = () => {
`}</style>
</div>
<Suspense fallback={<SectionFallback height={320} />}>
<Profilecardemo />
<Profilecardemo profiles={dashboardData?.daily_recommended} />
</Suspense>
{/* <DailyRecommendedCard/> */}
<Suspense fallback={<SectionFallback height={220} />}>
<ProfileCompletion />
<ProfileCompletion
percentage={dashboardData?.profile_complete_percentage}
missingDetails={dashboardData?.non_filled_sections}
/>
</Suspense>
{/* <DailyRecommendedCard/> */}
<Suspense fallback={<SectionFallback height={280} />}>
<MatrimonyArticles />
<MatrimonyArticles articles={dashboardData?.blogs} />
</Suspense>
<Suspense fallback={<SectionFallback height={320} />}>
<MatchingList />
<MatchingList matches={dashboardData?.all_matches} />
</Suspense>
{/* <PaidMemberCard/> */}
{/* <NewJoinedProfile/> */}
{/* <CustomerSupportCard/> */}
<Suspense fallback={<SectionFallback height={240} />}>
<VideoSwiperGallery />
<VideoSwiperGallery videos={dashboardData?.youtube_videos} />
</Suspense>
</>
)