diff --git a/packages/shared/src/components/profile/ProfileTooltip.spec.tsx b/packages/shared/src/components/profile/ProfileTooltip.spec.tsx new file mode 100644 index 0000000000..04bbad963e --- /dev/null +++ b/packages/shared/src/components/profile/ProfileTooltip.spec.tsx @@ -0,0 +1,74 @@ +import React from 'react'; +import { act, render } from '@testing-library/react'; +import type { TooltipProps } from '../tooltips/BaseTooltip'; +import { ProfileTooltip } from './ProfileTooltip'; +import { useLogContext } from '../../contexts/LogContext'; +import { LogEvent } from '../../lib/log'; + +const mockSetQueryData = jest.fn(); +const mockLogEvent = jest.fn(); +const mockSimpleTooltipSpy = jest.fn(); + +jest.mock('@tanstack/react-query', () => ({ + ...jest.requireActual('@tanstack/react-query'), + useQueryClient: () => ({ setQueryData: mockSetQueryData }), + useQuery: () => ({ data: null, isLoading: false }), +})); + +jest.mock('../../contexts/LogContext', () => ({ + useLogContext: jest.fn(), +})); + +jest.mock('../tooltips/SimpleTooltip', () => ({ + SimpleTooltip: ({ children, ...props }: TooltipProps) => { + mockSimpleTooltipSpy(props); + return
{children}
; + }, +})); + +describe('ProfileTooltip', () => { + beforeEach(() => { + jest.clearAllMocks(); + (useLogContext as jest.Mock).mockReturnValue({ logEvent: mockLogEvent }); + }); + + it('should log hover user card event on show', () => { + render( + + + , + ); + + const [props] = mockSimpleTooltipSpy.mock.calls[0] as [TooltipProps]; + const { onShow } = props; + + act(() => { + onShow?.({} as never); + }); + + expect(mockLogEvent).toHaveBeenCalledWith({ + event_name: LogEvent.HoverUserCard, + target_id: 'user-1', + }); + }); + + it('should call custom tooltip onShow callback', () => { + const tooltipOnShow = jest.fn(); + + render( + + + , + ); + + const [props] = mockSimpleTooltipSpy.mock.calls[0] as [TooltipProps]; + const { onShow } = props; + const instance = {} as never; + + act(() => { + onShow?.(instance); + }); + + expect(tooltipOnShow).toHaveBeenCalledWith(instance); + }); +}); diff --git a/packages/shared/src/components/profile/ProfileTooltip.tsx b/packages/shared/src/components/profile/ProfileTooltip.tsx index 80a602352c..fa841f91ee 100644 --- a/packages/shared/src/components/profile/ProfileTooltip.tsx +++ b/packages/shared/src/components/profile/ProfileTooltip.tsx @@ -9,6 +9,8 @@ import { SimpleTooltip } from '../tooltips/SimpleTooltip'; import type { MostReadTag, UserReadingRank } from '../../graphql/users'; import { getUserShortInfo } from '../../graphql/users'; import UserEntityCard from '../cards/entity/UserEntityCard'; +import { useLogContext } from '../../contexts/LogContext'; +import { LogEvent } from '../../lib/log'; import { generateQueryKey, RequestKey } from '../../lib/query'; export interface ProfileTooltipProps extends ProfileTooltipContentProps { @@ -42,6 +44,7 @@ export function ProfileTooltip({ onTooltipMouseLeave, }: Omit): ReactElement { const query = useQueryClient(); + const { logEvent } = useLogContext(); const handler = useRef<() => void>(); const [id, setId] = useState(undefined); const { data, isLoading } = useQuery({ @@ -52,7 +55,7 @@ export function ProfileTooltip({ enabled: !!id, }); - const onShow = () => { + const handleShow = () => { if (!scrollingContainer) { return; } @@ -124,6 +127,10 @@ export function ProfileTooltip({ onTooltipMouseEnter || onTooltipMouseLeave ? [hoverPlugin] : undefined, ...tooltip, onShow: (instance) => { + logEvent({ + event_name: LogEvent.HoverUserCard, + target_id: userId, + }); if (id !== userId) { setId(userId); } @@ -131,7 +138,7 @@ export function ProfileTooltip({ tooltip.onShow(instance); return; } - onShow(); + handleShow(); }, }; diff --git a/packages/shared/src/lib/log.ts b/packages/shared/src/lib/log.ts index e0d0e21b64..c1136d49e9 100644 --- a/packages/shared/src/lib/log.ts +++ b/packages/shared/src/lib/log.ts @@ -297,6 +297,7 @@ export enum LogEvent { ProfileView = 'profile view', UpdateProfile = 'update profile', UpdateProfileImage = 'update profile image', + HoverUserCard = 'hover user card', // End Profile TranslatePost = 'translate post', // Start Credits