diff --git a/src/CONST.js b/src/CONST.js index ef02585f6aed..aa98b8b73aa8 100755 --- a/src/CONST.js +++ b/src/CONST.js @@ -455,7 +455,7 @@ const CONST = { EMOJI_FREQUENT_ROW_COUNT: 3, - EMOJI_INVISIBLE_CODEPOINTS: ['fe0f', '200d'], + INVISIBLE_CODEPOINTS: ['fe0f', '200d', '2066'], TOOLTIP_MAX_LINES: 3, @@ -754,7 +754,7 @@ const CONST = { HYPERLINK: /^(?:(?:(?:https?|ftp):\/\/)?)(?:\S+(?::\S*)?@)?(?:(?!(?:10|127)(?:\.\d{1,3}){3})(?!(?:169\.254|192\.168)(?:\.\d{1,3}){2})(?!172\.(?:1[6-9]|2\d|3[0-1])(?:\.\d{1,3}){2})(?:[1-9]\d?|1\d\d|2[01]\d|22[0-3])(?:\.(?:1?\d{1,2}|2[0-4]\d|25[0-5])){2}(?:\.(?:[1-9]\d?|1\d\d|2[0-4]\d|25[0-4]))|(?:(?:[a-z0-9\u00a1-\uffff][a-z0-9\u00a1-\uffff_-]{0,62})?[a-z0-9\u00a1-\uffff]\.)+(?:[a-z\u00a1-\uffff]{2,}\.?))(?::\d{2,5})?(?:[/?#]\S*)?$/i, // eslint-disable-next-line max-len, no-misleading-character-class - EMOJIS: /(?:\uD83D(?:\uDC41\u200D\uD83D\uDDE8|\uDC68\u200D\uD83D[\uDC68\uDC69]\u200D\uD83D(?:\uDC66(?:\u200D\uD83D\uDC66)?|\uDC67(?:\u200D\uD83D[\uDC66\uDC67])?)|\uDC69\u200D\uD83D\uDC69\u200D\uD83D(?:\uDC66(?:\u200D\uD83D\uDC66)?|\uDC67(?:\u200D\uD83D[\uDC66\uDC67])?))|[\u2700-\u27bf]|(?:\ud83c[\udde6-\uddff]){2}|[\ud800-\udbff][\udc00-\udfff]|[\u0023-\u0039]\ufe0f?\u20e3|\u3299|\u3297|\u303d|\u3030|\u24c2|\ud83c[\udd70-\udd71]|\ud83c[\udd7e-\udd7f]|\ud83c\udd8e|\ud83c[\udd91-\udd9a]|\ud83c[\udde6-\uddff]|[\ud83c\ude01-\ude02]|\ud83c\ude1a|\ud83c\ude2f|[\ud83c\ude32-\ude3a]|[\ud83c\ude50-\ude51]|\u203c|\u2049|[\u25aa-\u25ab]|\u25b6|\u25c0|[\u25fb-\u25fe]|\u00a9|\u00ae|\u2122|\u2139|\ud83c\udc04|[\u2600-\u26FF]|\u2b05|\u2b06|\u2b07|\u2b1b|\u2b1c|\u2b50|\u2b55|\u231a|\u231b|\u2328|\u23cf|[\u23e9-\u23f3]|[\u23f8-\u23fa]|\ud83c\udccf|\u2934|\u2935|[\u2190-\u21ff])/g, + EMOJIS: /[\p{Extended_Pictographic}\u200d\u{1f1e6}-\u{1f1ff}\u{1f3fb}-\u{1f3ff}\u{e0020}-\u{e007f}\u20E3\uFE0F]|[#*0-9]\uFE0F?\u20E3/gu, TAX_ID: /^\d{9}$/, NON_NUMERIC: /\D/g, EMOJI_NAME: /:[\w+-]+:/g, diff --git a/src/libs/EmojiUtils.js b/src/libs/EmojiUtils.js index 617c624b2c5b..f06cc76bee18 100644 --- a/src/libs/EmojiUtils.js +++ b/src/libs/EmojiUtils.js @@ -69,7 +69,7 @@ function containsOnlyEmojis(message) { const codes = []; _.map(match, emoji => _.map(getEmojiUnicode(emoji).split(' '), (code) => { - if (!CONST.EMOJI_INVISIBLE_CODEPOINTS.includes(code)) { + if (!CONST.INVISIBLE_CODEPOINTS.includes(code)) { codes.push(code); } return code; @@ -77,7 +77,7 @@ function containsOnlyEmojis(message) { // Emojis are stored as multiple characters, so we're using spread operator // to iterate over the actual emojis, not just characters that compose them - const messageCodes = _.filter(_.map([...trimmedMessage], char => getEmojiUnicode(char)), string => string.length > 0 && !CONST.EMOJI_INVISIBLE_CODEPOINTS.includes(string)); + const messageCodes = _.filter(_.map([...trimmedMessage], char => getEmojiUnicode(char)), string => string.length > 0 && !CONST.INVISIBLE_CODEPOINTS.includes(string)); return codes.length === messageCodes.length; } diff --git a/tests/unit/EmojiTest.js b/tests/unit/EmojiTest.js index 387d716a1f03..43971a2e2580 100644 --- a/tests/unit/EmojiTest.js +++ b/tests/unit/EmojiTest.js @@ -76,6 +76,21 @@ describe('EmojiTest', () => { // Given an input when we check only multiple emojis with additional whitespace, then it should return false expect(EmojiUtils.containsOnlyEmojis('😄 👋')).toBe(true); + + // Given an emoji with an LTR unicode, when we check if it contains only emoji, then it should return true + expect(EmojiUtils.containsOnlyEmojis('\u2066😄')).toBe(true); + }); + + it('will not match for non emoji', () => { + // Given a non-emoji input, when we check if it contains only emoji, then it should return false + expect(EmojiUtils.containsOnlyEmojis('1')).toBe(false); + expect(EmojiUtils.containsOnlyEmojis('a')).toBe(false); + expect(EmojiUtils.containsOnlyEmojis('~')).toBe(false); + expect(EmojiUtils.containsOnlyEmojis('𝕥𝕖𝕤𝕥')).toBe(false); + expect(EmojiUtils.containsOnlyEmojis('𝓣𝓮𝓼𝓽')).toBe(false); + expect(EmojiUtils.containsOnlyEmojis('𝕿𝖊𝖘𝖙')).toBe(false); + expect(EmojiUtils.containsOnlyEmojis('🆃🅴🆂🆃')).toBe(false); + expect(EmojiUtils.containsOnlyEmojis('🅃🄴🅂🅃')).toBe(false); }); it('replaces an emoji code with an emoji and a space', () => {