From 7359f8bd01530ec062117860745e54c5ed77c145 Mon Sep 17 00:00:00 2001 From: Dariusz Biela Date: Fri, 12 Dec 2025 14:14:31 +0100 Subject: [PATCH 1/7] feat: add Sentry labels to report preview components --- src/CONST/index.ts | 14 ++++++++++++++ src/components/AnimatedSubmitButton/index.tsx | 6 +++++- src/components/ButtonWithDropdownMenu/index.tsx | 4 ++++ src/components/ButtonWithDropdownMenu/types.ts | 3 +++ .../ReportActionItem/ExportWithDropdownMenu.tsx | 5 +++++ .../MoneyRequestReportPreviewContent.tsx | 9 +++++++++ .../ReportActionItem/TransactionPreview/index.tsx | 1 + .../SettlementButton/AnimatedSettlementButton.tsx | 3 +++ src/components/SettlementButton/index.tsx | 2 ++ src/components/SettlementButton/types.ts | 3 +++ 10 files changed, 49 insertions(+), 1 deletion(-) diff --git a/src/CONST/index.ts b/src/CONST/index.ts index 975cbd0052a77..e35df81049c37 100755 --- a/src/CONST/index.ts +++ b/src/CONST/index.ts @@ -7525,6 +7525,20 @@ const CONST = { WORKSPACES: 'NavigationTabBar-Workspaces', ACCOUNT: 'NavigationTabBar-Account', }, + REPORT_PREVIEW: { + CARD: 'ReportPreview-Card', + CAROUSEL_PREVIOUS: 'ReportPreview-CarouselPrevious', + CAROUSEL_NEXT: 'ReportPreview-CarouselNext', + SUBMIT_BUTTON: 'ReportPreview-SubmitButton', + APPROVE_BUTTON: 'ReportPreview-ApproveButton', + PAY_BUTTON: 'ReportPreview-PayButton', + EXPORT_BUTTON: 'ReportPreview-ExportButton', + VIEW_BUTTON: 'ReportPreview-ViewButton', + ADD_EXPENSE_BUTTON: 'ReportPreview-AddExpenseButton', + }, + TRANSACTION_PREVIEW: { + CARD: 'TransactionPreview-Card', + }, }, } as const; diff --git a/src/components/AnimatedSubmitButton/index.tsx b/src/components/AnimatedSubmitButton/index.tsx index e85907f5e0ae1..f555672feaa79 100644 --- a/src/components/AnimatedSubmitButton/index.tsx +++ b/src/components/AnimatedSubmitButton/index.tsx @@ -26,9 +26,12 @@ type AnimatedSubmitButtonProps = { // Whether the button should be disabled isDisabled?: boolean; + + // Label for Sentry tracking + sentryLabel?: string; }; -function AnimatedSubmitButton({success, text, onPress, isSubmittingAnimationRunning, onAnimationFinish, isDisabled}: AnimatedSubmitButtonProps) { +function AnimatedSubmitButton({success, text, onPress, isSubmittingAnimationRunning, onAnimationFinish, isDisabled, sentryLabel}: AnimatedSubmitButtonProps) { const styles = useThemeStyles(); const {translate} = useLocalize(); const isAnimationRunning = isSubmittingAnimationRunning; @@ -133,6 +136,7 @@ function AnimatedSubmitButton({success, text, onPress, isSubmittingAnimationRunn onPress={onPress} icon={icon} isDisabled={isDisabled} + sentryLabel={sentryLabel} /> )} diff --git a/src/components/ButtonWithDropdownMenu/index.tsx b/src/components/ButtonWithDropdownMenu/index.tsx index efa05d4482a3a..1a55f377406ca 100644 --- a/src/components/ButtonWithDropdownMenu/index.tsx +++ b/src/components/ButtonWithDropdownMenu/index.tsx @@ -60,6 +60,7 @@ function ButtonWithDropdownMenu({ref, ...props}: ButtonWithDropdownM shouldUseShortForm = false, shouldUseOptionIcon = false, shouldStayNormalOnDisable = false, + sentryLabel, } = props; const theme = useTheme(); @@ -187,6 +188,7 @@ function ButtonWithDropdownMenu({ref, ...props}: ButtonWithDropdownM textStyles={[isTextTooLong && shouldUseShortForm ? {...styles.textExtraSmall, ...styles.textBold} : {}]} secondLineText={secondLineText} icon={icon} + sentryLabel={sentryLabel} /> {isSplitButton && ( @@ -204,6 +206,7 @@ function ButtonWithDropdownMenu({ref, ...props}: ButtonWithDropdownM small={buttonSize === CONST.DROPDOWN_BUTTON_SIZE.SMALL} innerStyles={[styles.dropDownButtonCartIconContainerPadding, innerStyleDropButton, isButtonSizeSmall && styles.dropDownButtonCartIcon]} enterKeyEventListenerPriority={enterKeyEventListenerPriority} + sentryLabel={sentryLabel} > @@ -253,6 +256,7 @@ function ButtonWithDropdownMenu({ref, ...props}: ButtonWithDropdownM iconRight={shouldShowButtonRightIcon ? options.at(0)?.icon : undefined} shouldShowRightIcon={shouldShowButtonRightIcon} testID={testID} + sentryLabel={sentryLabel} /> )} {(shouldAlwaysShowDropdownMenu || options.length > 1) && !!popoverAnchorPosition && ( diff --git a/src/components/ButtonWithDropdownMenu/types.ts b/src/components/ButtonWithDropdownMenu/types.ts index 5224c0afd3378..04c07c16a2173 100644 --- a/src/components/ButtonWithDropdownMenu/types.ts +++ b/src/components/ButtonWithDropdownMenu/types.ts @@ -157,6 +157,9 @@ type ButtonWithDropdownMenuProps = { /** Reference to the outer element */ ref?: React.Ref; + + /** Label for Sentry tracking */ + sentryLabel?: string; }; type ButtonWithDropdownMenuRef = { diff --git a/src/components/ReportActionItem/ExportWithDropdownMenu.tsx b/src/components/ReportActionItem/ExportWithDropdownMenu.tsx index 75df574589a3a..bdaccf92f57db 100644 --- a/src/components/ReportActionItem/ExportWithDropdownMenu.tsx +++ b/src/components/ReportActionItem/ExportWithDropdownMenu.tsx @@ -31,6 +31,9 @@ type ExportWithDropdownMenuProps = { dropdownAnchorAlignment?: AnchorAlignment; wrapperStyle?: StyleProp; + + /** Label for Sentry tracking */ + sentryLabel?: string; }; function ExportWithDropdownMenu({ @@ -42,6 +45,7 @@ function ExportWithDropdownMenu({ vertical: CONST.MODAL.ANCHOR_ORIGIN_VERTICAL.TOP, }, wrapperStyle, + sentryLabel, }: ExportWithDropdownMenuProps) { const reportID = report?.reportID; const styles = useThemeStyles(); @@ -131,6 +135,7 @@ function ExportWithDropdownMenu({ style={[shouldUseNarrowLayout && styles.flexGrow1]} wrapperStyle={flattenedWrapperStyle} buttonSize={CONST.DROPDOWN_BUTTON_SIZE.MEDIUM} + sentryLabel={sentryLabel} /> ), [CONST.REPORT.REPORT_PREVIEW_ACTIONS.APPROVE]: ( @@ -552,6 +553,7 @@ function MoneyRequestReportPreviewContent({ text={translate('iou.approve')} success onPress={() => confirmApproval()} + sentryLabel={CONST.SENTRY_LABEL.REPORT_PREVIEW.APPROVE_BUTTON} /> ), [CONST.REPORT.REPORT_PREVIEW_ACTIONS.PAY]: ( @@ -583,6 +585,7 @@ function MoneyRequestReportPreviewContent({ }} isDisabled={isOffline && !canAllowSettlement} isLoading={!isOffline && !canAllowSettlement} + sentryLabel={CONST.SENTRY_LABEL.REPORT_PREVIEW.PAY_BUTTON} /> ), [CONST.REPORT.REPORT_PREVIEW_ACTIONS.EXPORT_TO_ACCOUNTING]: connectedIntegration ? ( @@ -595,6 +598,7 @@ function MoneyRequestReportPreviewContent({ horizontal: CONST.MODAL.ANCHOR_ORIGIN_HORIZONTAL.RIGHT, vertical: CONST.MODAL.ANCHOR_ORIGIN_VERTICAL.BOTTOM, }} + sentryLabel={CONST.SENTRY_LABEL.REPORT_PREVIEW.EXPORT_BUTTON} /> ) : null, [CONST.REPORT.REPORT_PREVIEW_ACTIONS.VIEW]: ( @@ -603,6 +607,7 @@ function MoneyRequestReportPreviewContent({ onPress={() => { openReportFromPreview(); }} + sentryLabel={CONST.SENTRY_LABEL.REPORT_PREVIEW.VIEW_BUTTON} /> ), [CONST.REPORT.REPORT_PREVIEW_ACTIONS.ADD_EXPENSE]: ( @@ -616,6 +621,7 @@ function MoneyRequestReportPreviewContent({ horizontal: CONST.MODAL.ANCHOR_ORIGIN_HORIZONTAL.RIGHT, vertical: CONST.MODAL.ANCHOR_ORIGIN_VERTICAL.BOTTOM, }} + sentryLabel={CONST.SENTRY_LABEL.REPORT_PREVIEW.ADD_EXPENSE_BUTTON} /> ), }; @@ -670,6 +676,7 @@ function MoneyRequestReportPreviewContent({ role={getButtonRole(true)} isNested accessibilityLabel={translate('iou.viewDetails')} + sentryLabel={CONST.SENTRY_LABEL.REPORT_PREVIEW.CARD} > handleChange(currentIndex - 1)} disabled={optimisticIndex !== undefined ? optimisticIndex === 0 : currentIndex === 0 && currentVisibleItems.at(0) === 0} disabledStyle={[styles.cursorDefault, styles.buttonOpacityDisabled]} + sentryLabel={CONST.SENTRY_LABEL.REPORT_PREVIEW.CAROUSEL_PREVIOUS} > )} diff --git a/src/components/SettlementButton/index.tsx b/src/components/SettlementButton/index.tsx index 906f8a0102d12..9d4bb177ee933 100644 --- a/src/components/SettlementButton/index.tsx +++ b/src/components/SettlementButton/index.tsx @@ -93,6 +93,7 @@ function SettlementButton({ wrapperStyle, shouldUseShortForm = false, hasOnlyHeldExpenses = false, + sentryLabel, }: SettlementButtonProps) { const icons = useMemoizedLazyExpensifyIcons(['Building', 'User', 'ThumbsUp'] as const); const styles = useThemeStyles(); @@ -639,6 +640,7 @@ function SettlementButton({ enterKeyEventListenerPriority={enterKeyEventListenerPriority} useKeyboardShortcuts={useKeyboardShortcuts} shouldUseModalPaddingStyle={paymentButtonOptions.length <= 5} + sentryLabel={sentryLabel} /> )} diff --git a/src/components/SettlementButton/types.ts b/src/components/SettlementButton/types.ts index 6355f78566a84..f96f9bc0540c9 100644 --- a/src/components/SettlementButton/types.ts +++ b/src/components/SettlementButton/types.ts @@ -103,6 +103,9 @@ type SettlementButtonProps = { /** Whether we the report has only held expenses */ hasOnlyHeldExpenses?: boolean; + + /** Label for Sentry tracking */ + sentryLabel?: string; }; export default SettlementButtonProps; From 01e499dc3622895544eee84a2dafc1686dafb3e4 Mon Sep 17 00:00:00 2001 From: Dariusz Biela Date: Fri, 12 Dec 2025 14:48:25 +0100 Subject: [PATCH 2/7] feat: add Sentry labels to emoji picker and reactions components --- src/CONST/index.ts | 17 +++++++++++++++++ src/components/BaseMiniContextMenuItem.tsx | 8 +++++++- .../EmojiPicker/CategoryShortcutButton.tsx | 1 + .../EmojiPicker/EmojiPickerButton.tsx | 1 + .../EmojiPicker/EmojiPickerButtonDropdown.tsx | 1 + .../EmojiPickerMenu/index.native.tsx | 1 + .../EmojiPicker/EmojiPickerMenu/index.tsx | 1 + .../EmojiPickerMenuItem/index.native.tsx | 1 + .../EmojiPicker/EmojiPickerMenuItem/index.tsx | 1 + .../EmojiPicker/EmojiSkinToneList.tsx | 1 + src/components/Reactions/AddReactionBubble.tsx | 1 + .../Reactions/EmojiReactionBubble.tsx | 1 + .../Reactions/MiniQuickEmojiReactions.tsx | 2 ++ .../BaseTextInput/implementation/index.tsx | 3 +++ src/components/TextInput/BaseTextInput/types.ts | 3 +++ .../TextInput/TextInputClearButton/index.tsx | 5 ++++- 16 files changed, 46 insertions(+), 2 deletions(-) diff --git a/src/CONST/index.ts b/src/CONST/index.ts index e35df81049c37..0ce5e2d248082 100755 --- a/src/CONST/index.ts +++ b/src/CONST/index.ts @@ -7539,6 +7539,23 @@ const CONST = { TRANSACTION_PREVIEW: { CARD: 'TransactionPreview-Card', }, + EMOJI_PICKER: { + BUTTON: 'EmojiPicker-Button', + BUTTON_DROPDOWN: 'EmojiPicker-ButtonDropdown', + MENU_ITEM: 'EmojiPicker-MenuItem', + SKIN_TONE_TOGGLE: 'EmojiPicker-SkinToneToggle', + SKIN_TONE_ITEM: 'EmojiPicker-SkinToneItem', + CATEGORY_SHORTCUT: 'EmojiPicker-CategoryShortcut', + SEARCH_INPUT: 'EmojiPicker-SearchInput', + }, + EMOJI_REACTIONS: { + REACTION_BUBBLE: 'EmojiReactions-ReactionBubble', + ADD_REACTION_BUBBLE: 'EmojiReactions-AddReactionBubble', + }, + MINI_CONTEXT_MENU: { + QUICK_REACTION: 'MiniContextMenu-QuickReaction', + EMOJI_PICKER_BUTTON: 'MiniContextMenu-EmojiPickerButton', + }, }, } as const; diff --git a/src/components/BaseMiniContextMenuItem.tsx b/src/components/BaseMiniContextMenuItem.tsx index c9738970bbe3e..ab8873c2d5617 100644 --- a/src/components/BaseMiniContextMenuItem.tsx +++ b/src/components/BaseMiniContextMenuItem.tsx @@ -41,13 +41,18 @@ type BaseMiniContextMenuItemProps = { * Reference to the outer element */ ref?: PressableRef; + + /** + * Label for Sentry tracking + */ + sentryLabel?: string; }; /** * Component that renders a mini context menu item with a * pressable. Also renders a tooltip when hovering the item. */ -function BaseMiniContextMenuItem({tooltipText, onPress, children, isDelayButtonStateComplete = true, shouldPreventDefaultFocusOnPress = true, ref}: BaseMiniContextMenuItemProps) { +function BaseMiniContextMenuItem({tooltipText, onPress, children, isDelayButtonStateComplete = true, shouldPreventDefaultFocusOnPress = true, ref, sentryLabel}: BaseMiniContextMenuItemProps) { const styles = useThemeStyles(); const StyleUtils = useStyleUtils(); return ( @@ -79,6 +84,7 @@ function BaseMiniContextMenuItem({tooltipText, onPress, children, isDelayButtonS }} accessibilityLabel={tooltipText} role={CONST.ROLE.BUTTON} + sentryLabel={sentryLabel} style={({hovered, pressed}) => [ styles.reportActionContextMenuMiniButton, StyleUtils.getButtonBackgroundColorStyle(getButtonState(hovered, pressed, isDelayButtonStateComplete), true), diff --git a/src/components/EmojiPicker/CategoryShortcutButton.tsx b/src/components/EmojiPicker/CategoryShortcutButton.tsx index 7ffff218d1fe6..775ffd7d8415f 100644 --- a/src/components/EmojiPicker/CategoryShortcutButton.tsx +++ b/src/components/EmojiPicker/CategoryShortcutButton.tsx @@ -43,6 +43,7 @@ function CategoryShortcutButton({code, icon, onPress}: CategoryShortcutButtonPro style={({pressed}) => [StyleUtils.getButtonBackgroundColorStyle(getButtonState(false, pressed)), styles.categoryShortcutButton, isHighlighted && styles.emojiItemHighlighted]} accessibilityLabel={`emojiPicker.headers.${code}`} role={CONST.ROLE.BUTTON} + sentryLabel={CONST.SENTRY_LABEL.EMOJI_PICKER.CATEGORY_SHORTCUT} > {({hovered, pressed}) => ( {({hovered, pressed}) => ( diff --git a/src/components/EmojiPicker/EmojiPickerMenu/index.native.tsx b/src/components/EmojiPicker/EmojiPickerMenu/index.native.tsx index 92fb036ce7a07..349b7e485685e 100644 --- a/src/components/EmojiPicker/EmojiPickerMenu/index.native.tsx +++ b/src/components/EmojiPicker/EmojiPickerMenu/index.native.tsx @@ -126,6 +126,7 @@ function EmojiPickerMenu({onEmojiSelected, activeEmoji, ref}: EmojiPickerMenuPro role={CONST.ROLE.PRESENTATION} onChangeText={filterEmojis} blurOnSubmit={filteredEmojis.length > 0} + sentryLabel={CONST.SENTRY_LABEL.EMOJI_PICKER.SEARCH_INPUT} /> setIsFocused(false)} autoCorrect={false} blurOnSubmit={filteredEmojis.length > 0} + sentryLabel={CONST.SENTRY_LABEL.EMOJI_PICKER.SEARCH_INPUT} /> {emoji} diff --git a/src/components/EmojiPicker/EmojiPickerMenuItem/index.tsx b/src/components/EmojiPicker/EmojiPickerMenuItem/index.tsx index 1629089dace55..b9901782573f8 100644 --- a/src/components/EmojiPicker/EmojiPickerMenuItem/index.tsx +++ b/src/components/EmojiPicker/EmojiPickerMenuItem/index.tsx @@ -74,6 +74,7 @@ function EmojiPickerMenuItem({ ]} accessibilityLabel={emoji} role={CONST.ROLE.BUTTON} + sentryLabel={CONST.SENTRY_LABEL.EMOJI_PICKER.MENU_ITEM} > {emoji} diff --git a/src/components/EmojiPicker/EmojiSkinToneList.tsx b/src/components/EmojiPicker/EmojiSkinToneList.tsx index 99819e415e5af..ad4d49c08c68a 100644 --- a/src/components/EmojiPicker/EmojiSkinToneList.tsx +++ b/src/components/EmojiPicker/EmojiSkinToneList.tsx @@ -55,6 +55,7 @@ function EmojiSkinToneList() { style={[styles.flexRow, styles.alignSelfCenter, styles.justifyContentStart, styles.alignItemsCenter]} accessibilityLabel={translate('emojiPicker.skinTonePickerLabel')} role={CONST.ROLE.BUTTON} + sentryLabel={CONST.SENTRY_LABEL.EMOJI_PICKER.SKIN_TONE_TOGGLE} > {currentSkinTone.code} diff --git a/src/components/Reactions/AddReactionBubble.tsx b/src/components/Reactions/AddReactionBubble.tsx index d98e2ac9ecf7d..92ac8270cd4bd 100644 --- a/src/components/Reactions/AddReactionBubble.tsx +++ b/src/components/Reactions/AddReactionBubble.tsx @@ -107,6 +107,7 @@ function AddReactionBubble({onSelectEmoji, reportAction, onPressOpenPicker, onWi // disable dimming pressDimmingValue={1} dataSet={{[CONST.SELECTION_SCRAPER_HIDDEN_ELEMENT]: true}} + sentryLabel={CONST.SENTRY_LABEL.EMOJI_REACTIONS.ADD_REACTION_BUBBLE} > {({hovered, pressed}) => ( <> diff --git a/src/components/Reactions/EmojiReactionBubble.tsx b/src/components/Reactions/EmojiReactionBubble.tsx index 91863a2e3839d..9db1f82e356a8 100644 --- a/src/components/Reactions/EmojiReactionBubble.tsx +++ b/src/components/Reactions/EmojiReactionBubble.tsx @@ -90,6 +90,7 @@ function EmojiReactionBubble({ accessibilityLabel={emojiCodes.join('')} accessible dataSet={{[CONST.SELECTION_SCRAPER_HIDDEN_ELEMENT]: true}} + sentryLabel={CONST.SENTRY_LABEL.EMOJI_REACTIONS.REACTION_BUBBLE} > {emojiCodes.join('')} {count > 0 && {count}} diff --git a/src/components/Reactions/MiniQuickEmojiReactions.tsx b/src/components/Reactions/MiniQuickEmojiReactions.tsx index 7530ab735e6d3..dcbecb6ff6bcf 100644 --- a/src/components/Reactions/MiniQuickEmojiReactions.tsx +++ b/src/components/Reactions/MiniQuickEmojiReactions.tsx @@ -69,6 +69,7 @@ function MiniQuickEmojiReactions({reportAction, reportActionID, onEmojiSelected, isDelayButtonStateComplete={false} tooltipText={`:${getLocalizedEmojiName(emoji.name, preferredLocale)}:`} onPress={callFunctionIfActionIsAllowed(() => onEmojiSelected(emoji, emojiReactions, preferredSkinTone))} + sentryLabel={CONST.SENTRY_LABEL.MINI_CONTEXT_MENU.QUICK_REACTION} > {({hovered, pressed}) => ( )} diff --git a/src/components/TextInput/BaseTextInput/types.ts b/src/components/TextInput/BaseTextInput/types.ts index 7795345cf6b20..5b1039057c62d 100644 --- a/src/components/TextInput/BaseTextInput/types.ts +++ b/src/components/TextInput/BaseTextInput/types.ts @@ -200,6 +200,9 @@ type CustomBaseTextInputProps = ForwardedFSClassProps & { navigation?: Omit, 'getState'> & { getState(): NavigationState | undefined; }; + + /** Label for Sentry tracking */ + sentryLabel?: string; }; type BaseTextInputRef = HTMLFormElement | AnimatedTextInputRef; diff --git a/src/components/TextInput/TextInputClearButton/index.tsx b/src/components/TextInput/TextInputClearButton/index.tsx index eb419e60784b8..09828330f9272 100644 --- a/src/components/TextInput/TextInputClearButton/index.tsx +++ b/src/components/TextInput/TextInputClearButton/index.tsx @@ -12,9 +12,11 @@ import CONST from '@src/CONST'; type TextInputClearButtonProps = { style?: StyleProp; onPressButton: () => void; + /** Label for Sentry tracking */ + sentryLabel?: string; }; -function TextInputClearButton({style, onPressButton}: TextInputClearButtonProps) { +function TextInputClearButton({style, onPressButton, sentryLabel}: TextInputClearButtonProps) { const theme = useTheme(); const styles = useThemeStyles(); const {translate} = useLocalize(); @@ -28,6 +30,7 @@ function TextInputClearButton({style, onPressButton}: TextInputClearButtonProps) e.preventDefault(); }} onPress={onPressButton} + sentryLabel={sentryLabel ? `${sentryLabel}-ClearButton` : undefined} > Date: Fri, 12 Dec 2025 16:08:33 +0100 Subject: [PATCH 3/7] feat: Add sentry labels to Task components on report page Add sentryLabel prop to track user interactions for Sentry INP monitoring: - TaskPreview: card pressable and checkbox - TaskView: title, checkbox, description and assignee menu items - TaskHeaderActionButton: mark complete/incomplete button - MenuItem: add sentryLabel prop support for all menu items --- src/CONST/index.ts | 9 +++++++++ src/components/MenuItem.tsx | 5 +++++ src/components/ReportActionItem/TaskPreview.tsx | 2 ++ src/components/ReportActionItem/TaskView.tsx | 5 +++++ src/components/TaskHeaderActionButton.tsx | 2 ++ 5 files changed, 23 insertions(+) diff --git a/src/CONST/index.ts b/src/CONST/index.ts index 0ce5e2d248082..7fc8c3030a0eb 100755 --- a/src/CONST/index.ts +++ b/src/CONST/index.ts @@ -7556,6 +7556,15 @@ const CONST = { QUICK_REACTION: 'MiniContextMenu-QuickReaction', EMOJI_PICKER_BUTTON: 'MiniContextMenu-EmojiPickerButton', }, + TASK: { + PREVIEW_CARD: 'Task-PreviewCard', + PREVIEW_CHECKBOX: 'Task-PreviewCheckbox', + VIEW_TITLE: 'Task-ViewTitle', + VIEW_CHECKBOX: 'Task-ViewCheckbox', + VIEW_DESCRIPTION: 'Task-ViewDescription', + VIEW_ASSIGNEE: 'Task-ViewAssignee', + HEADER_ACTION_BUTTON: 'Task-HeaderActionButton', + }, }, } as const; diff --git a/src/components/MenuItem.tsx b/src/components/MenuItem.tsx index 7d65a8c4294a6..b2fa949596c58 100644 --- a/src/components/MenuItem.tsx +++ b/src/components/MenuItem.tsx @@ -394,6 +394,9 @@ type MenuItemBaseProps = ForwardedFSClassProps & { /** Whether the screen containing the item is focused */ isFocused?: boolean; + + /** Label for Sentry tracking */ + sentryLabel?: string; }; type MenuItemProps = (IconProps | AvatarProps | NoIcon) & MenuItemBaseProps; @@ -522,6 +525,7 @@ function MenuItem({ forwardedFSClass, ref, isFocused, + sentryLabel, }: MenuItemProps) { const theme = useTheme(); const styles = useThemeStyles(); @@ -722,6 +726,7 @@ function MenuItem({ accessibilityLabel={title ? title.toString() : ''} accessible onFocus={onFocus} + sentryLabel={sentryLabel} > {({pressed}) => ( diff --git a/src/components/ReportActionItem/TaskPreview.tsx b/src/components/ReportActionItem/TaskPreview.tsx index 8b3de9cac130e..0f5cbb00c7e12 100644 --- a/src/components/ReportActionItem/TaskPreview.tsx +++ b/src/components/ReportActionItem/TaskPreview.tsx @@ -139,6 +139,7 @@ function TaskPreview({ style={[styles.flexRow, styles.justifyContentBetween, style]} role={CONST.ROLE.BUTTON} accessibilityLabel={translate('task.task')} + sentryLabel={CONST.SENTRY_LABEL.TASK.PREVIEW_CARD} > @@ -154,6 +155,7 @@ function TaskPreview({ } })} accessibilityLabel={translate('task.task')} + sentryLabel={CONST.SENTRY_LABEL.TASK.PREVIEW_CHECKBOX} /> {hasAssignee && ( diff --git a/src/components/ReportActionItem/TaskView.tsx b/src/components/ReportActionItem/TaskView.tsx index 2e98c4b0e44c3..ffcbc0abca996 100644 --- a/src/components/ReportActionItem/TaskView.tsx +++ b/src/components/ReportActionItem/TaskView.tsx @@ -120,6 +120,7 @@ function TaskView({report, parentReport, action}: TaskViewProps) { ]} accessibilityLabel={taskTitle || translate('task.task')} disabled={isDisableInteractive} + sentryLabel={CONST.SENTRY_LABEL.TASK.VIEW_TITLE} > {({pressed}) => ( @@ -144,6 +145,7 @@ function TaskView({report, parentReport, action}: TaskViewProps) { caretSize={16} accessibilityLabel={taskTitle || translate('task.task')} disabled={!isTaskActionable} + sentryLabel={CONST.SENTRY_LABEL.TASK.VIEW_CHECKBOX} /> @@ -176,6 +178,7 @@ function TaskView({report, parentReport, action}: TaskViewProps) { numberOfLinesTitle={0} interactive={!isDisableInteractive} shouldUseDefaultCursorWhenDisabled + sentryLabel={CONST.SENTRY_LABEL.TASK.VIEW_DESCRIPTION} /> @@ -196,6 +199,7 @@ function TaskView({report, parentReport, action}: TaskViewProps) { interactive={!isDisableInteractive} titleWithTooltips={assigneeTooltipDetails} shouldUseDefaultCursorWhenDisabled + sentryLabel={CONST.SENTRY_LABEL.TASK.VIEW_ASSIGNEE} /> ) : ( )} diff --git a/src/components/TaskHeaderActionButton.tsx b/src/components/TaskHeaderActionButton.tsx index a041da910c885..14ffbd440ff6b 100644 --- a/src/components/TaskHeaderActionButton.tsx +++ b/src/components/TaskHeaderActionButton.tsx @@ -11,6 +11,7 @@ import {canWriteInReport, isCompletedTaskReport} from '@libs/ReportUtils'; import {isActiveTaskEditRoute} from '@libs/TaskUtils'; import {callFunctionIfActionIsAllowed} from '@userActions/Session'; import {canActionTask, completeTask, reopenTask} from '@userActions/Task'; +import CONST from '@src/CONST'; import type * as OnyxTypes from '@src/types/onyx'; import Button from './Button'; @@ -51,6 +52,7 @@ function TaskHeaderActionButton({report}: TaskHeaderActionButtonProps) { } })} style={styles.flex1} + sentryLabel={CONST.SENTRY_LABEL.TASK.HEADER_ACTION_BUTTON} /> ); From 27418966f9e49107e8e8b4ee352133148bb91f37 Mon Sep 17 00:00:00 2001 From: Dariusz Biela Date: Fri, 12 Dec 2025 16:23:09 +0100 Subject: [PATCH 4/7] refactor(sentry): Move ClearButton suffix logic from TextInputClearButton to BaseTextInput --- src/components/TextInput/BaseTextInput/implementation/index.tsx | 2 +- src/components/TextInput/TextInputClearButton/index.tsx | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/components/TextInput/BaseTextInput/implementation/index.tsx b/src/components/TextInput/BaseTextInput/implementation/index.tsx index dc5f39a686546..61d107f79e9a2 100644 --- a/src/components/TextInput/BaseTextInput/implementation/index.tsx +++ b/src/components/TextInput/BaseTextInput/implementation/index.tsx @@ -473,7 +473,7 @@ function BaseTextInput({ onClearInput?.(); }} style={[StyleUtils.getTextInputIconContainerStyles(hasLabel, false, verticalPaddingDiff)]} - sentryLabel={sentryLabel} + sentryLabel={sentryLabel ? `${sentryLabel}-ClearButton` : undefined} /> )} diff --git a/src/components/TextInput/TextInputClearButton/index.tsx b/src/components/TextInput/TextInputClearButton/index.tsx index 09828330f9272..26f0f41f3e201 100644 --- a/src/components/TextInput/TextInputClearButton/index.tsx +++ b/src/components/TextInput/TextInputClearButton/index.tsx @@ -30,7 +30,7 @@ function TextInputClearButton({style, onPressButton, sentryLabel}: TextInputClea e.preventDefault(); }} onPress={onPressButton} - sentryLabel={sentryLabel ? `${sentryLabel}-ClearButton` : undefined} + sentryLabel={sentryLabel} > Date: Fri, 12 Dec 2025 16:57:20 +0100 Subject: [PATCH 5/7] fix: fixes prettier error --- src/components/BaseMiniContextMenuItem.tsx | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/src/components/BaseMiniContextMenuItem.tsx b/src/components/BaseMiniContextMenuItem.tsx index ab8873c2d5617..ac83a4d3e5b73 100644 --- a/src/components/BaseMiniContextMenuItem.tsx +++ b/src/components/BaseMiniContextMenuItem.tsx @@ -52,7 +52,15 @@ type BaseMiniContextMenuItemProps = { * Component that renders a mini context menu item with a * pressable. Also renders a tooltip when hovering the item. */ -function BaseMiniContextMenuItem({tooltipText, onPress, children, isDelayButtonStateComplete = true, shouldPreventDefaultFocusOnPress = true, ref, sentryLabel}: BaseMiniContextMenuItemProps) { +function BaseMiniContextMenuItem({ + tooltipText, + onPress, + children, + isDelayButtonStateComplete = true, + shouldPreventDefaultFocusOnPress = true, + ref, + sentryLabel, +}: BaseMiniContextMenuItemProps) { const styles = useThemeStyles(); const StyleUtils = useStyleUtils(); return ( From 3ab4fece219a3b230ea247ddb08d269850398bd0 Mon Sep 17 00:00:00 2001 From: Dariusz Biela Date: Tue, 16 Dec 2025 13:21:28 +0100 Subject: [PATCH 6/7] fix: resolve ESLint errors in EmojiPicker components - Replace deprecated blurOnSubmit with submitBehavior in EmojiPickerMenu - Change namespace import to named imports in EmojiPickerMenuItem --- .../EmojiPicker/EmojiPickerMenu/index.native.tsx | 2 +- src/components/EmojiPicker/EmojiPickerMenu/index.tsx | 2 +- src/components/EmojiPicker/EmojiPickerMenuItem/index.tsx | 8 ++++---- 3 files changed, 6 insertions(+), 6 deletions(-) diff --git a/src/components/EmojiPicker/EmojiPickerMenu/index.native.tsx b/src/components/EmojiPicker/EmojiPickerMenu/index.native.tsx index 349b7e485685e..61d8ab2601a55 100644 --- a/src/components/EmojiPicker/EmojiPickerMenu/index.native.tsx +++ b/src/components/EmojiPicker/EmojiPickerMenu/index.native.tsx @@ -125,7 +125,7 @@ function EmojiPickerMenu({onEmojiSelected, activeEmoji, ref}: EmojiPickerMenuPro accessibilityLabel={translate('common.search')} role={CONST.ROLE.PRESENTATION} onChangeText={filterEmojis} - blurOnSubmit={filteredEmojis.length > 0} + submitBehavior={filteredEmojis.length > 0 ? 'blurAndSubmit' : 'submit'} sentryLabel={CONST.SENTRY_LABEL.EMOJI_PICKER.SEARCH_INPUT} /> diff --git a/src/components/EmojiPicker/EmojiPickerMenu/index.tsx b/src/components/EmojiPicker/EmojiPickerMenu/index.tsx index f8405c8d8d0e0..2be9443606fdc 100755 --- a/src/components/EmojiPicker/EmojiPickerMenu/index.tsx +++ b/src/components/EmojiPicker/EmojiPickerMenu/index.tsx @@ -341,7 +341,7 @@ function EmojiPickerMenu({onEmojiSelected, activeEmoji, ref}: EmojiPickerMenuPro }} onBlur={() => setIsFocused(false)} autoCorrect={false} - blurOnSubmit={filteredEmojis.length > 0} + submitBehavior={filteredEmojis.length > 0 ? 'blurAndSubmit' : 'submit'} sentryLabel={CONST.SENTRY_LABEL.EMOJI_PICKER.SEARCH_INPUT} /> diff --git a/src/components/EmojiPicker/EmojiPickerMenuItem/index.tsx b/src/components/EmojiPicker/EmojiPickerMenuItem/index.tsx index b9901782573f8..2508433d9ed87 100644 --- a/src/components/EmojiPicker/EmojiPickerMenuItem/index.tsx +++ b/src/components/EmojiPicker/EmojiPickerMenuItem/index.tsx @@ -5,7 +5,7 @@ import PressableWithoutFeedback from '@components/Pressable/PressableWithoutFeed import Text from '@components/Text'; import useStyleUtils from '@hooks/useStyleUtils'; import useThemeStyles from '@hooks/useThemeStyles'; -import * as Browser from '@libs/Browser'; +import {isMobile, isMobileChrome} from '@libs/Browser'; import getButtonState from '@libs/getButtonState'; import CONST from '@src/CONST'; import type EmojiPickerMenuItemProps from './types'; @@ -46,8 +46,8 @@ function EmojiPickerMenuItem({ shouldUseAutoHitSlop={false} onPress={() => onPress(emoji)} // In order to prevent haptic feedback, pass empty callback as onLongPress Please refer https://github.com/necolas/react-native-web/issues/2349#issuecomment-1195564240 - onLongPress={Browser.isMobileChrome() ? () => {} : undefined} - onPressOut={Browser.isMobile() ? onHoverOut : undefined} + onLongPress={isMobileChrome() ? () => {} : undefined} + onPressOut={isMobile() ? onHoverOut : undefined} onHoverIn={() => { if (onHoverIn) { onHoverIn(); @@ -69,7 +69,7 @@ function EmojiPickerMenuItem({ }} style={({pressed}) => [ isFocused || isHovered || isHighlighted ? themeStyles.emojiItemHighlighted : {}, - Browser.isMobile() && StyleUtils.getButtonBackgroundColorStyle(getButtonState(false, pressed)), + isMobile() && StyleUtils.getButtonBackgroundColorStyle(getButtonState(false, pressed)), themeStyles.emojiItem, ]} accessibilityLabel={emoji} From 63e80a31c0e0ab12c9a3838ad7872baa1572d33a Mon Sep 17 00:00:00 2001 From: Dariusz Biela Date: Tue, 16 Dec 2025 13:33:38 +0100 Subject: [PATCH 7/7] fix: remove duplicate TASK_ACTION_BUTTON constant after merge --- src/CONST/index.ts | 1 - 1 file changed, 1 deletion(-) diff --git a/src/CONST/index.ts b/src/CONST/index.ts index d4b8e3054f159..b7c633bd94550 100755 --- a/src/CONST/index.ts +++ b/src/CONST/index.ts @@ -7579,7 +7579,6 @@ const CONST = { HEADER_VIEW: { BACK_BUTTON: 'HeaderView-BackButton', DETAILS_BUTTON: 'HeaderView-DetailsButton', - TASK_ACTION_BUTTON: 'HeaderView-TaskActionButton', }, SEARCH: { SEARCH_BUTTON: 'Search-SearchButton',