import { useEffect, useState, useMemo } from 'react'; import { useToast } from '../../hooks/use-toast'; import { getUrlParams } from '../../lib/browser'; import { httpGet } from '../../lib/http'; import type { ResourceType } from '../../lib/resource-progress'; import type { AllowedActivityActionType } from '../Activity/ActivityStream'; import { pageProgressMessage } from '../../stores/page'; import { TeamActivityItem } from './TeamActivityItem'; import { TeamActivityTopicsModal } from './TeamActivityTopicsModal'; import { TeamEmptyStream } from './TeamEmptyStream'; import { Pagination } from '../Pagination/Pagination'; import { ChartNoAxesGantt, CircleDashed, Flag, LoaderCircle, } from 'lucide-react'; export type TeamStreamActivity = { _id?: string; resourceType: ResourceType | 'question'; resourceId: string; resourceTitle: string; resourceSlug?: string; isCustomResource?: boolean; actionType: AllowedActivityActionType; topicTitles?: string[]; createdAt: Date; updatedAt: Date; }; export interface TeamActivityStreamDocument { _id?: string; teamId: string; userId: string; activity: TeamStreamActivity[]; createdAt: Date; updatedAt: Date; } type GetTeamActivityResponse = { data: { users: { _id: string; name: string; avatar?: string; username?: string; memberId?: string; }[]; activities: TeamActivityStreamDocument[]; }; totalCount: number; totalPages: number; currPage: number; perPage: number; }; type TeamActivityPageProps = { teamId?: string; canManageCurrentTeam?: boolean; }; export function TeamActivityPage(props: TeamActivityPageProps) { const { teamId: defaultTeamId, canManageCurrentTeam = false } = props; const { t: teamId = defaultTeamId } = getUrlParams(); const toast = useToast(); const [isLoading, setIsLoading] = useState(true); const [selectedActivity, setSelectedActivity] = useState(null); const [teamActivities, setTeamActivities] = useState( { data: { users: [], activities: [], }, totalCount: 0, totalPages: 0, currPage: 1, perPage: 21, }, ); const [currPage, setCurrPage] = useState(1); const getTeamProgress = async (currPage: number = 1) => { const { response, error } = await httpGet( `${import.meta.env.PUBLIC_API_URL}/v1-get-team-activity/${teamId}`, { currPage, }, ); if (error || !response) { toast.error(error?.message || 'Failed to get team activity'); return; } setTeamActivities(response); setCurrPage(response.currPage); }; useEffect(() => { if (!teamId) { return; } setIsLoading(true); setTeamActivities({ data: { users: [], activities: [], }, totalCount: 0, totalPages: 0, currPage: 1, perPage: 21, }); setCurrPage(1); getTeamProgress().then(() => { pageProgressMessage.set(''); setIsLoading(false); }); }, [teamId]); const { users, activities } = teamActivities?.data; const validActivities = useMemo(() => { return activities?.filter((activity) => { return ( activity.activity.length > 0 && activity.activity.some((t) => (t?.topicTitles?.length || 0) > 0) ); }); }, [activities]); const sortedUniqueCreatedAt = useMemo(() => { return new Set( validActivities ?.map((activity) => new Date(activity.createdAt).setHours(0, 0, 0, 0)) .sort((a, b) => { return new Date(b).getTime() - new Date(a).getTime(); }), ); }, [validActivities]); const usersWithActivities = useMemo(() => { const enrichedUsers: { _id: string; name: string; avatar?: string; username?: string; activities: TeamStreamActivity[]; }[] = []; for (const uniqueCreatedAt of sortedUniqueCreatedAt) { const uniqueActivities = validActivities.filter( (activity) => new Date(activity.createdAt).setHours(0, 0, 0, 0) === uniqueCreatedAt, ); const usersWithUniqueActivities = users .map((user) => { const userActivities = uniqueActivities .filter((activity) => activity.userId === user._id) .flatMap((activity) => activity.activity) .filter((activity) => (activity?.topicTitles?.length || 0) > 0) .sort((a, b) => { return ( new Date(b.updatedAt).getTime() - new Date(a.updatedAt).getTime() ); }); return { ...user, activities: userActivities, }; }) .filter((user) => user.activities.length > 0) .sort((a, b) => { return ( new Date(b.activities[0].updatedAt).getTime() - new Date(a.activities[0].updatedAt).getTime() ); }); enrichedUsers.push(...usersWithUniqueActivities); } return enrichedUsers; }, [users, activities]); const sectionHeading = (

Team Activity {canManageCurrentTeam && ( Progresses )}

); if (isLoading) { return ( <> {sectionHeading}
{Array.from({ length: 4 }).map((_, index) => (
))}
); } if (!teamId) { if (typeof window !== 'undefined') { window.location.href = '/'; } else { return null; } } return ( <> {selectedActivity && ( setSelectedActivity(null)} /> )} {usersWithActivities.length > 0 ? ( <> {sectionHeading}
    {usersWithActivities.map((user, index) => { return ( ); })}
{ setCurrPage(page); pageProgressMessage.set('Loading...'); getTeamProgress(page).finally(() => { pageProgressMessage.set(''); }); }} /> ) : ( <> {sectionHeading}
)} ); }