From b5d38bc696f642fdf94d14198a12caefce6db90b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Bar=C4=B1=C5=9F=20Soner=20U=C5=9Fakl=C4=B1?= Date: Sat, 29 Oct 2022 16:57:03 -0400 Subject: [PATCH 1/7] feat: new search hooks filter:search.isAllowed, allow plugins to check if searching is allowed filter:search.searchIn, allow searching in custom items --- src/controllers/search.js | 8 ++++++-- src/search.js | 5 +++++ 2 files changed, 11 insertions(+), 2 deletions(-) diff --git a/src/controllers/search.js b/src/controllers/search.js index 82aed2b308..238c167709 100644 --- a/src/controllers/search.js +++ b/src/controllers/search.js @@ -29,11 +29,15 @@ searchController.search = async function (req, res, next) { 'search:tags': privileges.global.can('search:tags', req.uid), }); req.query.in = req.query.in || meta.config.searchDefaultIn || 'titlesposts'; - const allowed = (req.query.in === 'users' && userPrivileges['search:users']) || + let allowed = (req.query.in === 'users' && userPrivileges['search:users']) || (req.query.in === 'tags' && userPrivileges['search:tags']) || (req.query.in === 'categories') || (['titles', 'titlesposts', 'posts'].includes(req.query.in) && userPrivileges['search:content']); - + ({ allowed } = await plugins.hooks.fire('filter:search.isAllowed', { + uid: req.uid, + query: req.query, + allowed, + })); if (!allowed) { return helpers.notAllowed(req, res); } diff --git a/src/search.js b/src/search.js index a46934ff2f..c1463486d2 100644 --- a/src/search.js +++ b/src/search.js @@ -27,6 +27,10 @@ search.search = async function (data) { result = await categories.search(data); } else if (data.searchIn === 'tags') { result = await topics.searchAndLoadTags(data); + } else if (data.searchIn) { + result = await plugins.hooks.fire('filter:search.searchIn', { + data, + }); } else { throw new Error('[[error:unknown-search-filter]]'); } @@ -108,6 +112,7 @@ async function searchInContent(data) { returnData.posts = await posts.getPostSummaryByPids(metadata.pids, data.uid, {}); await plugins.hooks.fire('filter:search.contentGetResult', { result: returnData, data: data }); delete metadata.pids; + delete metadata.data; return Object.assign(returnData, metadata); } From c833d3cdc4e4f3576e85d1d2c4e0aca1eb93d665 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Bar=C4=B1=C5=9F=20Soner=20U=C5=9Fakl=C4=B1?= Date: Sat, 29 Oct 2022 17:05:16 -0400 Subject: [PATCH 2/7] test: fix test --- test/search.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/search.js b/test/search.js index b58702bb38..e86d48bc48 100644 --- a/test/search.js +++ b/test/search.js @@ -183,7 +183,7 @@ describe('Search', () => { it('should fail if searchIn is wrong', (done) => { search.search({ query: 'plug', - searchIn: 'invalidfilter', + searchIn: '', }, (err) => { assert.equal(err.message, '[[error:unknown-search-filter]]'); done(); From 06d15391371e92fe0059e7c8ed48622f6e639b28 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Bar=C4=B1=C5=9F=20Soner=20U=C5=9Fakl=C4=B1?= Date: Sat, 29 Oct 2022 17:40:33 -0400 Subject: [PATCH 3/7] test: fix tests again --- src/search.js | 1 - test/search.js | 1 + 2 files changed, 1 insertion(+), 1 deletion(-) diff --git a/src/search.js b/src/search.js index c1463486d2..cbd4e4f40c 100644 --- a/src/search.js +++ b/src/search.js @@ -15,7 +15,6 @@ const search = module.exports; search.search = async function (data) { const start = process.hrtime(); - data.searchIn = data.searchIn || 'titlesposts'; data.sortBy = data.sortBy || 'relevance'; let result; diff --git a/test/search.js b/test/search.js index e86d48bc48..14179ad5cd 100644 --- a/test/search.js +++ b/test/search.js @@ -216,6 +216,7 @@ describe('Search', () => { it('should not find anything', (done) => { search.search({ query: 'xxxxxxxxxxxxxx', + searchIn: 'titles', }, (err, data) => { assert.ifError(err); assert(Array.isArray(data.posts)); From d264c6ac4bfa8cafe4466cb922270fcac3416920 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Bar=C4=B1=C5=9F=20Soner=20U=C5=9Fakl=C4=B1?= Date: Thu, 3 Nov 2022 20:17:38 -0400 Subject: [PATCH 4/7] refactor: use utils.debounce --- public/src/client/groups/memberlist.js | 34 ++++++++++++-------------- 1 file changed, 15 insertions(+), 19 deletions(-) diff --git a/public/src/client/groups/memberlist.js b/public/src/client/groups/memberlist.js index 44b593c63c..7a3376eb51 100644 --- a/public/src/client/groups/memberlist.js +++ b/public/src/client/groups/memberlist.js @@ -2,7 +2,6 @@ define('forum/groups/memberlist', ['api', 'bootbox', 'alerts'], function (api, bootbox, alerts) { const MemberList = {}; - let searchInterval; let groupName; let templateName; @@ -89,25 +88,22 @@ define('forum/groups/memberlist', ['api', 'bootbox', 'alerts'], function (api, b } function handleMemberSearch() { - $('[component="groups/members/search"]').on('keyup', function () { - const query = $(this).val(); - if (searchInterval) { - clearInterval(searchInterval); - searchInterval = 0; - } - - searchInterval = setTimeout(function () { - socket.emit('groups.searchMembers', { groupName: groupName, query: query }, function (err, results) { - if (err) { - return alerts.error(err); - } - parseAndTranslate(results.users, function (html) { - $('[component="groups/members"] tbody').html(html); - $('[component="groups/members"]').attr('data-nextstart', 20); - }); + const searchEl = $('[component="groups/members/search"]'); + searchEl.on('keyup', utils.debounce(function () { + const query = searchEl.val(); + socket.emit('groups.searchMembers', { + groupName: groupName, + query: query, + }, function (err, results) { + if (err) { + return alerts.error(err); + } + parseAndTranslate(results.users, function (html) { + $('[component="groups/members"] tbody').html(html); + $('[component="groups/members"]').attr('data-nextstart', 20); }); - }, 250); - }); + }); + }, 250)); } function handleMemberInfiniteScroll() { From 078bd4dd1f69075b6d239c12ace65b508b9e6c11 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Bar=C4=B1=C5=9F=20Soner=20U=C5=9Fakl=C4=B1?= Date: Fri, 4 Nov 2022 19:34:33 -0400 Subject: [PATCH 5/7] Update README.md --- README.md | 1 + 1 file changed, 1 insertion(+) diff --git a/README.md b/README.md index ec84b1303e..d06bc0362a 100644 --- a/README.md +++ b/README.md @@ -3,6 +3,7 @@ [![Workflow](https://github.com/NodeBB/NodeBB/actions/workflows/test.yaml/badge.svg)](https://github.com/NodeBB/NodeBB/actions/workflows/test.yaml) [![Coverage Status](https://coveralls.io/repos/github/NodeBB/NodeBB/badge.svg?branch=master)](https://coveralls.io/github/NodeBB/NodeBB?branch=master) [![Code Climate](https://codeclimate.com/github/NodeBB/NodeBB/badges/gpa.svg)](https://codeclimate.com/github/NodeBB/NodeBB) +[![](https://dcbadge.vercel.app/api/server/p6YKPXu7er?style=flat)](https://discord.gg/p6YKPXu7er) [**NodeBB Forum Software**](https://nodebb.org) is powered by Node.js and supports either Redis, MongoDB, or a PostgreSQL database. It utilizes web sockets for instant interactions and real-time notifications. NodeBB takes the best of the modern web: real-time streaming discussions, mobile responsiveness, and rich RESTful read/write APIs, while staying true to the original bulletin board/forum format → categorical hierarchies, local user accounts, and asynchronous messaging. From a31ba824ea34b197aa0fad9f34582e9cdc33f29f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Bar=C4=B1=C5=9F=20Soner=20U=C5=9Fakl=C4=B1?= Date: Sat, 5 Nov 2022 14:44:12 -0400 Subject: [PATCH 6/7] fix: upgrade script to work from 0.x to 2.x --- .../1.11.0/navigation_visibility_groups.js | 38 +++++++++++++++++-- 1 file changed, 34 insertions(+), 4 deletions(-) diff --git a/src/upgrades/1.11.0/navigation_visibility_groups.js b/src/upgrades/1.11.0/navigation_visibility_groups.js index 3567b3c9c1..4e3730b9cb 100644 --- a/src/upgrades/1.11.0/navigation_visibility_groups.js +++ b/src/upgrades/1.11.0/navigation_visibility_groups.js @@ -4,9 +4,7 @@ module.exports = { name: 'Navigation item visibility groups', timestamp: Date.UTC(2018, 10, 10), method: async function () { - const navigationAdmin = require('../../navigation/admin'); - - const data = await navigationAdmin.get(); + const data = await navigationAdminGet(); data.forEach((navItem) => { if (navItem && navItem.properties) { navItem.groups = []; @@ -23,6 +21,38 @@ module.exports = { } } }); - await navigationAdmin.save(data); + await navigationAdminSave(data); }, }; +// use navigation.get/save as it was in 1.11.0 so upgrade script doesn't crash on latest nbb +// see https://github.com/NodeBB/NodeBB/pull/11013 +async function navigationAdminGet() { + const db = require('../../database'); + const data = await db.getSortedSetRange('navigation:enabled', 0, -1); + return data.filter(Boolean).map((item) => { + item = JSON.parse(item); + item.groups = item.groups || []; + if (item.groups && !Array.isArray(item.groups)) { + item.groups = [item.groups]; + } + return item; + }); +} + +async function navigationAdminSave(data) { + const db = require('../../database'); + const translator = require('../../translator'); + const order = Object.keys(data); + const items = data.map((item, index) => { + Object.keys(item).forEach((key) => { + if (item.hasOwnProperty(key) && typeof item[key] === 'string' && (key === 'title' || key === 'text')) { + item[key] = translator.escape(item[key]); + } + }); + item.order = order[index]; + return JSON.stringify(item); + }); + + await db.delete('navigation:enabled'); + await db.sortedSetAdd('navigation:enabled', order, items); +} From 55a197a7d79037a08cec9c71bb6b9e66f09f94f8 Mon Sep 17 00:00:00 2001 From: Julian Lam Date: Wed, 9 Nov 2022 12:00:59 -0500 Subject: [PATCH 7/7] fix: check for csrf token on /register/abort, + theme changes for v2.x branches of themes --- install/package.json | 4 ++-- src/routes/authentication.js | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/install/package.json b/install/package.json index 9428775781..ef7ad84789 100644 --- a/install/package.json +++ b/install/package.json @@ -99,9 +99,9 @@ "nodebb-plugin-spam-be-gone": "1.0.2", "nodebb-rewards-essentials": "0.2.1", "nodebb-theme-lavender": "6.0.0", - "nodebb-theme-persona": "12.1.1", + "nodebb-theme-persona": "12.1.10", "nodebb-theme-slick": "2.0.2", - "nodebb-theme-vanilla": "12.1.18", + "nodebb-theme-vanilla": "12.1.19", "nodebb-widget-essentials": "6.0.0", "nodemailer": "6.7.8", "nprogress": "0.2.0", diff --git a/src/routes/authentication.js b/src/routes/authentication.js index 3c6ea76f0b..9febe062a8 100644 --- a/src/routes/authentication.js +++ b/src/routes/authentication.js @@ -171,7 +171,7 @@ Auth.reloadRoutes = async function (params) { router.post('/register', middlewares, controllers.authentication.register); router.post('/register/complete', middlewares, controllers.authentication.registerComplete); - router.post('/register/abort', controllers.authentication.registerAbort); + router.post('/register/abort', Auth.middleware.applyCSRF, controllers.authentication.registerAbort); router.post('/login', Auth.middleware.applyCSRF, Auth.middleware.applyBlacklist, controllers.authentication.login); router.post('/logout', Auth.middleware.applyCSRF, controllers.authentication.logout); };