Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: add rules to recognize user and @here mentions #524

Closed
wants to merge 51 commits into from
Closed
Show file tree
Hide file tree
Changes from 12 commits
Commits
Show all changes
51 commits
Select commit Hold shift + click to select a range
76e8afb
feat: add rules to recognize user and @here mentions
getusha Apr 25, 2023
b919cfb
allow bold, italic, strikethrough, heading1 on mentions
getusha Apr 25, 2023
87466b7
fix wrong </em> placement on italic mention style
getusha Apr 25, 2023
1bd2f9f
add tests for mentions rule
getusha Apr 25, 2023
7f8f66a
rename mentions name from singular
getusha Apr 25, 2023
43431db
update valid user mention meaning comment
getusha Apr 25, 2023
925b29b
update tests to perform the test on current valid user mentions
getusha Apr 25, 2023
905dd4a
update mentions regex to allow only current valid mentions and added …
getusha Apr 25, 2023
0bfaede
add tests for code fence styling
getusha Apr 27, 2023
874a84c
update user mention regex to match only valid login
getusha Apr 27, 2023
43af179
add more tests
getusha Apr 27, 2023
ea1ab1b
fix leading space inside here mention tag
getusha Apr 28, 2023
ea19c7a
fix incompatible regular expression
getusha May 1, 2023
31e2b55
remove unnecessary character from regex
getusha May 1, 2023
afb1d85
Revert "remove unnecessary character from regex"
getusha May 1, 2023
bb12f26
remove unnecessary character from regex
getusha May 1, 2023
13f3505
a function to check if a matched mention has valid preceding styling…
getusha May 1, 2023
bfffc13
fix regex compatibility and improve userMentions
getusha May 1, 2023
b64e339
remove commented test and add more tests
getusha May 1, 2023
cc91439
update tests with new line at the end
getusha May 2, 2023
fa6683f
update comments
getusha May 2, 2023
a19a064
update mistaken value inside a comment
getusha May 2, 2023
e9083fd
use existing email validation regex
getusha May 3, 2023
0f1233c
fix: added protocols to the url along with correct port range
allroundexperts Apr 18, 2023
6159a19
feat: add tests for url validation
allroundexperts Apr 18, 2023
d68bf37
feat: remove SMTP from the allowed protocols
allroundexperts Apr 19, 2023
c1da171
Update URL-test.js
allroundexperts Apr 21, 2023
847f50e
Update URL-test.js
allroundexperts Apr 21, 2023
73436fe
fix: update unit test to include smtp failure
allroundexperts Apr 21, 2023
b39e125
avoid creating empty blockquote tag
eh2077 Apr 20, 2023
d6d0155
improve method name and doc
eh2077 Apr 20, 2023
39cac50
add test cases
eh2077 Apr 24, 2023
15582f8
keep all blank rows inside a quote
eh2077 Apr 24, 2023
03a1275
rename method
eh2077 Apr 25, 2023
19783ca
remove extra trim
eh2077 Apr 25, 2023
feb75c6
Disallow hyphens at start or end of domains
jjcoffee Apr 25, 2023
eb69c97
Add tests for start and end hyphen for URL regex
jjcoffee Apr 25, 2023
f9811d3
allow heading inside a quote
eh2077 Apr 25, 2023
4be959f
remove commemt line
eh2077 Apr 25, 2023
01523cb
fix case of having two continous headers
eh2077 Apr 27, 2023
8b8aa9c
format code
eh2077 May 1, 2023
9b327c2
fix code format
eh2077 May 3, 2023
b1d7ca9
Link to new sync manager file in Const
puneetlath May 3, 2023
147b7e0
Add sync manager version const
puneetlath May 3, 2023
2446473
fix: regex of italic
dukenv0307 May 3, 2023
8c1b102
fix: add UTs
dukenv0307 May 3, 2023
93187e8
fix: remove redundant
dukenv0307 May 3, 2023
73ffa03
fix: lint
dukenv0307 May 4, 2023
b42ed3a
fix: remove captured group redundant
dukenv0307 May 5, 2023
e1c8d70
Merge remote-tracking branch 'expensify/main' into recognize-mentions
getusha May 9, 2023
853cc5e
add tests
getusha May 9, 2023
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
158 changes: 158 additions & 0 deletions __tests__/ExpensiMark-HTML-test.js
Original file line number Diff line number Diff line change
Expand Up @@ -664,3 +664,161 @@ test('Test for link with no content', () => {
const resultString = '[ ](<a href="https://www.link.com" target="_blank" rel="noreferrer noopener">www.link.com</a>)';
expect(parser.replace(testString)).toBe(resultString);
});

