From 9d4e18c269c0b3f23e6f4fb2ebdb27fbe2850554 Mon Sep 17 00:00:00 2001 From: "Builder.io" Date: Tue, 30 Sep 2025 22:06:29 +0000 Subject: [PATCH] Add ProfilesDirectory page cgen-3ecafeccebb7431fafb6040a16a00e5a --- client/pages/ProfilesDirectory.tsx | 247 +++++++++++++++++++++++++++++ 1 file changed, 247 insertions(+) create mode 100644 client/pages/ProfilesDirectory.tsx diff --git a/client/pages/ProfilesDirectory.tsx b/client/pages/ProfilesDirectory.tsx new file mode 100644 index 00000000..16d04019 --- /dev/null +++ b/client/pages/ProfilesDirectory.tsx @@ -0,0 +1,247 @@ +import { useEffect, useMemo, useState } from "react"; +import { Link } from "react-router-dom"; +import Layout from "@/components/Layout"; +import { + Card, + CardContent, + CardDescription, + CardHeader, + CardTitle, +} from "@/components/ui/card"; +import { Input } from "@/components/ui/input"; +import { + Select, + SelectContent, + SelectItem, + SelectTrigger, + SelectValue, +} from "@/components/ui/select"; +import { Badge } from "@/components/ui/badge"; +import { Button } from "@/components/ui/button"; +import LoadingScreen from "@/components/LoadingScreen"; +import { + aethexUserService, + type AethexUserProfile, +} from "@/lib/aethex-database-adapter"; +import { cn } from "@/lib/utils"; +import { + Search, + RefreshCw, + UserRound, + Users, + Sparkles, +} from "lucide-react"; + +const realmFilters: Array<{ value: string; label: string }> = [ + { value: "all", label: "All Realms" }, + { value: "game_developer", label: "Development Forge" }, + { value: "client", label: "Strategist Nexus" }, + { value: "community_member", label: "Innovation Commons" }, + { value: "customer", label: "Experience Hub" }, +]; + +const realmBadgeStyles: Record = { + game_developer: "bg-gradient-to-r from-neon-purple to-aethex-500 text-white", + client: "bg-gradient-to-r from-neon-blue to-aethex-400 text-white", + community_member: "bg-gradient-to-r from-neon-green to-aethex-600 text-white", + customer: "bg-gradient-to-r from-amber-400 to-aethex-700 text-white", +}; + +interface ProfileCardProps { + profile: AethexUserProfile & { email?: string | null }; +} + +const ProfileCard = ({ profile }: ProfileCardProps) => { + const realmStyle = realmBadgeStyles[profile.user_type] || "bg-aethex-500 text-white"; + return ( + + +
+ + {profile.user_type.replace("_", " ")} + + + Level {profile.level ?? 1} + +
+ + {profile.full_name || profile.username || "AeThex Explorer"} + + {profile.email && ( + + {profile.email} + + )} +
+ +
+
+
+ XP +
+
{profile.total_xp ?? 0}
+
+
+
+ Loyalty +
+
+ {(profile as any)?.loyalty_points ?? 0} +
+
+
+
+ {(profile as any)?.skills?.slice(0, 3)?.map((skill: string) => ( + + {skill} + + ))} + {((profile as any)?.skills?.length || 0) > 3 && ( + + +{((profile as any)?.skills?.length || 0) - 3} + + )} +
+ +
+
+ ); +}; + +const ProfilesDirectory = () => { + const [profiles, setProfiles] = useState([]); + const [loading, setLoading] = useState(true); + const [search, setSearch] = useState(""); + const [realmFilter, setRealmFilter] = useState("all"); + + const filteredProfiles = useMemo(() => { + const lowerSearch = search.trim().toLowerCase(); + return profiles.filter((profile) => { + const matchesRealm = + realmFilter === "all" || profile.user_type === realmFilter; + const matchesSearch = lowerSearch + ? [ + profile.full_name, + profile.username, + (profile as any)?.company, + ] + .filter(Boolean) + .some((value) => + String(value).toLowerCase().includes(lowerSearch), + ) + : true; + return matchesRealm && matchesSearch; + }); + }, [profiles, search, realmFilter]); + + const refreshProfiles = async () => { + try { + setLoading(true); + const list = await aethexUserService.listProfiles(60); + setProfiles(list); + } catch (error) { + console.error("Failed to load profiles", error); + setProfiles([]); + } finally { + setLoading(false); + } + }; + + useEffect(() => { + refreshProfiles(); + }, []); + + if (loading) { + return ; + } + + return ( + +
+
+
+ + AeThex Passport Network + +
+
+

+ Discover AeThex talent +

+

+ Browse verified creators, clients, and community members across every AeThex realm. +

+
+
+ + +
+
+
+ +
+
+ + setSearch(event.target.value)} + placeholder="Search by name, username, or company" + className="border-0 bg-transparent text-slate-100 focus-visible:ring-0" + /> +
+ +
+ + {filteredProfiles.length === 0 ? ( + + +
+ No passports found +
+

+ Try adjusting your search or realm filters. New members join AeThex every day! +

+
+ ) : ( +
+ {filteredProfiles.map((profile) => ( + + ))} +
+ )} +
+
+
+ ); +}; + +export default ProfilesDirectory;