From d6eca15fe76de9c0bba2c66fcfb135a1c18c89b6 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Lucas=20M=C3=B3rawski?= Date: Fri, 15 Sep 2023 16:54:27 +0200 Subject: [PATCH 01/12] displayName fallback to Hidden --- src/libs/ReportUtils.js | 3 +++ 1 file changed, 3 insertions(+) diff --git a/src/libs/ReportUtils.js b/src/libs/ReportUtils.js index f24959c4bac2..df030ddd3756 100644 --- a/src/libs/ReportUtils.js +++ b/src/libs/ReportUtils.js @@ -1103,6 +1103,9 @@ function getDisplayNameForParticipant(accountID, shouldUseShortForm = false) { const personalDetails = getPersonalDetailsForAccountID(accountID); const longName = personalDetails.displayName; const shortName = personalDetails.firstName || longName; + if (!longName && !personalDetails.login) { + return Localize.translateLocal('common.hidden'); + } return shouldUseShortForm ? shortName : longName; } From cbd28d3758af5d28b0787a9799aa8683eb3a0757 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Lucas=20M=C3=B3rawski?= Date: Mon, 25 Sep 2023 12:43:07 +0200 Subject: [PATCH 02/12] fix/search list shows hidden for unkown yet contact --- src/components/OptionRow.js | 1 + src/libs/ReportUtils.js | 10 ++++++---- 2 files changed, 7 insertions(+), 4 deletions(-) diff --git a/src/components/OptionRow.js b/src/components/OptionRow.js index a07510f7603d..2644feaccb58 100644 --- a/src/components/OptionRow.js +++ b/src/components/OptionRow.js @@ -162,6 +162,7 @@ class OptionRow extends Component { const displayNamesWithTooltips = ReportUtils.getDisplayNamesWithTooltips( (this.props.option.participantsList || (this.props.option.accountID ? [this.props.option] : [])).slice(0, 10), isMultipleParticipant, + true, ); let subscriptColor = themeColors.appBG; if (this.props.optionIsFocused) { diff --git a/src/libs/ReportUtils.js b/src/libs/ReportUtils.js index df030ddd3756..6d2e99dbd4f4 100644 --- a/src/libs/ReportUtils.js +++ b/src/libs/ReportUtils.js @@ -1094,16 +1094,17 @@ function getPersonalDetailsForAccountID(accountID) { * * @param {Number} accountID * @param {Boolean} [shouldUseShortForm] + * @param {Boolean} shouldNotFallbackToHidden * @returns {String} */ -function getDisplayNameForParticipant(accountID, shouldUseShortForm = false) { +function getDisplayNameForParticipant(accountID, shouldUseShortForm = false, shouldNotFallbackToHidden = false) { if (!accountID) { return ''; } const personalDetails = getPersonalDetailsForAccountID(accountID); const longName = personalDetails.displayName; const shortName = personalDetails.firstName || longName; - if (!longName && !personalDetails.login) { + if (!longName && !personalDetails.login && !shouldNotFallbackToHidden) { return Localize.translateLocal('common.hidden'); } return shouldUseShortForm ? shortName : longName; @@ -1112,12 +1113,13 @@ function getDisplayNameForParticipant(accountID, shouldUseShortForm = false) { /** * @param {Object} personalDetailsList * @param {Boolean} isMultipleParticipantReport + * @param {Boolean} shouldNotFallbackToHidden * @returns {Array} */ -function getDisplayNamesWithTooltips(personalDetailsList, isMultipleParticipantReport) { +function getDisplayNamesWithTooltips(personalDetailsList, isMultipleParticipantReport, shouldNotFallbackToHidden) { return _.map(personalDetailsList, (user) => { const accountID = Number(user.accountID); - const displayName = getDisplayNameForParticipant(accountID, isMultipleParticipantReport) || user.login || ''; + const displayName = getDisplayNameForParticipant(accountID, isMultipleParticipantReport, shouldNotFallbackToHidden) || user.login || ''; const avatar = UserUtils.getDefaultAvatar(accountID); let pronouns = user.pronouns; From 02c07aa736b7b5b2fba8edb9034f5cae7b59daba Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Lucas=20M=C3=B3rawski?= Date: Wed, 27 Sep 2023 16:56:45 +0200 Subject: [PATCH 03/12] more fixes --- src/components/OptionRow.js | 1 - src/libs/OptionsListUtils.js | 5 +++-- src/libs/ReportUtils.js | 9 +++++++++ 3 files changed, 12 insertions(+), 3 deletions(-) diff --git a/src/components/OptionRow.js b/src/components/OptionRow.js index 2644feaccb58..a07510f7603d 100644 --- a/src/components/OptionRow.js +++ b/src/components/OptionRow.js @@ -162,7 +162,6 @@ class OptionRow extends Component { const displayNamesWithTooltips = ReportUtils.getDisplayNamesWithTooltips( (this.props.option.participantsList || (this.props.option.accountID ? [this.props.option] : [])).slice(0, 10), isMultipleParticipant, - true, ); let subscriptColor = themeColors.appBG; if (this.props.optionIsFocused) { diff --git a/src/libs/OptionsListUtils.js b/src/libs/OptionsListUtils.js index 7629a1acc0a6..12b820a5ba60 100644 --- a/src/libs/OptionsListUtils.js +++ b/src/libs/OptionsListUtils.js @@ -430,7 +430,7 @@ function getLastMessageTextForReport(report) { * @param {Boolean} [options.forcePolicyNamePreview] * @returns {Object} */ -function createOption(accountIDs, personalDetails, report, reportActions = {}, {showChatPreviewLine = false, forcePolicyNamePreview = false}) { +function createOption(accountIDs, personalDetails, report, reportActions = {}, {showChatPreviewLine = false, forcePolicyNamePreview = false, shouldNotFallbackToHidden = false}) { const result = { text: null, alternateText: null, @@ -528,7 +528,7 @@ function createOption(accountIDs, personalDetails, report, reportActions = {}, { } reportName = ReportUtils.getReportName(report); } else { - reportName = ReportUtils.getDisplayNameForParticipant(accountIDs[0]); + reportName = ReportUtils.getDisplayNameForParticipant(accountIDs[0], false, shouldNotFallbackToHidden); result.keyForList = String(accountIDs[0]); result.alternateText = LocalePhoneNumber.formatPhoneNumber(lodashGet(personalDetails, [accountIDs[0], 'login'], '')); } @@ -998,6 +998,7 @@ function getOptions( }; userToInvite = createOption([optimisticAccountID], personalDetailsExtended, null, reportActions, { showChatPreviewLine, + shouldNotFallbackToHidden: true, }); userToInvite.isOptimisticAccount = true; userToInvite.login = searchValue; diff --git a/src/libs/ReportUtils.js b/src/libs/ReportUtils.js index 6d2e99dbd4f4..0d04dcd5c031 100644 --- a/src/libs/ReportUtils.js +++ b/src/libs/ReportUtils.js @@ -1089,6 +1089,11 @@ function getPersonalDetailsForAccountID(accountID) { ); } +function hasOnlyAvatarField(obj) { + const keys = _.keys(obj); + return keys.length === 1 && keys[0] === 'avatar'; +} + /** * Get the displayName for a single report participant. * @@ -1102,6 +1107,10 @@ function getDisplayNameForParticipant(accountID, shouldUseShortForm = false, sho return ''; } const personalDetails = getPersonalDetailsForAccountID(accountID); + // check if it's invite account + if (hasOnlyAvatarField(personalDetails)) { + return ''; + } const longName = personalDetails.displayName; const shortName = personalDetails.firstName || longName; if (!longName && !personalDetails.login && !shouldNotFallbackToHidden) { From b663bb6a956bdc63917dc8b753a3586be7fe3822 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Lucas=20M=C3=B3rawski?= Date: Wed, 4 Oct 2023 10:13:23 +0200 Subject: [PATCH 04/12] small refactors --- src/libs/OptionsListUtils.js | 4 ++-- src/libs/ReportUtils.js | 25 ++++++++++++++++--------- 2 files changed, 18 insertions(+), 11 deletions(-) diff --git a/src/libs/OptionsListUtils.js b/src/libs/OptionsListUtils.js index 12b820a5ba60..cac758162ddd 100644 --- a/src/libs/OptionsListUtils.js +++ b/src/libs/OptionsListUtils.js @@ -430,7 +430,7 @@ function getLastMessageTextForReport(report) { * @param {Boolean} [options.forcePolicyNamePreview] * @returns {Object} */ -function createOption(accountIDs, personalDetails, report, reportActions = {}, {showChatPreviewLine = false, forcePolicyNamePreview = false, shouldNotFallbackToHidden = false}) { +function createOption(accountIDs, personalDetails, report, reportActions = {}, {showChatPreviewLine = false, forcePolicyNamePreview = false, shouldFallbackToHidden = true}) { const result = { text: null, alternateText: null, @@ -528,7 +528,7 @@ function createOption(accountIDs, personalDetails, report, reportActions = {}, { } reportName = ReportUtils.getReportName(report); } else { - reportName = ReportUtils.getDisplayNameForParticipant(accountIDs[0], false, shouldNotFallbackToHidden); + reportName = ReportUtils.getDisplayNameForParticipant(accountIDs[0], false, shouldFallbackToHidden); result.keyForList = String(accountIDs[0]); result.alternateText = LocalePhoneNumber.formatPhoneNumber(lodashGet(personalDetails, [accountIDs[0], 'login'], '')); } diff --git a/src/libs/ReportUtils.js b/src/libs/ReportUtils.js index 0d04dcd5c031..40fac8ae163f 100644 --- a/src/libs/ReportUtils.js +++ b/src/libs/ReportUtils.js @@ -1089,8 +1089,15 @@ function getPersonalDetailsForAccountID(accountID) { ); } -function hasOnlyAvatarField(obj) { - const keys = _.keys(obj); +/** + * Checks if the personalDetailsObject has only one key named `avatar` and returns a bool flag. + * This can be used to check if the user account is an "invite" one - is not a Expensify account yet. + * + * @param {Object} personalDetailsObject + * @returns {Boolean} + */ +function hasOnlyAvatarField(personalDetailsObject) { + const keys = _.keys(personalDetailsObject); return keys.length === 1 && keys[0] === 'avatar'; } @@ -1099,21 +1106,21 @@ function hasOnlyAvatarField(obj) { * * @param {Number} accountID * @param {Boolean} [shouldUseShortForm] - * @param {Boolean} shouldNotFallbackToHidden + * @param {Boolean} shouldFallbackToHidden * @returns {String} */ -function getDisplayNameForParticipant(accountID, shouldUseShortForm = false, shouldNotFallbackToHidden = false) { +function getDisplayNameForParticipant(accountID, shouldUseShortForm = false, shouldFallbackToHidden = true) { if (!accountID) { return ''; } const personalDetails = getPersonalDetailsForAccountID(accountID); - // check if it's invite account + // check if it's an invite account if (hasOnlyAvatarField(personalDetails)) { return ''; } const longName = personalDetails.displayName; const shortName = personalDetails.firstName || longName; - if (!longName && !personalDetails.login && !shouldNotFallbackToHidden) { + if (!longName && !personalDetails.login && shouldFallbackToHidden) { return Localize.translateLocal('common.hidden'); } return shouldUseShortForm ? shortName : longName; @@ -1122,13 +1129,13 @@ function getDisplayNameForParticipant(accountID, shouldUseShortForm = false, sho /** * @param {Object} personalDetailsList * @param {Boolean} isMultipleParticipantReport - * @param {Boolean} shouldNotFallbackToHidden + * @param {Boolean} shouldFallbackToHidden * @returns {Array} */ -function getDisplayNamesWithTooltips(personalDetailsList, isMultipleParticipantReport, shouldNotFallbackToHidden) { +function getDisplayNamesWithTooltips(personalDetailsList, isMultipleParticipantReport, shouldFallbackToHidden) { return _.map(personalDetailsList, (user) => { const accountID = Number(user.accountID); - const displayName = getDisplayNameForParticipant(accountID, isMultipleParticipantReport, shouldNotFallbackToHidden) || user.login || ''; + const displayName = getDisplayNameForParticipant(accountID, isMultipleParticipantReport, shouldFallbackToHidden) || user.login || ''; const avatar = UserUtils.getDefaultAvatar(accountID); let pronouns = user.pronouns; From 7d65a15338be07f813c97925eb41c731d3cc7421 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Lucas=20M=C3=B3rawski?= Date: Tue, 10 Oct 2023 16:53:00 +0200 Subject: [PATCH 05/12] iou display name for report action item when hidden --- src/pages/home/report/ReportActionItemSingle.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/pages/home/report/ReportActionItemSingle.js b/src/pages/home/report/ReportActionItemSingle.js index 60de11bdf218..3e8eab26f4b6 100644 --- a/src/pages/home/report/ReportActionItemSingle.js +++ b/src/pages/home/report/ReportActionItemSingle.js @@ -112,12 +112,12 @@ function ReportActionItemSingle(props) { // If this is a report preview, display names and avatars of both people involved let secondaryAvatar = {}; - const primaryDisplayName = displayName; + const primaryDisplayName = ReportUtils.getDisplayNameForParticipant(actorAccountID); if (displayAllActors) { // The ownerAccountID and actorAccountID can be the same if the a user requests money back from the IOU's original creator, in that case we need to use managerID to avoid displaying the same user twice const secondaryAccountId = props.iouReport.ownerAccountID === actorAccountID ? props.iouReport.managerID : props.iouReport.ownerAccountID; const secondaryUserDetails = props.personalDetailsList[secondaryAccountId] || {}; - const secondaryDisplayName = lodashGet(secondaryUserDetails, 'displayName', ''); + const secondaryDisplayName = ReportUtils.getDisplayNameForParticipant(secondaryAccountId); displayName = `${primaryDisplayName} & ${secondaryDisplayName}`; secondaryAvatar = { source: UserUtils.getAvatar(secondaryUserDetails.avatar, secondaryAccountId), From 3db91a2cf9f824c106700b660edf3739595b44d5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Lucas=20M=C3=B3rawski?= Date: Tue, 10 Oct 2023 17:20:08 +0200 Subject: [PATCH 06/12] fix/dont allow users without login to split payment/money request --- src/pages/iou/steps/MoneyRequestConfirmPage.js | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-) diff --git a/src/pages/iou/steps/MoneyRequestConfirmPage.js b/src/pages/iou/steps/MoneyRequestConfirmPage.js index 3881221d5c52..865025deddfe 100644 --- a/src/pages/iou/steps/MoneyRequestConfirmPage.js +++ b/src/pages/iou/steps/MoneyRequestConfirmPage.js @@ -69,10 +69,13 @@ function MoneyRequestConfirmPage(props) { const reportID = useRef(lodashGet(props.route, 'params.reportID', '')); const participants = useMemo( () => - _.map(props.iou.participants, (participant) => { - const isPolicyExpenseChat = lodashGet(participant, 'isPolicyExpenseChat', false); - return isPolicyExpenseChat ? OptionsListUtils.getPolicyExpenseReportOption(participant) : OptionsListUtils.getParticipantsOption(participant, props.personalDetails); - }), + _.chain(props.iou.participants) + .map((participant) => { + const isPolicyExpenseChat = lodashGet(participant, 'isPolicyExpenseChat', false); + return isPolicyExpenseChat ? OptionsListUtils.getPolicyExpenseReportOption(participant) : OptionsListUtils.getParticipantsOption(participant, props.personalDetails); + }) + .filter((participant) => !!participant.login) + .value(), [props.iou.participants, props.personalDetails], ); const isManualRequestDM = props.selectedTab === CONST.TAB.MANUAL && iouType.current === CONST.IOU.MONEY_REQUEST_TYPE.REQUEST; From 3b2da52e01cea3974cde6dd5eb39c5e64375b55c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Lucas=20M=C3=B3rawski?= Date: Tue, 10 Oct 2023 17:24:15 +0200 Subject: [PATCH 07/12] dont show participants time when there's no display name --- src/pages/home/report/ParticipantLocalTime.js | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/src/pages/home/report/ParticipantLocalTime.js b/src/pages/home/report/ParticipantLocalTime.js index 058346287b11..2e000c2de1d3 100644 --- a/src/pages/home/report/ParticipantLocalTime.js +++ b/src/pages/home/report/ParticipantLocalTime.js @@ -45,6 +45,10 @@ function ParticipantLocalTime(props) { const reportRecipientDisplayName = lodashGet(props, 'participant.firstName') || lodashGet(props, 'participant.displayName'); + if (!reportRecipientDisplayName) { + return null; + } + return ( Date: Tue, 10 Oct 2023 17:44:22 +0200 Subject: [PATCH 08/12] linting --- src/libs/ReportUtils.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/libs/ReportUtils.js b/src/libs/ReportUtils.js index 197d6b5db6fd..c359be40211a 100644 --- a/src/libs/ReportUtils.js +++ b/src/libs/ReportUtils.js @@ -1212,7 +1212,7 @@ function getDisplayNameForParticipant(accountID, shouldUseShortForm = false, sho * @returns {Array} */ function getDisplayNamesWithTooltips(personalDetailsList, isMultipleParticipantReport, shouldFallbackToHidden) { - return _.map(personalDetailsList, (user) => { + return _.map(personalDetailsList, (user) => { const accountID = Number(user.accountID); const displayName = getDisplayNameForParticipant(accountID, isMultipleParticipantReport, shouldFallbackToHidden) || user.login || ''; const avatar = UserUtils.getDefaultAvatar(accountID); From d9fa89e616fc737f18052e91a8feee85720f381f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Lucas=20M=C3=B3rawski?= Date: Tue, 17 Oct 2023 17:48:38 +0200 Subject: [PATCH 09/12] removed shouldFallbackToHidden flag from createOption method --- src/libs/OptionsListUtils.js | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/src/libs/OptionsListUtils.js b/src/libs/OptionsListUtils.js index 9b6167252561..85907c66eb29 100644 --- a/src/libs/OptionsListUtils.js +++ b/src/libs/OptionsListUtils.js @@ -441,7 +441,7 @@ function getLastMessageTextForReport(report) { * @param {Boolean} [options.forcePolicyNamePreview] * @returns {Object} */ -function createOption(accountIDs, personalDetails, report, reportActions = {}, {showChatPreviewLine = false, forcePolicyNamePreview = false, shouldFallbackToHidden = true}) { +function createOption(accountIDs, personalDetails, report, reportActions = {}, {showChatPreviewLine = false, forcePolicyNamePreview = false}) { const result = { text: null, alternateText: null, @@ -540,7 +540,7 @@ function createOption(accountIDs, personalDetails, report, reportActions = {}, { } reportName = ReportUtils.getReportName(report); } else { - reportName = ReportUtils.getDisplayNameForParticipant(accountIDs[0], false, shouldFallbackToHidden); + reportName = ReportUtils.getDisplayNameForParticipant(accountIDs[0], false); result.keyForList = String(accountIDs[0]); result.alternateText = LocalePhoneNumber.formatPhoneNumber(lodashGet(personalDetails, [accountIDs[0], 'login'], '')); } @@ -1215,7 +1215,6 @@ function getOptions( }; userToInvite = createOption([optimisticAccountID], personalDetailsExtended, null, reportActions, { showChatPreviewLine, - shouldNotFallbackToHidden: true, }); userToInvite.isOptimisticAccount = true; userToInvite.login = searchValue; From ad942f692d203ca9b4da76f17710346eb59efbde Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Lucas=20M=C3=B3rawski?= Date: Tue, 17 Oct 2023 17:49:02 +0200 Subject: [PATCH 10/12] refactored check for invite account --- src/libs/ReportUtils.js | 15 ++------------- 1 file changed, 2 insertions(+), 13 deletions(-) diff --git a/src/libs/ReportUtils.js b/src/libs/ReportUtils.js index c359be40211a..1389fb4b2cc3 100644 --- a/src/libs/ReportUtils.js +++ b/src/libs/ReportUtils.js @@ -1164,22 +1164,11 @@ function getPersonalDetailsForAccountID(accountID) { return ( (allPersonalDetails && allPersonalDetails[accountID]) || { avatar: UserUtils.getDefaultAvatar(accountID), + isOptimisticPersonalDetail: true, } ); } -/** - * Checks if the personalDetailsObject has only one key named `avatar` and returns a bool flag. - * This can be used to check if the user account is an "invite" one - is not a Expensify account yet. - * - * @param {Object} personalDetailsObject - * @returns {Boolean} - */ -function hasOnlyAvatarField(personalDetailsObject) { - const keys = _.keys(personalDetailsObject); - return keys.length === 1 && keys[0] === 'avatar'; -} - /** * Get the displayName for a single report participant. * @@ -1194,7 +1183,7 @@ function getDisplayNameForParticipant(accountID, shouldUseShortForm = false, sho } const personalDetails = getPersonalDetailsForAccountID(accountID); // check if it's an invite account - if (hasOnlyAvatarField(personalDetails)) { + if (lodashGet(personalDetails, 'isOptimisticPersonalDetail') === true) { return ''; } const longName = personalDetails.displayName; From a3f64d6932361a86f45f4056371f0aa4cf577ac1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Lucas=20M=C3=B3rawski?= Date: Wed, 18 Oct 2023 12:46:47 +0200 Subject: [PATCH 11/12] commment update --- src/libs/ReportUtils.js | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/libs/ReportUtils.js b/src/libs/ReportUtils.js index 1389fb4b2cc3..dcd8b269d08b 100644 --- a/src/libs/ReportUtils.js +++ b/src/libs/ReportUtils.js @@ -1182,7 +1182,9 @@ function getDisplayNameForParticipant(accountID, shouldUseShortForm = false, sho return ''; } const personalDetails = getPersonalDetailsForAccountID(accountID); - // check if it's an invite account + // this is to check if account is an invite/optimistically created one + // and prevent from falling back to 'Hidden', so a correct value is shown + // when searching for a new user if (lodashGet(personalDetails, 'isOptimisticPersonalDetail') === true) { return ''; } From 20d20dc51ca023dde5f0142667c6456920f9a1fe Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Lucas=20M=C3=B3rawski?= Date: Thu, 19 Oct 2023 18:05:05 +0200 Subject: [PATCH 12/12] getDisplayNameForParticipant optimistic personal details improvements --- src/libs/ReportUtils.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/libs/ReportUtils.js b/src/libs/ReportUtils.js index d176f1130344..fab8b4418895 100644 --- a/src/libs/ReportUtils.js +++ b/src/libs/ReportUtils.js @@ -1186,7 +1186,7 @@ function getDisplayNameForParticipant(accountID, shouldUseShortForm = false, sho // and prevent from falling back to 'Hidden', so a correct value is shown // when searching for a new user if (lodashGet(personalDetails, 'isOptimisticPersonalDetail') === true) { - return ''; + return personalDetails.login || ''; } const longName = personalDetails.displayName; const shortName = personalDetails.firstName || longName;