nodebb-plugin-mentions 4.6.4 → 4.6.6

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/library.js CHANGED
@@ -36,7 +36,6 @@ const parts = {
36
36
  };
37
37
  const regex = RegExp(`${parts.before}${parts.main}`, 'gu');
38
38
  const isLatinMention = /@[\w\d\-_.@]+$/;
39
- const anchorRegex = /<a.*?href=['"](.+?)['"].*?>(.*?)<\/a>/ig;
40
39
 
41
40
  const Mentions = module.exports;
42
41
 
@@ -356,38 +355,7 @@ async function getMatches(content, isMarkdown = false) {
356
355
  }
357
356
  });
358
357
 
359
- // Early return
360
- if (isMarkdown) {
361
- return { splitContent, matches, urlMap: new Map() };
362
- }
363
-
364
- // Find matches via backreferenced href
365
- const joined = splitContent.join('');
366
- const anchors = new Set(joined.matchAll(anchorRegex));
367
- const urlMap = new Map();
368
- const urls = new Set();
369
- if (!isMarkdown && anchors.size) {
370
- anchors.forEach((match) => {
371
- const [, url] = match;
372
- urls.add(url);
373
- });
374
-
375
- // Filter out urls that don't backreference to a remote id
376
- const backrefs = urls.size ? await db.getObjectFields('remoteUrl:uid', Array.from(urls)) : {};
377
- const urlAsIdExists = await db.isSortedSetMembers('usersRemote:lastCrawled', Array.from(urls));
378
- Array.from(urls).map(async (url, index) => {
379
- if (backrefs[url] || urlAsIdExists[index]) {
380
- urlMap.set(url, backrefs[url] || url);
381
- }
382
- });
383
- let slugs = await User.getUsersFields(Array.from(urlMap.values()), ['userslug']);
384
- slugs = slugs.map(({ userslug }) => userslug);
385
- Array.from(urlMap.keys()).forEach((url, idx) => {
386
- urlMap.set(url, `/user/${encodeURIComponent(slugs[idx])}`);
387
- });
388
- }
389
-
390
- return { splitContent, matches, urlMap };
358
+ return { splitContent, matches };
391
359
  }
392
360
 
393
361
  Mentions.getMatches = async (content) => {
@@ -416,9 +384,9 @@ Mentions.parseRaw = async (content, type = 'default') => {
416
384
  }
417
385
 
418
386
  // Note: Mentions.clean explicitly can't be called here because I need the content unstripped
419
- let { splitContent, matches, urlMap } = await getMatches(content);
387
+ let { splitContent, matches } = await getMatches(content);
420
388
 
421
- if (!matches.length && !urlMap.size) {
389
+ if (!matches.length) {
422
390
  return content;
423
391
  }
424
392
 
@@ -436,19 +404,23 @@ Mentions.parseRaw = async (content, type = 'default') => {
436
404
  await Promise.all(matches.map(async (match) => {
437
405
  const slug = slugify(match.slice(1));
438
406
  match = removePunctuationSuffix(match);
407
+ let cid = 0;
408
+ let groupExists = 0;
439
409
  const uid = await User.getUidByUserslug(slug);
440
- const cid = await categories.getCidByHandle(slug);
441
- const { groupExists, user, category } = await utils.promiseParallel({
442
- groupExists: Groups.existsBySlug(slug),
443
- user: User.getUserFields(uid, ['uid', 'username', 'userslug', 'fullname', 'url']),
444
- category: categories.getCategoryFields(cid, ['slug']),
445
- });
410
+ if (!uid) {
411
+ ({ groupExists, cid } = await utils.promiseParallel({
412
+ groupExists: Groups.existsBySlug(slug),
413
+ cid: categories.getCidByHandle(slug),
414
+ }));
415
+ }
446
416
 
447
417
  if (uid || groupExists || cid) {
448
418
  let url;
449
-
419
+ let user;
420
+ let mentionType = 'user';
450
421
  switch (true) {
451
422
  case !!uid: {
423
+ user = await User.getUserFields(uid, ['uid', 'username', 'userslug', 'fullname', 'url']);
452
424
  url = `/user/${encodeURIComponent(user.userslug)}`;
453
425
  if (type.startsWith('activitypub') && !utils.isNumber(uid)) {
454
426
  url = user.url || user.uid;
@@ -457,11 +429,14 @@ Mentions.parseRaw = async (content, type = 'default') => {
457
429
  }
458
430
 
459
431
  case !!cid: {
432
+ mentionType = 'category';
433
+ const category = await categories.getCategoryFields(cid, ['slug']);
460
434
  url = `/category/${category.slug}`;
461
435
  break;
462
436
  }
463
437
 
464
438
  case !!groupExists: {
439
+ mentionType = 'group';
465
440
  url = `/groups/${slug}`;
466
441
  break;
467
442
  }
@@ -483,7 +458,7 @@ Mentions.parseRaw = async (content, type = 'default') => {
483
458
  const atIndex = match.indexOf('@');
484
459
  const plain = match.slice(0, atIndex);
485
460
  match = match.slice(atIndex);
486
- if (user.uid) {
461
+ if (user && user.uid) {
487
462
  switch (Mentions._settings.display) {
488
463
  case 'fullname':
489
464
  match = user.fullname || match;
@@ -494,7 +469,7 @@ Mentions.parseRaw = async (content, type = 'default') => {
494
469
  }
495
470
  }
496
471
 
497
- const str = `<a class="plugin-mentions-${user.uid ? 'user' : 'group'} plugin-mentions-a" href="${url}">${match}</a>`;
472
+ const str = `<a class="plugin-mentions-${mentionType} plugin-mentions-a" href="${url}">${match}</a>`;
498
473
 
499
474
  return plain + str;
500
475
  });
@@ -502,25 +477,7 @@ Mentions.parseRaw = async (content, type = 'default') => {
502
477
  }
503
478
  }));
504
479
 
505
- let parsed = splitContent.join('');
506
-
507
- // Early return if no urls to modify
508
- if (!urlMap.size) {
509
- return parsed;
510
- }
511
-
512
- // Modify existing anchors to local profile
513
- const anchors = new Set(Array.from(parsed.matchAll(anchorRegex)).reverse());
514
- if (!anchors.size) {
515
- return parsed;
516
- }
517
-
518
- anchors.forEach(([match, href]) => {
519
- const replacement = match.replace(href, urlMap.get(href));
520
- parsed = parsed.split(match).join(replacement);
521
- });
522
-
523
- return parsed;
480
+ return splitContent.join('');
524
481
  };
525
482
 
526
483
  Mentions.clean = function (input, isMarkdown, stripBlockquote, stripCode) {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "nodebb-plugin-mentions",
3
- "version": "4.6.4",
3
+ "version": "4.6.6",
4
4
  "description": "NodeBB Plugin that allows users to mention other users by prepending an '@' sign to their username",
5
5
  "main": "library.js",
6
6
  "repository": {
@@ -43,7 +43,7 @@ $(document).ready(function () {
43
43
  const localMatches = localUserList.filter(
44
44
  u => u.username.toLocaleLowerCase().startsWith(termLowerCase)
45
45
  );
46
- const categoryMatches = categoryList.filter(c => c.handle.startsWith(termLowerCase));
46
+ const categoryMatches = categoryList.filter(c => c && c.handle && c.handle.startsWith(termLowerCase));
47
47
 
48
48
  // remove local matches from search results, add category matches
49
49
  users = users.filter(u => !localMatches.find(lu => lu.uid === u.uid));