// Valid text that should match for user mentions
test('Test for user mention with @[email protected]', () => {
const testString = '@[email protected]';
const resultString = '<mention-user>@[email protected]</mention-user>';
expect(parser.replace(testString)).toBe(resultString);
});

test('Test for user mention with @[email protected]', () => {
const testString = '@[email protected]';
const resultString = '<mention-user>@[email protected]</mention-user>';
expect(parser.replace(testString)).toBe(resultString);
});

test('Test for user mention with bold style', () => {
const testString = '*@[email protected]*';
const resultString = '<strong><mention-user>@[email protected]</mention-user></strong>';
expect(parser.replace(testString)).toBe(resultString);
});

test('Test for user mention with italic style', () => {
const testString = '_@[email protected]_';
const resultString = '<em><mention-user>@[email protected]</mention-user></em>';
expect(parser.replace(testString)).toBe(resultString);
});

test('Test for user mention with heading1 style', () => {
const testString = '# @[email protected]';
const resultString = '<h1><mention-user>@[email protected]</mention-user></h1>';
expect(parser.replace(testString)).toBe(resultString);
});

test('Test for user mention with strikethrough style', () => {
getusha marked this conversation as resolved.
Show resolved Hide resolved
const testString = '~@[email protected]~';
const resultString = '<del><mention-user>@[email protected]</mention-user></del>';
expect(parser.replace(testString)).toBe(resultString);
});

test('Test for user mention with @here', () => {
const testString = '@here say hello to @[email protected]';
const resultString = '<mention-here>@here</mention-here> say hello to <mention-user>@[email protected]</mention-user>';
expect(parser.replace(testString)).toBe(resultString);
});

/**
getusha marked this conversation as resolved.
Show resolved Hide resolved
* Uncomment this tests if @username became supported for user mention
*
test('Test for user mention with single username', () => {
const testString = '@username';
const resultString = '<mention-user>@username</mention-user>';
expect(parser.replace(testString)).toBe(resultString);
});

test('Test for user mention with bold style', () => {
const testString = '*@username*';
const resultString = '<strong><mention-user>@username</mention-user></strong>';
expect(parser.replace(testString)).toBe(resultString);
});

test('Test for user mention with italic style', () => {
const testString = '_@username_';
const resultString = '<em><mention-user>@username</mention-user></em>';
expect(parser.replace(testString)).toBe(resultString);
});

test('Test for user mention with heading1 style', () => {
const testString = '# @username';
const resultString = '<h1><mention-user>@username</mention-user></h1>';
expect(parser.replace(testString)).toBe(resultString);
});

test('Test for user mention with strikethrough style', () => {
const testString = '~@username~';
const resultString = '<del><mention-user>@username</mention-user></del>';
expect(parser.replace(testString)).toBe(resultString);
});
*/

// Invalid text should not match for user mentions:
test('Test for user mention without leading whitespace', () => {
getusha marked this conversation as resolved.
Show resolved Hide resolved
const testString = 'hi...@[email protected]';
getusha marked this conversation as resolved.
Show resolved Hide resolved
const resultString = 'hi...@<a href=\"mailto:[email protected]\">[email protected]</a>';
expect(parser.replace(testString)).toBe(resultString);
});

test('Test for user mention with @username@expensify', () => {
const testString = '@username@expensify';
const resultString = '@username@expensify';
expect(parser.replace(testString)).toBe(resultString);
});

test('Test for user mention with valid email in the middle of a word', () => {
const testString = 'hello [email protected] is my email';
const resultString = 'hello <a href=\"mailto:[email protected]\">[email protected]</a> is my email';
expect(parser.replace(testString)).toBe(resultString);
});

