diff --git a/packages/constants/src/event-tracker/core.ts b/packages/constants/src/event-tracker/core.ts index 6f499d8b6c0..94bebf4806b 100644 --- a/packages/constants/src/event-tracker/core.ts +++ b/packages/constants/src/event-tracker/core.ts @@ -25,7 +25,6 @@ export const getProjectEventPayload = (payload: any) => ({ element: payload.element, }); - export const getPageEventPayload = (payload: any) => ({ workspace_id: payload.workspace_id, project_id: payload.project, @@ -208,35 +207,46 @@ export const AUTH_TRACKER_EVENTS = { forgot_password: "forgot_password_clicked", }; -export const PRODUCT_TOUR_TRACKER_EVENTS = { - start: "product_tour_started", - complete: "product_tour_completed", - skip: "product_tour_skipped", -}; - -export const GLOBAL_VIEW_TOUR_TRACKER_EVENTS = { +export const GLOBAL_VIEW_TRACKER_EVENTS = { create: "global_view_created", update: "global_view_updated", delete: "global_view_deleted", open: "global_view_opened", }; +export const GLOBAL_VIEW_TRACKER_ELEMENTS = { + RIGHT_HEADER_ADD_BUTTON: "global_view_right_header_add_button", + HEADER_SAVE_VIEW_BUTTON: "global_view_header_save_view_button", + QUICK_ACTIONS: "global_view_quick_actions", + LIST_ITEM: "global_view_list_item", +}; + +export const PRODUCT_TOUR_TRACKER_EVENTS = { + complete: "product_tour_completed", +}; +export const PRODUCT_TOUR_TRACKER_ELEMENTS = { + START_BUTTON: "product_tour_start_button", + SKIP_BUTTON: "product_tour_skip_button", + CREATE_PROJECT_BUTTON: "product_tour_create_project_button", +}; export const NOTIFICATION_TRACKER_EVENTS = { archive: "notification_archived", all_marked_read: "all_notifications_marked_read", }; +export const NOTIFICATION_TRACKER_ELEMENTS = { + MARK_ALL_AS_READ_BUTTON: "mark_all_as_read_button", + ARCHIVE_BUTTON: "archive_button", + MARK_READ_BUTTON: "mark_read_button", +}; export const USER_TRACKER_EVENTS = { add_details: "user_details_added", onboarding_complete: "user_onboarding_completed", }; - -export const ONBOARDING_TRACKER_EVENTS = { - root: "onboarding", - step_1: "onboarding_step_1", - step_2: "onboarding_step_2", +export const ONBOARDING_TRACKER_ELEMENTS = { + PROFILE_SETUP_FORM: "onboarding_profile_setup_form", }; -export const SIDEBAR_TRACKER_EVENTS = { - click: "sidenav_clicked", +export const SIDEBAR_TRACKER_ELEMENTS = { + USER_MENU_ITEM: "sidenav_user_menu_item", }; diff --git a/web/app/(all)/[workspaceSlug]/(projects)/workspace-views/header.tsx b/web/app/(all)/[workspaceSlug]/(projects)/workspace-views/header.tsx index 399f9aab690..e1f34b348a9 100644 --- a/web/app/(all)/[workspaceSlug]/(projects)/workspace-views/header.tsx +++ b/web/app/(all)/[workspaceSlug]/(projects)/workspace-views/header.tsx @@ -10,7 +10,8 @@ import { EIssueFilterType, EIssuesStoreType, ISSUE_DISPLAY_FILTERS_BY_PAGE, - EIssueLayoutTypes + EIssueLayoutTypes, + GLOBAL_VIEW_TRACKER_ELEMENTS, } from "@plane/constants"; import { useTranslation } from "@plane/i18n"; // types @@ -228,7 +229,12 @@ export const GlobalIssuesHeader = observer(() => { <> )} -
diff --git a/web/app/(all)/onboarding/page.tsx b/web/app/(all)/onboarding/page.tsx index 078d6fefaec..7e7d15a10ee 100644 --- a/web/app/(all)/onboarding/page.tsx +++ b/web/app/(all)/onboarding/page.tsx @@ -16,7 +16,8 @@ import { USER_WORKSPACES_LIST } from "@/constants/fetch-keys"; // helpers import { EPageTypes } from "@/helpers/authentication.helper"; // hooks -import { useUser, useWorkspace, useUserProfile, useEventTracker } from "@/hooks/store"; +import { captureSuccess } from "@/helpers/event-tracker.helper"; +import { useUser, useWorkspace, useUserProfile } from "@/hooks/store"; // wrappers import { AuthenticationWrapper } from "@/lib/wrappers"; import { WorkspaceService } from "@/plane-web/services"; @@ -35,7 +36,6 @@ const OnboardingPage = observer(() => { const [step, setStep] = useState(null); const [totalSteps, setTotalSteps] = useState(null); // store hooks - const { captureEvent } = useEventTracker(); const { isLoading: userLoader, data: user, updateCurrentUser } = useUser(); const { data: profile, updateUserProfile, finishUserOnboarding } = useUserProfile(); const { workspaces, fetchWorkspaces } = useWorkspace(); @@ -73,10 +73,12 @@ const OnboardingPage = observer(() => { await finishUserOnboarding() .then(() => { - captureEvent(USER_TRACKER_EVENTS.onboarding_complete, { - email: user.email, - user_id: user.id, - status: "SUCCESS", + captureSuccess({ + eventName: USER_TRACKER_EVENTS.onboarding_complete, + payload: { + email: user.email, + user_id: user.id, + }, }); }) .catch(() => { diff --git a/web/core/components/home/root.tsx b/web/core/components/home/root.tsx index 4c25bc3f68e..fd3c256b0ee 100644 --- a/web/core/components/home/root.tsx +++ b/web/core/components/home/root.tsx @@ -1,18 +1,21 @@ import { observer } from "mobx-react"; import { useParams } from "next/navigation"; -// components import useSWR from "swr"; +// plane imports import { PRODUCT_TOUR_TRACKER_EVENTS } from "@plane/constants"; import { ContentWrapper } from "@plane/ui"; import { cn } from "@plane/utils"; +// components import { TourRoot } from "@/components/onboarding"; -// constants // helpers +import { captureSuccess } from "@/helpers/event-tracker.helper"; // hooks -import { useUserProfile, useEventTracker, useUser } from "@/hooks/store"; +import { useUserProfile, useUser } from "@/hooks/store"; import { useHome } from "@/hooks/store/use-home"; import useSize from "@/hooks/use-window-size"; +// plane web components import { HomePeekOverviewsRoot } from "@/plane-web/components/home"; +// local imports import { DashboardWidgets } from "./home-dashboard-widgets"; import { UserGreetingsView } from "./user-greetings"; @@ -21,7 +24,6 @@ export const WorkspaceHomeView = observer(() => { const { workspaceSlug } = useParams(); const { data: currentUser } = useUser(); const { data: currentUserProfile, updateTourCompleted } = useUserProfile(); - const { captureEvent } = useEventTracker(); const { toggleWidgetSettings, fetchWidgets } = useHome(); const [windowWidth] = useSize(); @@ -38,9 +40,11 @@ export const WorkspaceHomeView = observer(() => { const handleTourCompleted = () => { updateTourCompleted() .then(() => { - captureEvent(PRODUCT_TOUR_TRACKER_EVENTS.complete, { - user_id: currentUser?.id, - state: "SUCCESS", + captureSuccess({ + eventName: PRODUCT_TOUR_TRACKER_EVENTS.complete, + payload: { + user_id: currentUser?.id, + }, }); }) .catch((error) => { diff --git a/web/core/components/issues/issue-layouts/filters/applied-filters/roots/global-view-root.tsx b/web/core/components/issues/issue-layouts/filters/applied-filters/roots/global-view-root.tsx index 6bf8ed36160..124b9465f9a 100644 --- a/web/core/components/issues/issue-layouts/filters/applied-filters/roots/global-view-root.tsx +++ b/web/core/components/issues/issue-layouts/filters/applied-filters/roots/global-view-root.tsx @@ -13,7 +13,7 @@ import { EViewAccess, EUserPermissions, EUserPermissionsLevel, - GLOBAL_VIEW_TOUR_TRACKER_EVENTS, + GLOBAL_VIEW_TRACKER_EVENTS, } from "@plane/constants"; import { IIssueFilterOptions, TStaticViewTypes } from "@plane/types"; //ui @@ -26,7 +26,8 @@ import { CreateUpdateWorkspaceViewModal } from "@/components/workspace"; // constants // helpers // hooks -import { useEventTracker, useGlobalView, useIssues, useLabel, useUser, useUserPermissions } from "@/hooks/store"; +import { captureError, captureSuccess } from "@/helpers/event-tracker.helper"; +import { useGlobalView, useIssues, useLabel, useUser, useUserPermissions } from "@/hooks/store"; import { getAreFiltersEqual } from "../../../utils"; type Props = { @@ -44,7 +45,6 @@ export const GlobalViewsAppliedFiltersRoot = observer((props: Props) => { } = useIssues(EIssuesStoreType.GLOBAL); const { workspaceLabels } = useLabel(); const { globalViewMap, updateGlobalView } = useGlobalView(); - const { captureEvent } = useEventTracker(); const { data } = useUser(); const { allowPermissions } = useUserPermissions(); @@ -112,15 +112,25 @@ export const GlobalViewsAppliedFiltersRoot = observer((props: Props) => { const handleUpdateView = () => { if (!workspaceSlug || !globalViewId) return; - updateGlobalView(workspaceSlug.toString(), globalViewId.toString(), viewFilters).then((res) => { - if (res) - captureEvent(GLOBAL_VIEW_TOUR_TRACKER_EVENTS.update, { - view_id: res.id, - applied_filters: res.filters, - state: "SUCCESS", - element: "Spreadsheet view", + updateGlobalView(workspaceSlug.toString(), globalViewId.toString(), viewFilters) + .then((res) => { + if (res) + captureSuccess({ + eventName: GLOBAL_VIEW_TRACKER_EVENTS.update, + payload: { + view_id: globalViewId, + }, + }); + }) + .catch((error) => { + captureError({ + eventName: GLOBAL_VIEW_TRACKER_EVENTS.update, + payload: { + view_id: globalViewId, + }, + error: error, }); - }); + }); }; // add a placeholder object instead of appliedFilters if it is undefined diff --git a/web/core/components/onboarding/profile-setup.tsx b/web/core/components/onboarding/profile-setup.tsx index 68c4d7c05a0..8fbafd6af8e 100644 --- a/web/core/components/onboarding/profile-setup.tsx +++ b/web/core/components/onboarding/profile-setup.tsx @@ -6,7 +6,7 @@ import Image from "next/image"; import { useTheme } from "next-themes"; import { Controller, useForm } from "react-hook-form"; import { Eye, EyeOff } from "lucide-react"; -import { E_PASSWORD_STRENGTH, ONBOARDING_TRACKER_EVENTS, USER_TRACKER_EVENTS } from "@plane/constants"; +import { E_PASSWORD_STRENGTH, ONBOARDING_TRACKER_ELEMENTS, USER_TRACKER_EVENTS } from "@plane/constants"; // types import { useTranslation } from "@plane/i18n"; import { IUser, TUserProfile, TOnboardingSteps } from "@plane/types"; @@ -20,7 +20,8 @@ import { OnboardingHeader, SwitchAccountDropdown } from "@/components/onboarding // constants // helpers // hooks -import { useEventTracker, useUser, useUserProfile } from "@/hooks/store"; +import { captureError, captureSuccess, captureView } from "@/helpers/event-tracker.helper"; +import { useUser, useUserProfile } from "@/hooks/store"; // assets import ProfileSetupDark from "@/public/onboarding/profile-setup-dark.webp"; import ProfileSetupLight from "@/public/onboarding/profile-setup-light.webp"; @@ -98,7 +99,6 @@ export const ProfileSetup: React.FC = observer((props) => { // store hooks const { updateCurrentUser } = useUser(); const { updateUserProfile } = useUserProfile(); - const { captureEvent } = useEventTracker(); // form info const { getValues, @@ -143,11 +143,12 @@ export const ProfileSetup: React.FC = observer((props) => { updateUserProfile(profileUpdatePayload), totalSteps > 2 && stepChange({ profile_complete: true }), ]); - captureEvent(USER_TRACKER_EVENTS.add_details, { - use_case: formData.use_case, - role: formData.role, - state: "SUCCESS", - element: ONBOARDING_TRACKER_EVENTS.step_1, + captureSuccess({ + eventName: USER_TRACKER_EVENTS.add_details, + payload: { + use_case: formData.use_case, + role: formData.role, + }, }); setToast({ type: TOAST_TYPE.SUCCESS, @@ -159,9 +160,8 @@ export const ProfileSetup: React.FC = observer((props) => { finishOnboarding(); } } catch { - captureEvent(USER_TRACKER_EVENTS.add_details, { - state: "FAILED", - element: ONBOARDING_TRACKER_EVENTS.step_1, + captureError({ + eventName: USER_TRACKER_EVENTS.add_details, }); setToast({ type: TOAST_TYPE.ERROR, @@ -183,9 +183,8 @@ export const ProfileSetup: React.FC = observer((props) => { formData.password && handleSetPassword(formData.password), ]).then(() => setProfileSetupStep(EProfileSetupSteps.USER_PERSONALIZATION)); } catch { - captureEvent(USER_TRACKER_EVENTS.add_details, { - state: "FAILED", - element: ONBOARDING_TRACKER_EVENTS.step_1, + captureError({ + eventName: USER_TRACKER_EVENTS.add_details, }); setToast({ type: TOAST_TYPE.ERROR, @@ -205,11 +204,12 @@ export const ProfileSetup: React.FC = observer((props) => { updateUserProfile(profileUpdatePayload), totalSteps > 2 && stepChange({ profile_complete: true }), ]); - captureEvent(USER_TRACKER_EVENTS.add_details, { - use_case: formData.use_case, - role: formData.role, - state: "SUCCESS", - element: ONBOARDING_TRACKER_EVENTS.step_2, + captureSuccess({ + eventName: USER_TRACKER_EVENTS.add_details, + payload: { + use_case: formData.use_case, + role: formData.role, + }, }); setToast({ type: TOAST_TYPE.SUCCESS, @@ -221,9 +221,8 @@ export const ProfileSetup: React.FC = observer((props) => { finishOnboarding(); } } catch { - captureEvent(USER_TRACKER_EVENTS.add_details, { - state: "FAILED", - element: ONBOARDING_TRACKER_EVENTS.step_2, + captureError({ + eventName: USER_TRACKER_EVENTS.add_details, }); setToast({ type: TOAST_TYPE.ERROR, @@ -235,6 +234,9 @@ export const ProfileSetup: React.FC = observer((props) => { const onSubmit = async (formData: TProfileSetupFormValues) => { if (!user) return; + captureView({ + elementName: ONBOARDING_TRACKER_ELEMENTS.PROFILE_SETUP_FORM, + }); if (profileSetupStep === EProfileSetupSteps.ALL) await handleSubmitProfileSetup(formData); if (profileSetupStep === EProfileSetupSteps.USER_DETAILS) await handleSubmitUserDetail(formData); if (profileSetupStep === EProfileSetupSteps.USER_PERSONALIZATION) await handleSubmitUserPersonalization(formData); diff --git a/web/core/components/onboarding/tour/root.tsx b/web/core/components/onboarding/tour/root.tsx index 90a183e0b3f..167ee752f54 100644 --- a/web/core/components/onboarding/tour/root.tsx +++ b/web/core/components/onboarding/tour/root.tsx @@ -5,13 +5,14 @@ import { observer } from "mobx-react"; import Image, { StaticImageData } from "next/image"; import { X } from "lucide-react"; // ui -import { PRODUCT_TOUR_TRACKER_EVENTS } from "@plane/constants"; +import { PRODUCT_TOUR_TRACKER_ELEMENTS } from "@plane/constants"; import { Button } from "@plane/ui"; // components import { TourSidebar } from "@/components/onboarding"; // constants // hooks -import { useCommandPalette, useEventTracker, useUser } from "@/hooks/store"; +import { captureClick } from "@/helpers/event-tracker.helper"; +import { useCommandPalette, useUser } from "@/hooks/store"; // assets import CyclesTour from "@/public/onboarding/cycles.webp"; import IssuesTour from "@/public/onboarding/issues.webp"; @@ -85,7 +86,6 @@ export const TourRoot: React.FC = observer((props) => { const [step, setStep] = useState("welcome"); // store hooks const { toggleCreateProjectModal } = useCommandPalette(); - const { setTrackElement, captureEvent } = useEventTracker(); const { data: currentUser } = useUser(); const currentStepIndex = TOUR_STEPS.findIndex((tourStep) => tourStep.key === step); @@ -112,7 +112,9 @@ export const TourRoot: React.FC = observer((props) => { {isOwner && <>{updateButton}} diff --git a/web/core/components/workspace-notifications/sidebar/header/options/root.tsx b/web/core/components/workspace-notifications/sidebar/header/options/root.tsx index 4de95375929..f15520ec326 100644 --- a/web/core/components/workspace-notifications/sidebar/header/options/root.tsx +++ b/web/core/components/workspace-notifications/sidebar/header/options/root.tsx @@ -2,14 +2,20 @@ import { FC } from "react"; import { observer } from "mobx-react"; import { CheckCheck, RefreshCw } from "lucide-react"; // plane imports -import { ENotificationLoader, ENotificationQueryParamType, NOTIFICATION_TRACKER_EVENTS } from "@plane/constants"; +import { + ENotificationLoader, + ENotificationQueryParamType, + NOTIFICATION_TRACKER_ELEMENTS, + NOTIFICATION_TRACKER_EVENTS, +} from "@plane/constants"; import { useTranslation } from "@plane/i18n"; import { Spinner, Tooltip } from "@plane/ui"; // components import { NotificationFilter, NotificationHeaderMenuOption } from "@/components/workspace-notifications"; // constants // hooks -import { useEventTracker, useWorkspaceNotifications } from "@/hooks/store"; +import { captureSuccess } from "@/helpers/event-tracker.helper"; +import { useWorkspaceNotifications } from "@/hooks/store"; import { usePlatformOS } from "@/hooks/use-platform-os"; type TNotificationSidebarHeaderOptions = { @@ -21,7 +27,6 @@ export const NotificationSidebarHeaderOptions: FC { @@ -49,8 +54,11 @@ export const NotificationSidebarHeaderOptions: FC
{ - captureEvent(NOTIFICATION_TRACKER_EVENTS.all_marked_read); + captureSuccess({ + eventName: NOTIFICATION_TRACKER_EVENTS.all_marked_read, + }); handleMarkAllNotificationsAsRead(); }} > diff --git a/web/core/components/workspace-notifications/sidebar/notification-card/options/archive.tsx b/web/core/components/workspace-notifications/sidebar/notification-card/options/archive.tsx index 0c7c87411fc..402ee37f4b8 100644 --- a/web/core/components/workspace-notifications/sidebar/notification-card/options/archive.tsx +++ b/web/core/components/workspace-notifications/sidebar/notification-card/options/archive.tsx @@ -3,14 +3,15 @@ import { FC } from "react"; import { observer } from "mobx-react"; import { ArchiveRestore } from "lucide-react"; -import { NOTIFICATION_TRACKER_EVENTS } from "@plane/constants"; +import { NOTIFICATION_TRACKER_ELEMENTS, NOTIFICATION_TRACKER_EVENTS } from "@plane/constants"; import { useTranslation } from "@plane/i18n"; import { ArchiveIcon, TOAST_TYPE, setToast } from "@plane/ui"; // components import { NotificationItemOptionButton } from "@/components/workspace-notifications"; // constants // hooks -import { useEventTracker, useWorkspaceNotifications } from "@/hooks/store"; +import { captureClick, captureSuccess } from "@/helpers/event-tracker.helper"; +import { useWorkspaceNotifications } from "@/hooks/store"; // store import { INotification } from "@/store/notifications/notification"; @@ -22,7 +23,6 @@ type TNotificationItemArchiveOption = { export const NotificationItemArchiveOption: FC = observer((props) => { const { workspaceSlug, notification } = props; // hooks - const { captureEvent } = useEventTracker(); const { currentNotificationTab } = useWorkspaceNotifications(); const { asJson: data, archiveNotification, unArchiveNotification } = notification; const { t } = useTranslation(); @@ -30,11 +30,16 @@ export const NotificationItemArchiveOption: FC = const handleNotificationUpdate = async () => { try { const request = data.archived_at ? unArchiveNotification : archiveNotification; + captureClick({ + elementName: NOTIFICATION_TRACKER_ELEMENTS.ARCHIVE_BUTTON, + }); await request(workspaceSlug); - captureEvent(NOTIFICATION_TRACKER_EVENTS.archive, { - issue_id: data?.data?.issue?.id, - tab: currentNotificationTab, - state: "SUCCESS", + captureSuccess({ + eventName: NOTIFICATION_TRACKER_EVENTS.archive, + payload: { + id: data?.data?.issue?.id, + tab: currentNotificationTab, + }, }); setToast({ title: data.archived_at ? t("notification.toasts.unarchived") : t("notification.toasts.archived"), diff --git a/web/core/components/workspace-notifications/sidebar/notification-card/options/read.tsx b/web/core/components/workspace-notifications/sidebar/notification-card/options/read.tsx index 74ca4b2fd2a..c9761d685c4 100644 --- a/web/core/components/workspace-notifications/sidebar/notification-card/options/read.tsx +++ b/web/core/components/workspace-notifications/sidebar/notification-card/options/read.tsx @@ -3,14 +3,15 @@ import { FC } from "react"; import { observer } from "mobx-react"; import { MessageSquare } from "lucide-react"; -import { NOTIFICATION_TRACKER_EVENTS } from "@plane/constants"; +import { NOTIFICATION_TRACKER_ELEMENTS, NOTIFICATION_TRACKER_EVENTS } from "@plane/constants"; import { useTranslation } from "@plane/i18n"; import { TOAST_TYPE, setToast } from "@plane/ui"; // components import { NotificationItemOptionButton } from "@/components/workspace-notifications"; // constants // hooks -import { useEventTracker, useWorkspaceNotifications } from "@/hooks/store"; +import { captureClick, captureSuccess } from "@/helpers/event-tracker.helper"; +import { useWorkspaceNotifications } from "@/hooks/store"; // store import { INotification } from "@/store/notifications/notification"; @@ -22,7 +23,6 @@ type TNotificationItemReadOption = { export const NotificationItemReadOption: FC = observer((props) => { const { workspaceSlug, notification } = props; // hooks - const { captureEvent } = useEventTracker(); const { currentNotificationTab } = useWorkspaceNotifications(); const { asJson: data, markNotificationAsRead, markNotificationAsUnRead } = notification; const { t } = useTranslation(); @@ -30,11 +30,16 @@ export const NotificationItemReadOption: FC = obser const handleNotificationUpdate = async () => { try { const request = data.read_at ? markNotificationAsUnRead : markNotificationAsRead; + captureClick({ + elementName: NOTIFICATION_TRACKER_ELEMENTS.MARK_READ_BUTTON, + }); await request(workspaceSlug); - captureEvent(NOTIFICATION_TRACKER_EVENTS.all_marked_read, { - issue_id: data?.data?.issue?.id, - tab: currentNotificationTab, - state: "SUCCESS", + captureSuccess({ + eventName: NOTIFICATION_TRACKER_EVENTS.all_marked_read, + payload: { + id: data?.data?.issue?.id, + tab: currentNotificationTab, + }, }); setToast({ title: data.read_at ? t("notification.toasts.unread") : t("notification.toasts.read"), diff --git a/web/core/components/workspace/sidebar/user-menu-item.tsx b/web/core/components/workspace/sidebar/user-menu-item.tsx index 3f89dd6875b..d3124c6659e 100644 --- a/web/core/components/workspace/sidebar/user-menu-item.tsx +++ b/web/core/components/workspace/sidebar/user-menu-item.tsx @@ -3,7 +3,7 @@ import { observer } from "mobx-react"; import Link from "next/link"; import { useParams, usePathname } from "next/navigation"; // plane imports -import { EUserPermissionsLevel, EUserWorkspaceRoles, SIDEBAR_TRACKER_EVENTS } from "@plane/constants"; +import { EUserPermissionsLevel, EUserWorkspaceRoles, SIDEBAR_TRACKER_ELEMENTS } from "@plane/constants"; import { usePlatformOS } from "@plane/hooks"; import { useTranslation } from "@plane/i18n"; import { Tooltip } from "@plane/ui"; @@ -11,7 +11,8 @@ import { Tooltip } from "@plane/ui"; import { SidebarNavItem } from "@/components/sidebar"; import { NotificationAppSidebarOption } from "@/components/workspace-notifications"; // hooks -import { useAppTheme, useEventTracker, useUserPermissions } from "@/hooks/store"; +import { captureClick } from "@/helpers/event-tracker.helper"; +import { useAppTheme, useUserPermissions } from "@/hooks/store"; export interface SidebarUserMenuItemProps { item: { @@ -33,7 +34,6 @@ export const SidebarUserMenuItem: FC = observer((props // package hooks const { t } = useTranslation(); // store hooks - const { captureEvent } = useEventTracker(); const { allowPermissions } = useUserPermissions(); const { toggleSidebar, sidebarCollapsed } = useAppTheme(); const { isMobile } = usePlatformOS(); @@ -49,8 +49,11 @@ export const SidebarUserMenuItem: FC = observer((props if (window.innerWidth < 768) { toggleSidebar(); } - captureEvent(SIDEBAR_TRACKER_EVENTS.click, { - destination: itemKey, + captureClick({ + elementName: SIDEBAR_TRACKER_ELEMENTS.USER_MENU_ITEM, + context: { + destination: itemKey, + }, }); }; diff --git a/web/core/components/workspace/views/delete-view-modal.tsx b/web/core/components/workspace/views/delete-view-modal.tsx index 65f4efdd4e5..0e6c5857e10 100644 --- a/web/core/components/workspace/views/delete-view-modal.tsx +++ b/web/core/components/workspace/views/delete-view-modal.tsx @@ -4,13 +4,14 @@ import React, { useState } from "react"; import { observer } from "mobx-react"; import { useParams } from "next/navigation"; // types -import { GLOBAL_VIEW_TOUR_TRACKER_EVENTS } from "@plane/constants"; +import { GLOBAL_VIEW_TRACKER_EVENTS } from "@plane/constants"; import { IWorkspaceView } from "@plane/types"; // ui import { AlertModalCore, TOAST_TYPE, setToast } from "@plane/ui"; // constants // hooks -import { useGlobalView, useEventTracker } from "@/hooks/store"; +import { captureError, captureSuccess } from "@/helpers/event-tracker.helper"; +import { useGlobalView } from "@/hooks/store"; type Props = { data: IWorkspaceView; @@ -26,7 +27,6 @@ export const DeleteGlobalViewModal: React.FC = observer((props) => { const { workspaceSlug } = useParams(); // store hooks const { deleteGlobalView } = useGlobalView(); - const { captureEvent } = useEventTracker(); const handleClose = () => onClose(); @@ -37,15 +37,20 @@ export const DeleteGlobalViewModal: React.FC = observer((props) => { await deleteGlobalView(workspaceSlug.toString(), data.id) .then(() => { - captureEvent(GLOBAL_VIEW_TOUR_TRACKER_EVENTS.delete, { - view_id: data.id, - state: "SUCCESS", + captureSuccess({ + eventName: GLOBAL_VIEW_TRACKER_EVENTS.delete, + payload: { + view_id: data.id, + }, }); }) .catch((error: any) => { - captureEvent(GLOBAL_VIEW_TOUR_TRACKER_EVENTS.delete, { - view_id: data.id, - state: "FAILED", + captureError({ + eventName: GLOBAL_VIEW_TRACKER_EVENTS.delete, + payload: { + view_id: data.id, + }, + error: error, }); setToast({ type: TOAST_TYPE.ERROR, diff --git a/web/core/components/workspace/views/header.tsx b/web/core/components/workspace/views/header.tsx index 4aa17493c30..c61290dcd19 100644 --- a/web/core/components/workspace/views/header.tsx +++ b/web/core/components/workspace/views/header.tsx @@ -8,7 +8,8 @@ import { DEFAULT_GLOBAL_VIEWS_LIST, EUserPermissions, EUserPermissionsLevel, - GLOBAL_VIEW_TOUR_TRACKER_EVENTS, + GLOBAL_VIEW_TRACKER_ELEMENTS, + GLOBAL_VIEW_TRACKER_EVENTS, } from "@plane/constants"; import { TStaticViewTypes } from "@plane/types"; // components @@ -20,6 +21,7 @@ import { } from "@/components/workspace"; // constants // store hooks +import { captureSuccess } from "@/helpers/event-tracker.helper"; import { useEventTracker, useGlobalView, useUserPermissions } from "@/hooks/store"; const ViewTab = observer((props: { viewId: string }) => { @@ -77,11 +79,14 @@ export const GlobalViewsHeader: React.FC = observer(() => { // bring the active view to the centre of the header useEffect(() => { if (globalViewId && currentWorkspaceViews) { - captureEvent(GLOBAL_VIEW_TOUR_TRACKER_EVENTS.open, { - view_id: globalViewId, - view_type: ["all-issues", "assigned", "created", "subscribed"].includes(globalViewId.toString()) - ? "Default" - : "Custom", + captureSuccess({ + eventName: GLOBAL_VIEW_TRACKER_EVENTS.open, + payload: { + view_id: globalViewId, + view_type: ["all-issues", "assigned", "created", "subscribed"].includes(globalViewId.toString()) + ? "Default" + : "Custom", + }, }); const activeTabElement = document.querySelector(`#global-view-${globalViewId.toString()}`); if (activeTabElement && containerRef.current) { @@ -115,6 +120,7 @@ export const GlobalViewsHeader: React.FC = observer(() => { {isAuthorizedUser ? (