test('Test for user mention with invalid username', () => {
const testString = '@ +19728974297 hey';
const resultString = '@ +19728974297 hey';
expect(parser.replace(testString)).toBe(resultString);
});

test('Test for user mention with codefence style', () => {
const testString = '```@[email protected]```';
const resultString = '<pre>@[email protected]</pre>';
expect(parser.replace(testString)).toBe(resultString);
});

test('Test for user mention with inlineCodeBlock style', () => {
const testString = '`@[email protected]`';
const resultString = '<code>@[email protected]</code>';
expect(parser.replace(testString)).toBe(resultString);
});

test('Test for @here mention with codefence style', () => {
const testString = '```@here```';
const resultString = '<pre>@here</pre>';
expect(parser.replace(testString)).toBe(resultString);
});

test('Test for @here mention with inlineCodeBlock style', () => {
const testString = '`@here`';
const resultString = '<code>@here</code>';
expect(parser.replace(testString)).toBe(resultString);
});

// Examples that should match for here mentions:
test('Test for here mention with @here', () => {
const testString = '@here';
const resultString = '<mention-here>@here</mention-here>';
expect(parser.replace(testString)).toBe(resultString);
});

test('Test for here mention with leading word and space', () => {
const testString = 'hi all @here';
const resultString = 'hi all <mention-here>@here</mention-here>';
expect(parser.replace(testString)).toBe(resultString);
});

test('Test for here mention with @here in the middle of a word', () => {
const testString = '@here how are you guys?';
const resultString = '<mention-here>@here</mention-here> how are you guys?';
expect(parser.replace(testString)).toBe(resultString);
});

// Examples that should not match for here mentions:
test('Test for here mention without leading whitespace', () => {
const testString = 'hi...@here';
const resultString = 'hi...@here';
expect(parser.replace(testString)).toBe(resultString);
});

test('Test for here mention with invalid username', () => {
const testString = '@ here hey';
const resultString = '@ here hey';
expect(parser.replace(testString)).toBe(resultString);
});
32 changes: 32 additions & 0 deletions lib/ExpensiMark.js
Original file line number Diff line number Diff line change
Expand Up @@ -49,6 +49,38 @@ export default class ExpensiMark {
replacement: '$1<code>$2</code>$3',
},

/**
* Apply the hereMention first because the string @here is still a valid mention for the userMention regex.
* This ensures that the hereMention is always considered first, even if it is followed by a valid userMention.
*/
{
name: 'hereMentions',
regex: /(?<![^\s]+)@here\b/g,
replacement: match => `<mention-here>${match}</mention-here>`,
},

/**
* This regex matches a valid user mention in a string.
* A user mention is a string that starts with the '@' symbol and is followed by a valid user's primary login
* The username can contain any combination of letters, numbers, periods, underscores, and hyphens
*
* Note: currently we are only allowing mentions in a format of @[email protected] and @[email protected]
getusha marked this conversation as resolved.
Show resolved Hide resolved
* inorder to match mentions in a format of @username we should update the regex to: /(?!@here)(?<![^_~#*\s]+)@([\w.@+-]+(?:\.[\w@+-]+)*\b)/g
*/
{
// (?<![^~#*-]+) excludes every mention with a character infront except ~, #, * and +
// this is to allow bold, italic, strikethrough, quote, heading1 on a mention
name: 'userMentions',
regex: /(?!@here)(?<![^_~#*\s]+)@([\w.@+-]+@+\w+[.]+\w+(?:\.[\w@+-]+)*\b)/g,
getusha marked this conversation as resolved.
Show resolved Hide resolved
replacement: (match) => {
if (match[match.length - 1] === '_') {
hayata-suenaga marked this conversation as resolved.
Show resolved Hide resolved
const mention = match.substring(0, match.length - 1);
return `<mention-user>${mention}</mention-user>_`;
getusha marked this conversation as resolved.
Show resolved Hide resolved
}
return `<mention-user>${match}</mention-user>`;
}
},

/**
* Converts markdown style links to anchor tags e.g. [Expensify]([email protected])
* We need to convert before the auto email link rule and the manual link rule since it will not try to create a link
Expand Down