From 0713475dc5ecb045d099381904b2db9cb27201e3 Mon Sep 17 00:00:00 2001 From: "Misty (Bot)" Date: Fri, 3 Sep 2021 15:04:06 +0000 Subject: [PATCH 01/30] chore: update changelog for v1.18.1 --- CHANGELOG.md | 44 ++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 44 insertions(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index de31b7fb97..466a49bd4a 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,47 @@ +#### v1.18.1 (2021-09-03) + +##### Chores + +* found some hooks that don't play well docgen (ae793b4a) +* incrementing version number - v1.18.0 (1e436ae7) +* update changelog for v1.18.0 (2fd9c095) +* **deps:** update dependency mocha to v9.1.1 (64bac178) + +##### New Features + +* create folders in ACP uploads #9638 (#9750) (3df79683) +* column based view on wide priv. tables (#9699) (61f02f17) +* als (#9749) (e59d3575) +* add quick reply key (e9314842) +* add new lang key for no best posts (6e73d8c9) + +##### Bug Fixes + +* **deps:** + * update dependency autoprefixer to v10.3.4 (67b932f4) + * update dependency nodebb-theme-persona to v11.2.4 (fe18e100) + * update dependency mongodb to v3.7.0 (31a35d7f) + * update socket.io packages to v4.2.0 (f2028d70) + * update dependency ioredis to v4.27.9 (6052eb16) + * update dependency mongodb to v3.6.12 (#9761) (5fa982c1) + * update dependency nodebb-plugin-composer-default to v7.0.2 (33d51201) + * update dependency nodebb-theme-slick to v1.4.12 (1b416d7e) + * update dependency nodebb-theme-slick to v1.4.11 (65b32fa1) + * update dependency nodebb-theme-persona to v11.2.3 (6ce321e4) + * update dependency autoprefixer to v10.3.3 (91ba7cdf) + * update dependency nodebb-theme-slick to v1.4.9 (d80b378f) + * update dependency jquery-deserialize to v2.0.0 (#9744) (7f9451ce) +* determine indeterminate checkboxes (760ea9df) +* move app.alert back into the conditionals (ca9bae3a) +* only show email confirmation warning toast on pages that it applies (1bd1cc74) +* updated email confirm warning to be more positive (2d1380dd) +* automated tests are a good thing to have (6afeac37) + +##### Refactors + +* consistent jquery element var naming (fc0e655e) +* var to const (1272da65) + #### v1.18.0 (2021-08-25) ##### Breaking Changes From f8f80e4fb3f5677af80de00e848c6227896cbaa2 Mon Sep 17 00:00:00 2001 From: "Misty (Bot)" Date: Fri, 3 Sep 2021 15:04:06 +0000 Subject: [PATCH 02/30] chore: incrementing version number - v1.18.1 (cherry picked from commit 0409403f5b122fbf4221491cf3c81ff76fa0e4b1) Signed-off-by: Misty (Bot) --- install/package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/install/package.json b/install/package.json index 3e837e7f90..345e5e1add 100644 --- a/install/package.json +++ b/install/package.json @@ -2,7 +2,7 @@ "name": "nodebb", "license": "GPL-3.0", "description": "NodeBB Forum", - "version": "1.18.0", + "version": "1.18.1", "homepage": "http://www.nodebb.org", "repository": { "type": "git", From 6869920e06e0f92b3a1a662be400f79d377d331d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Bar=C4=B1=C5=9F=20Soner=20U=C5=9Fakl=C4=B1?= Date: Fri, 3 Sep 2021 11:22:42 -0400 Subject: [PATCH 03/30] fix: #9773, fire hooks properly for priv changes (#9774) --- src/api/categories.js | 18 ++++++++++++++---- 1 file changed, 14 insertions(+), 4 deletions(-) diff --git a/src/api/categories.js b/src/api/categories.js index 3486df1ad5..f2b3a830b6 100644 --- a/src/api/categories.js +++ b/src/api/categories.js @@ -65,10 +65,20 @@ categoriesAPI.setPrivilege = async (caller, data) => { if (!userExists && !groupExists) { throw new Error('[[error:no-user-or-group]]'); } - - await privileges.categories[data.set ? 'give' : 'rescind']( - Array.isArray(data.privilege) ? data.privilege : [data.privilege], data.cid, data.member - ); + const privs = Array.isArray(data.privilege) ? data.privilege : [data.privilege]; + const type = data.set ? 'give' : 'rescind'; + if (!privs.length) { + throw new Error('[[error:invalid-data]]'); + } + let privMethod = privileges.categories[type]; + if (parseInt(data.cid, 10) === 0) { + if (privs[0].startsWith('admin:')) { + privMethod = privileges.admin[type]; + } else { + privMethod = privileges.global[type]; + } + } + await privMethod(privs, data.cid, data.member); await events.log({ uid: caller.uid, From 46e5e17d0fff3c44765f376f298ba5636cde890a Mon Sep 17 00:00:00 2001 From: Julian Lam Date: Fri, 3 Sep 2021 11:34:09 -0400 Subject: [PATCH 04/30] fix: focus on save button on plugin activation --- public/src/admin/extend/plugins.js | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/public/src/admin/extend/plugins.js b/public/src/admin/extend/plugins.js index 064b2fa79e..b51e8e4189 100644 --- a/public/src/admin/extend/plugins.js +++ b/public/src/admin/extend/plugins.js @@ -79,6 +79,12 @@ define('admin/extend/plugins', [ callback: toggleActivate, }, }, + onShown: function () { + const saveEl = this.querySelector('button.btn-primary'); + if (saveEl) { + saveEl.focus(); + } + }, }); }); } else { From 4ac701d7473ec43c79bdb7073e1534c32607b51e Mon Sep 17 00:00:00 2001 From: Julian Lam Date: Fri, 3 Sep 2021 11:57:18 -0400 Subject: [PATCH 05/30] fix: deprecate userData.showHidden as it is functionally equivalent to userData.canEdit --- src/controllers/accounts/helpers.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/controllers/accounts/helpers.js b/src/controllers/accounts/helpers.js index 359355da87..7628347dda 100644 --- a/src/controllers/accounts/helpers.js +++ b/src/controllers/accounts/helpers.js @@ -78,7 +78,7 @@ helpers.getUserDataByUserSlug = async function (userslug, callerUID, query = {}) userData.isSelf = isSelf; userData.isFollowing = results.isFollowing; userData.hasPrivateChat = results.hasPrivateChat; - userData.showHidden = isSelf || isAdmin || (isGlobalModerator && !results.isTargetAdmin); + userData.showHidden = results.canEdit; // remove in v1.19.0 userData.groups = Array.isArray(results.groups) && results.groups.length ? results.groups[0] : []; userData.disableSignatures = meta.config.disableSignatures === 1; userData['reputation:disabled'] = meta.config['reputation:disabled'] === 1; From 1f91a3132795b51a63ba124dbe2985b48c669f7e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Bar=C4=B1=C5=9F=20Soner=20U=C5=9Fakl=C4=B1?= Date: Fri, 3 Sep 2021 11:58:17 -0400 Subject: [PATCH 06/30] Priv hook fix (#9775) * fix: #9773, fire hooks properly for priv changes * fix: admin/global group privs dont allow invalid privs --- src/api/categories.js | 16 ++++++++++------ src/privileges/admin.js | 2 ++ src/privileges/global.js | 2 ++ 3 files changed, 14 insertions(+), 6 deletions(-) diff --git a/src/api/categories.js b/src/api/categories.js index f2b3a830b6..118dd0a258 100644 --- a/src/api/categories.js +++ b/src/api/categories.js @@ -70,15 +70,19 @@ categoriesAPI.setPrivilege = async (caller, data) => { if (!privs.length) { throw new Error('[[error:invalid-data]]'); } - let privMethod = privileges.categories[type]; if (parseInt(data.cid, 10) === 0) { - if (privs[0].startsWith('admin:')) { - privMethod = privileges.admin[type]; - } else { - privMethod = privileges.global[type]; + const adminPrivs = privs.filter(priv => privileges.admin.privilegeList.includes(priv)); + const globalPrivs = privs.filter(priv => privileges.global.privilegeList.includes(priv)); + if (adminPrivs.length) { + await privileges.admin[type](adminPrivs, data.member); } + if (globalPrivs.length) { + await privileges.global[type](globalPrivs, data.member); + } + } else { + const categoryPrivs = privs.filter(priv => privileges.categories.privilegeList.includes(priv)); + await privileges.categories[type](categoryPrivs, data.cid, data.member); } - await privMethod(privs, data.cid, data.member); await events.log({ uid: caller.uid, diff --git a/src/privileges/admin.js b/src/privileges/admin.js index ead7f6fc5e..d98e2c2bca 100644 --- a/src/privileges/admin.js +++ b/src/privileges/admin.js @@ -35,6 +35,8 @@ privsAdmin.userPrivilegeList = [ privsAdmin.groupPrivilegeList = privsAdmin.userPrivilegeList.map(privilege => `groups:${privilege}`); +privsAdmin.privilegeList = privsAdmin.userPrivilegeList.concat(privsAdmin.groupPrivilegeList); + // Mapping for a page route (via direct match or regexp) to a privilege privsAdmin.routeMap = { dashboard: 'admin:dashboard', diff --git a/src/privileges/global.js b/src/privileges/global.js index 563ae3d053..206e7769c3 100644 --- a/src/privileges/global.js +++ b/src/privileges/global.js @@ -49,6 +49,8 @@ privsGlobal.userPrivilegeList = [ privsGlobal.groupPrivilegeList = privsGlobal.userPrivilegeList.map(privilege => `groups:${privilege}`); +privsGlobal.privilegeList = privsGlobal.userPrivilegeList.concat(privsGlobal.groupPrivilegeList); + privsGlobal.list = async function () { async function getLabels() { return await utils.promiseParallel({ From dd4e66e22c93586d389b47fa197154620508ae8f Mon Sep 17 00:00:00 2001 From: Julian Lam Date: Fri, 3 Sep 2021 12:04:16 -0400 Subject: [PATCH 07/30] fix: push back some deprecations, remove deprecated stuff scheduled for v1.18.0 --- src/emailer.js | 2 +- src/middleware/user.js | 4 ++-- src/plugins/hooks.js | 2 +- src/plugins/index.js | 17 ----------------- src/privileges/index.js | 17 ----------------- 5 files changed, 4 insertions(+), 38 deletions(-) diff --git a/src/emailer.js b/src/emailer.js index 0d6e309b0a..754b794c05 100644 --- a/src/emailer.js +++ b/src/emailer.js @@ -324,7 +324,7 @@ Emailer.sendToEmail = async (template, email, language, params) => { !Plugins.hooks.hasListeners('static:email.send'); try { if (Plugins.hooks.hasListeners('filter:email.send')) { - // Deprecated, remove in v1.18.0 + // Deprecated, remove in v1.19.0 await Plugins.hooks.fire('filter:email.send', data); } else if (Plugins.hooks.hasListeners('static:email.send')) { await Plugins.hooks.fire('static:email.send', data); diff --git a/src/middleware/user.js b/src/middleware/user.js index 4adff804d5..b9f195477e 100644 --- a/src/middleware/user.js +++ b/src/middleware/user.js @@ -82,7 +82,7 @@ module.exports = function (middleware) { return !res.headersSent; } - // TODO: Remove in v1.18.0 + // TODO: Remove in v1.19.0 middleware.authenticate = helpers.try(async (req, res, next) => { winston.warn(`[middleware] middleware.authenticate has been deprecated, page and API routes are now automatically authenticated via setup(Page|API)Route. Use middleware.authenticateRequest (if not using route helper) and middleware.ensureLoggedIn instead. (request path: ${req.path})`); if (!await authenticate(req, res)) { @@ -101,7 +101,7 @@ module.exports = function (middleware) { next(); }); - // TODO: Remove in v1.18.0 + // TODO: Remove in v1.19.0 middleware.authenticateOrGuest = (req, res, next) => { winston.warn(`[middleware] middleware.authenticateOrGuest has been renamed, use middleware.authenticateRequest instead. (request path: ${req.path})`); middleware.authenticateRequest(req, res, next); diff --git a/src/plugins/hooks.js b/src/plugins/hooks.js index d46a1fcdb0..24875ca986 100644 --- a/src/plugins/hooks.js +++ b/src/plugins/hooks.js @@ -8,7 +8,7 @@ const utils = require('../utils'); const Hooks = module.exports; Hooks.deprecatedHooks = { - 'filter:email.send': 'static:email.send', // 👋 @ 1.18.0 + 'filter:email.send': 'static:email.send', // 👋 @ 1.19.0 'filter:router.page': 'response:router.page', // 👋 @ 2.0.0 }; diff --git a/src/plugins/index.js b/src/plugins/index.js index a7e8560dd5..772ec91e19 100644 --- a/src/plugins/index.js +++ b/src/plugins/index.js @@ -25,23 +25,6 @@ require('./usage')(Plugins); Plugins.data = require('./data'); Plugins.hooks = require('./hooks'); -// Backwards compatibility for hooks, remove in v1.18.0 -const _deprecate = async function (...args) { - const oldMethod = args.shift(); - const newMethod = args.shift(); - const method = args.shift(); - const stack = new Error().stack.toString().split(os.EOL); - const context = stack[stack.findIndex(line => line.startsWith(' at Object.wrapperCallback')) + 1]; - winston.warn(`[plugins/hooks] ${oldMethod} has been deprecated, call ${newMethod} instead.`); - winston.warn(`[plugins/hooks] ${context}`); - return method.apply(Plugins.hooks, args); -}; -Plugins.registerHook = _deprecate.bind(null, 'Plugins.registerHook', 'Plugins.hooks.register', Plugins.hooks.register); -Plugins.unregisterHook = _deprecate.bind(null, 'Plugins.unregisterHook', 'Plugins.hooks.unregister', Plugins.hooks.unregister); -Plugins.fireHook = _deprecate.bind(null, 'Plugins.fireHook', 'Plugins.hooks.fire', Plugins.hooks.fire); -Plugins.hasListeners = _deprecate.bind(null, 'Plugins.hasListeners', 'Plugins.hooks.hasListeners', Plugins.hooks.hasListeners); -// end - Plugins.getPluginPaths = Plugins.data.getPluginPaths; Plugins.loadPluginInfo = Plugins.data.loadPluginInfo; diff --git a/src/privileges/index.js b/src/privileges/index.js index 4a9c4d2096..6445b07b97 100644 --- a/src/privileges/index.js +++ b/src/privileges/index.js @@ -9,20 +9,3 @@ privileges.posts = require('./posts'); privileges.users = require('./users'); require('../promisify')(privileges); - -// TODO: backwards compatibility remove in 1.18.0 -[ - 'privilegeLabels', - 'userPrivilegeList', - 'groupPrivilegeList', - 'privilegeList', -].forEach((fieldName) => { - Object.defineProperty(privileges, fieldName, { - configurable: true, - enumerable: true, - get: function () { - console.warn(`[deprecated] privileges.${fieldName} is deprecated. Use privileges.categories.${fieldName}`); - return privileges.categories[fieldName]; - }, - }); -}); From 72710b804062e26460bd0195510523a876b51c3e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Bar=C4=B1=C5=9F=20Soner=20U=C5=9Fakl=C4=B1?= Date: Fri, 3 Sep 2021 12:22:03 -0400 Subject: [PATCH 08/30] fix: #9772, regression from https://github.com/NodeBB/NodeBB/commit/70a04bc10577e90e28d66a647d38cafc3307a285 --- src/controllers/authentication.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/controllers/authentication.js b/src/controllers/authentication.js index 132c0b33f7..875976a635 100644 --- a/src/controllers/authentication.js +++ b/src/controllers/authentication.js @@ -200,7 +200,7 @@ authenticationController.registerComplete = function (req, res, next) { return winston.warn('[register] Interstitial callbacks processed with no errors, but one or more interstitials remain. This is likely an issue with one of the interstitials not properly handling a null case or invalid value.'); } - done(); + done(null, data); } else { // Update user hash, clear registration data in session const payload = req.session.registration; From 488f0978a4aa1ca1e4d2a1f2e8c7ef7a681f2f27 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Bar=C4=B1=C5=9F=20Soner=20U=C5=9Fakl=C4=B1?= Date: Fri, 3 Sep 2021 12:29:11 -0400 Subject: [PATCH 09/30] fix: manifest error --- src/meta/tags.js | 1 + 1 file changed, 1 insertion(+) diff --git a/src/meta/tags.js b/src/meta/tags.js index daa4d4808c..1f2c68e13f 100644 --- a/src/meta/tags.js +++ b/src/meta/tags.js @@ -66,6 +66,7 @@ Tags.parse = async (req, data, meta, link) => { }, { rel: 'manifest', href: `${relative_path}/manifest.webmanifest`, + crossorigin: `use-credentials`, }]; if (plugins.hooks.hasListeners('filter:search.query')) { From 1e2bda13d0891dbd9b115ee57fa826fb89dc26a4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Bar=C4=B1=C5=9F=20Soner=20U=C5=9Fakl=C4=B1?= Date: Fri, 3 Sep 2021 12:41:11 -0400 Subject: [PATCH 10/30] fix: lint --- src/plugins/index.js | 1 - 1 file changed, 1 deletion(-) diff --git a/src/plugins/index.js b/src/plugins/index.js index 772ec91e19..04675f1a45 100644 --- a/src/plugins/index.js +++ b/src/plugins/index.js @@ -1,7 +1,6 @@ 'use strict'; const fs = require('fs'); -const os = require('os'); const path = require('path'); const winston = require('winston'); const semver = require('semver'); From 60de0844754fd9102027e013db0375429a6054f1 Mon Sep 17 00:00:00 2001 From: Julian Lam Date: Fri, 3 Sep 2021 13:36:56 -0400 Subject: [PATCH 11/30] fix: simplify logic for fullname and email blanking in user retrieval (getUserDataByUserSlug) Previous logic seemed to match the logic used in privileges.users.canEdit, except the latter allows plugins to modify the value. --- src/controllers/accounts/helpers.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/controllers/accounts/helpers.js b/src/controllers/accounts/helpers.js index 7628347dda..c3a4cb6d35 100644 --- a/src/controllers/accounts/helpers.js +++ b/src/controllers/accounts/helpers.js @@ -43,13 +43,13 @@ helpers.getUserDataByUserSlug = async function (userslug, callerUID, query = {}) userData.emailClass = 'hide'; - if (!isAdmin && !isGlobalModerator && !isSelf && (!userSettings.showemail || meta.config.hideEmail)) { + if (!results.canEdit && (!userSettings.showemail || meta.config.hideEmail)) { userData.email = ''; } else if (!userSettings.showemail) { userData.emailClass = ''; } - if (!isAdmin && !isGlobalModerator && !isSelf && (!userSettings.showfullname || meta.config.hideFullname)) { + if (!results.canEdit && (!userSettings.showfullname || meta.config.hideFullname)) { userData.fullname = ''; } From 57e54d559beece183cbce3b6cc7c7657d0ea17ad Mon Sep 17 00:00:00 2001 From: Renovate Bot Date: Fri, 3 Sep 2021 17:57:43 +0000 Subject: [PATCH 12/30] fix(deps): update dependency nodebb-theme-persona to v11.2.5 --- install/package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/install/package.json b/install/package.json index 345e5e1add..de02ca25a2 100644 --- a/install/package.json +++ b/install/package.json @@ -93,7 +93,7 @@ "nodebb-plugin-spam-be-gone": "0.7.9", "nodebb-rewards-essentials": "0.1.5", "nodebb-theme-lavender": "5.2.1", - "nodebb-theme-persona": "11.2.4", + "nodebb-theme-persona": "11.2.5", "nodebb-theme-slick": "1.4.12", "nodebb-theme-vanilla": "12.1.2", "nodebb-widget-essentials": "5.0.4", From a48bbdbfe38d9b802389d1b75f1cdc2045eacdac Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Bar=C4=B1=C5=9F=20Soner=20U=C5=9Fakl=C4=B1?= Date: Fri, 3 Sep 2021 15:30:05 -0400 Subject: [PATCH 13/30] fix: errors from registerComplete --- src/controllers/authentication.js | 33 ++++++++++++++----------------- 1 file changed, 15 insertions(+), 18 deletions(-) diff --git a/src/controllers/authentication.js b/src/controllers/authentication.js index 875976a635..4340b16508 100644 --- a/src/controllers/authentication.js +++ b/src/controllers/authentication.js @@ -138,16 +138,14 @@ async function addToApprovalQueue(req, userData) { return { message: message }; } -authenticationController.registerComplete = function (req, res, next) { - // For the interstitials that respond, execute the callback with the form body - plugins.hooks.fire('filter:register.interstitial', { - req, - userData: req.session.registration, - interstitials: [], - }, async (err, data) => { - if (err) { - return next(err); - } +authenticationController.registerComplete = async function (req, res) { + try { + // For the interstitials that respond, execute the callback with the form body + const data = await plugins.hooks.fire('filter:register.interstitial', { + req, + userData: req.session.registration, + interstitials: [], + }); const callbacks = data.interstitials.reduce((memo, cur) => { if (cur.hasOwnProperty('callback') && typeof cur.callback === 'function') { @@ -165,13 +163,10 @@ authenticationController.registerComplete = function (req, res, next) { return memo; }, []); - const done = function (err, data) { + const done = function (data) { delete req.session.registration; - if (err) { - return res.redirect(`${nconf.get('relative_path')}/?register=${encodeURIComponent(err.message)}`); - } - if (!err && data && data.message) { + if (data && data.message) { return res.redirect(`${nconf.get('relative_path')}/?register=${encodeURIComponent(data.message)}`); } @@ -199,8 +194,7 @@ authenticationController.registerComplete = function (req, res, next) { if (!data) { return winston.warn('[register] Interstitial callbacks processed with no errors, but one or more interstitials remain. This is likely an issue with one of the interstitials not properly handling a null case or invalid value.'); } - - done(null, data); + done(data); } else { // Update user hash, clear registration data in session const payload = req.session.registration; @@ -217,7 +211,10 @@ authenticationController.registerComplete = function (req, res, next) { await user.setUserFields(uid, payload); done(); } - }); + } catch (err) { + delete req.session.registration; + res.redirect(`${nconf.get('relative_path')}/?register=${encodeURIComponent(err.message)}`); + } }; authenticationController.registerAbort = function (req, res) { From e33e046f1547848883085896f0fc6df2e9d178a6 Mon Sep 17 00:00:00 2001 From: Julian Lam Date: Fri, 3 Sep 2021 15:24:50 -0400 Subject: [PATCH 14/30] fix: use privileges.users.canEdit for image upload priv check --- src/socket.io/user/profile.js | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/src/socket.io/user/profile.js b/src/socket.io/user/profile.js index 4f757943ac..2de4160ba5 100644 --- a/src/socket.io/user/profile.js +++ b/src/socket.io/user/profile.js @@ -6,6 +6,7 @@ const api = require('../../api'); const user = require('../../user'); const events = require('../../events'); const notifications = require('../../notifications'); +const privileges = require('../../privileges'); const db = require('../../database'); const plugins = require('../../plugins'); const sockets = require('..'); @@ -31,10 +32,10 @@ module.exports = function (SocketUser) { }; SocketUser.uploadCroppedPicture = async function (socket, data) { - if (!socket.uid) { + if (!socket.uid || !(await privileges.users.canEdit(socket.uid, data.uid))) { throw new Error('[[error:no-privileges]]'); } - await user.isAdminOrGlobalModOrSelf(socket.uid, data.uid); + await user.checkMinReputation(socket.uid, data.uid, 'min:rep:profile-picture'); data.callerUid = socket.uid; return await user.uploadCroppedPicture(data); From 0a41741b7e135c07ac360f6e44910a8a0133e3b7 Mon Sep 17 00:00:00 2001 From: Julian Lam Date: Fri, 3 Sep 2021 15:25:26 -0400 Subject: [PATCH 15/30] refactor: deprecate picture update socket call, new API routes for picture update --- public/openapi/write.yaml | 2 + public/openapi/write/users/uid/picture.yaml | 43 +++++++++++++++++++++ public/src/modules/accounts/picture.js | 19 +++------ src/api/users.js | 41 ++++++++++++++++++++ src/controllers/write/users.js | 5 +++ src/routes/write/users.js | 1 + src/socket.io/user/picture.js | 39 +++---------------- 7 files changed, 103 insertions(+), 47 deletions(-) create mode 100644 public/openapi/write/users/uid/picture.yaml diff --git a/public/openapi/write.yaml b/public/openapi/write.yaml index 8ac39fe982..734b64ff24 100644 --- a/public/openapi/write.yaml +++ b/public/openapi/write.yaml @@ -52,6 +52,8 @@ paths: $ref: 'write/users.yaml' /users/{uid}: $ref: 'write/users/uid.yaml' + /users/{uid}/picture: + $ref: 'write/users/uid/picture.yaml' /users/{uid}/content: $ref: 'write/users/uid/content.yaml' /users/{uid}/account: diff --git a/public/openapi/write/users/uid/picture.yaml b/public/openapi/write/users/uid/picture.yaml new file mode 100644 index 0000000000..d6498a0af2 --- /dev/null +++ b/public/openapi/write/users/uid/picture.yaml @@ -0,0 +1,43 @@ +put: + tags: + - users + summary: update user picture or icon background colour + parameters: + - in: path + name: uid + schema: + type: integer + required: true + description: uid of the user + example: 1 + requestBody: + content: + application/json: + schema: + type: object + properties: + type: + type: string + description: The source of the picture + enum: ['default', 'uploaded', 'external'] + example: default + url: + type: string + description: Only used for `external` type, specifies the source of the external image to use as avatar + example: '' + bgColor: + type: string + description: A hexadecimal colour representation + example: '#ff0000' + responses: + '200': + description: successfully updated user picture + content: + application/json: + schema: + type: object + properties: + status: + $ref: ../../../components/schemas/Status.yaml#/Status + response: + type: object \ No newline at end of file diff --git a/public/src/modules/accounts/picture.js b/public/src/modules/accounts/picture.js index a97e0fb891..3893f2e27a 100644 --- a/public/src/modules/accounts/picture.js +++ b/public/src/modules/accounts/picture.js @@ -2,7 +2,8 @@ define('accounts/picture', [ 'pictureCropper', -], (pictureCropper) => { + 'api', +], (pictureCropper, api) => { const Picture = {}; Picture.openChangeModal = () => { @@ -89,14 +90,10 @@ define('accounts/picture', [ var type = modal.find('.list-group-item.active').attr('data-type'); const iconBgColor = document.querySelector('.modal.picture-switcher input[type="radio"]:checked').value || 'transparent'; - changeUserPicture(type, iconBgColor, function (err) { - if (err) { - return app.alertError(err.message); - } - + changeUserPicture(type, iconBgColor).then(() => { Picture.updateHeader(type === 'default' ? '' : modal.find('.list-group-item.active img').attr('src'), iconBgColor); ajaxify.refresh(); - }); + }).catch(app.alertError); } function onCloseModal() { @@ -212,12 +209,8 @@ define('accounts/picture', [ }); } - function changeUserPicture(type, bgColor, callback) { - socket.emit('user.changePicture', { - type, - bgColor, - uid: ajaxify.data.theirid, - }, callback); + function changeUserPicture(type, bgColor) { + return api.put(`/users/${ajaxify.data.theirid}/picture`, { type, bgColor }); } return Picture; diff --git a/src/api/users.js b/src/api/users.js index b7deaed080..71d3a0c8f4 100644 --- a/src/api/users.js +++ b/src/api/users.js @@ -341,3 +341,44 @@ usersAPI.search = async function (caller, data) { filters: filters, }); }; + +usersAPI.changePicture = async (caller, data) => { + if (!data) { + throw new Error('[[error:invalid-data]]'); + } + + const { type, url } = data; + let picture = ''; + + await user.checkMinReputation(caller.uid, data.uid, 'min:rep:profile-picture'); + const canEdit = await privileges.users.canEdit(caller.uid, data.uid); + if (!canEdit) { + throw new Error('[[error:no-privileges]]'); + } + + if (type === 'default') { + picture = ''; + } else if (type === 'uploaded') { + picture = await user.getUserField(data.uid, 'uploadedpicture'); + } else if (type === 'external' && url) { + picture = validator.escape(url); + } else { + const returnData = await plugins.hooks.fire('filter:user.getPicture', { + uid: caller.uid, + type: type, + picture: undefined, + }); + picture = returnData && returnData.picture; + } + + const validBackgrounds = await user.getIconBackgrounds(caller.uid); + if (!validBackgrounds.includes(data.bgColor)) { + data.bgColor = validBackgrounds[0]; + } + + await user.updateProfile(caller.uid, { + uid: data.uid, + picture: picture, + 'icon:bgColor': data.bgColor, + }, ['picture', 'icon:bgColor']); +}; diff --git a/src/controllers/write/users.js b/src/controllers/write/users.js index 43aa2c0ccc..2469ae4b2a 100644 --- a/src/controllers/write/users.js +++ b/src/controllers/write/users.js @@ -76,6 +76,11 @@ Users.deleteMany = async (req, res) => { helpers.formatApiResponse(200, res); }; +Users.changePicture = async (req, res) => { + await api.users.changePicture(req, { ...req.body, uid: req.params.uid }); + helpers.formatApiResponse(200, res); +}; + Users.updateSettings = async (req, res) => { const settings = await api.users.updateSettings(req, { ...req.body, uid: req.params.uid }); helpers.formatApiResponse(200, res, settings); diff --git a/src/routes/write/users.js b/src/routes/write/users.js index 02a64e134f..418fa9897d 100644 --- a/src/routes/write/users.js +++ b/src/routes/write/users.js @@ -22,6 +22,7 @@ function authenticatedRoutes() { setupApiRoute(router, 'get', '/:uid', [...middlewares, middleware.assert.user], controllers.write.users.get); setupApiRoute(router, 'put', '/:uid', [...middlewares, middleware.assert.user], controllers.write.users.update); setupApiRoute(router, 'delete', '/:uid', [...middlewares, middleware.assert.user], controllers.write.users.delete); + setupApiRoute(router, 'put', '/:uid/picture', [...middlewares, middleware.assert.user], controllers.write.users.changePicture); setupApiRoute(router, 'delete', '/:uid/content', [...middlewares, middleware.assert.user], controllers.write.users.deleteContent); setupApiRoute(router, 'delete', '/:uid/account', [...middlewares, middleware.assert.user], controllers.write.users.deleteAccount); diff --git a/src/socket.io/user/picture.js b/src/socket.io/user/picture.js index a5a2fbbea7..186ab02835 100644 --- a/src/socket.io/user/picture.js +++ b/src/socket.io/user/picture.js @@ -3,42 +3,13 @@ const user = require('../../user'); const plugins = require('../../plugins'); +const websockets = require('../index'); +const api = require('../../api'); + module.exports = function (SocketUser) { SocketUser.changePicture = async function (socket, data) { - if (!socket.uid) { - throw new Error('[[error:invalid-uid]]'); - } - - if (!data) { - throw new Error('[[error:invalid-data]]'); - } - - const { type } = data; - let picture = ''; - await user.isAdminOrGlobalModOrSelf(socket.uid, data.uid); - if (type === 'default') { - picture = ''; - } else if (type === 'uploaded') { - picture = await user.getUserField(data.uid, 'uploadedpicture'); - } else { - const returnData = await plugins.hooks.fire('filter:user.getPicture', { - uid: socket.uid, - type: type, - picture: undefined, - }); - picture = returnData && returnData.picture; - } - - const validBackgrounds = await user.getIconBackgrounds(socket.uid); - if (!validBackgrounds.includes(data.bgColor)) { - data.bgColor = validBackgrounds[0]; - } - - await user.updateProfile(socket.uid, { - uid: data.uid, - picture: picture, - 'icon:bgColor': data.bgColor, - }, ['picture', 'icon:bgColor']); + websockets.warnDeprecated(socket, 'PUT /api/v3/users/:uid/picture'); + await api.users.changePicture(socket, data); }; SocketUser.removeUploadedPicture = async function (socket, data) { From cdaea61136f05e2f42a7aeb9f999f19e8517b8fb Mon Sep 17 00:00:00 2001 From: Julian Lam Date: Fri, 3 Sep 2021 15:53:25 -0400 Subject: [PATCH 16/30] fix: handle missing uid in deprecated socket call --- src/socket.io/user/picture.js | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/src/socket.io/user/picture.js b/src/socket.io/user/picture.js index 186ab02835..7de2ef7165 100644 --- a/src/socket.io/user/picture.js +++ b/src/socket.io/user/picture.js @@ -8,6 +8,10 @@ const api = require('../../api'); module.exports = function (SocketUser) { SocketUser.changePicture = async function (socket, data) { + if (!socket.uid) { + throw new Error('[[error:invalid-uid]]'); + } + websockets.warnDeprecated(socket, 'PUT /api/v3/users/:uid/picture'); await api.users.changePicture(socket, data); }; From 8cbad61e8a94f1dedfa308dc83da50d7f30d1879 Mon Sep 17 00:00:00 2001 From: Julian Lam Date: Fri, 3 Sep 2021 16:46:14 -0400 Subject: [PATCH 17/30] test: added test for external image via new change picture API --- test/helpers/index.js | 10 ++++++++++ test/user.js | 23 +++++++++++++++++++++++ 2 files changed, 33 insertions(+) diff --git a/test/helpers/index.js b/test/helpers/index.js index ecb2ebd0a4..79a0e9e41e 100644 --- a/test/helpers/index.js +++ b/test/helpers/index.js @@ -10,6 +10,16 @@ const utils = require('../../public/src/utils'); const helpers = module.exports; +helpers.getCsrfToken = async (jar) => { + const { csrf_token: token } = await requestAsync({ + url: `${nconf.get('url')}/api/config`, + json: true, + jar, + }); + + return token; +}; + helpers.loginUser = function (username, password, callback) { const jar = request.jar(); diff --git a/test/user.js b/test/user.js index 4c9a61cd86..e74eb8252d 100644 --- a/test/user.js +++ b/test/user.js @@ -5,6 +5,7 @@ const async = require('async'); const fs = require('fs'); const path = require('path'); const nconf = require('nconf'); +const validator = require('validator'); const request = require('request'); const requestAsync = require('request-promise-native'); const jwt = require('jsonwebtoken'); @@ -1070,6 +1071,28 @@ describe('User', () => { }); }); + it('should let you set an external image', async () => { + const token = await helpers.getCsrfToken(jar); + const body = await requestAsync(`${nconf.get('url')}/api/v3/users/${uid}/picture`, { + jar, + method: 'put', + json: true, + headers: { + 'x-csrf-token': token, + }, + body: { + type: 'external', + url: 'https://example.org/picture.jpg', + }, + }); + + assert(body && body.status && body.response); + assert.strictEqual(body.status.code, 'ok'); + + const picture = await User.getUserField(uid, 'picture'); + assert.strictEqual(picture, validator.escape('https://example.org/picture.jpg')); + }); + it('should fail to change user picture with invalid data', (done) => { socketUser.changePicture({ uid: uid }, null, (err) => { assert.equal(err.message, '[[error:invalid-data]]'); From 0b3ea5adb4ed4e302e78ca2305c7f7a5e246e931 Mon Sep 17 00:00:00 2001 From: Renovate Bot Date: Fri, 3 Sep 2021 21:05:03 +0000 Subject: [PATCH 18/30] fix(deps): update dependency nodebb-theme-vanilla to v12.1.3 --- install/package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/install/package.json b/install/package.json index de02ca25a2..1e2dd6e361 100644 --- a/install/package.json +++ b/install/package.json @@ -95,7 +95,7 @@ "nodebb-theme-lavender": "5.2.1", "nodebb-theme-persona": "11.2.5", "nodebb-theme-slick": "1.4.12", - "nodebb-theme-vanilla": "12.1.2", + "nodebb-theme-vanilla": "12.1.3", "nodebb-widget-essentials": "5.0.4", "nodemailer": "^6.5.0", "nprogress": "0.2.0", From 87ba768f5c5f060b4a3bf2ef9d303425a6f8aae8 Mon Sep 17 00:00:00 2001 From: Renovate Bot Date: Sun, 15 Aug 2021 11:23:02 +0000 Subject: [PATCH 19/30] chore(deps): update commitlint monorepo to v13 --- install/package.json | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/install/package.json b/install/package.json index 1e2dd6e361..4cf3e48156 100644 --- a/install/package.json +++ b/install/package.json @@ -142,8 +142,8 @@ }, "devDependencies": { "@apidevtools/swagger-parser": "10.0.3", - "@commitlint/cli": "12.1.4", - "@commitlint/config-angular": "12.1.4", + "@commitlint/cli": "13.1.0", + "@commitlint/config-angular": "13.1.0", "coveralls": "3.1.1", "eslint": "7.32.0", "eslint-config-nodebb": "0.0.2", From 856ba78a5f0c971dfd6d39a20a7d9fe25ceb4ec9 Mon Sep 17 00:00:00 2001 From: Julian Lam Date: Fri, 3 Sep 2021 17:13:55 -0400 Subject: [PATCH 20/30] fix: replace logic in isPrivilegedOrSelfAndPasswordMatch to use privileges.users.canEdit --- src/api/users.js | 9 ++------- 1 file changed, 2 insertions(+), 7 deletions(-) diff --git a/src/api/users.js b/src/api/users.js index 71d3a0c8f4..cbd64e7fd5 100644 --- a/src/api/users.js +++ b/src/api/users.js @@ -227,14 +227,9 @@ usersAPI.unban = async function (caller, data) { async function isPrivilegedOrSelfAndPasswordMatch(caller, data) { const { uid } = caller; const isSelf = parseInt(uid, 10) === parseInt(data.uid, 10); + const canEdit = await privileges.users.canEdit(uid, data.uid); - const [isAdmin, isTargetAdmin, isGlobalMod] = await Promise.all([ - user.isAdministrator(uid), - user.isAdministrator(data.uid), - user.isGlobalModerator(uid), - ]); - - if ((isTargetAdmin && !isAdmin) || (!isSelf && !(isAdmin || isGlobalMod))) { + if (!canEdit) { throw new Error('[[error:no-privileges]]'); } const [hasPassword, passwordMatch] = await Promise.all([ From 0ce4b87d856e7021a0d2394fcd60f8081c826ea5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Bar=C4=B1=C5=9F=20Soner=20U=C5=9Fakl=C4=B1?= Date: Fri, 3 Sep 2021 20:34:42 -0400 Subject: [PATCH 21/30] fix: #9781 (#9782) --- src/database/mongo/hash.js | 18 +++++++++++++++--- src/database/postgres/hash.js | 4 +++- src/database/redis/hash.js | 6 +++++- test/database/hash.js | 35 ++++++++++++++++++++++++++++++++++- 4 files changed, 57 insertions(+), 6 deletions(-) diff --git a/src/database/mongo/hash.js b/src/database/mongo/hash.js index 0829bbf8af..67daab7b16 100644 --- a/src/database/mongo/hash.js +++ b/src/database/mongo/hash.js @@ -14,6 +14,9 @@ module.exports = function (module) { } const writeData = helpers.serializeData(data); + if (!Object.keys(writeData).length) { + return; + } try { if (isArray) { const bulk = module.client.collection('objects').initializeUnorderedBulkOp(); @@ -39,9 +42,18 @@ module.exports = function (module) { const writeData = data.map(helpers.serializeData); try { - const bulk = module.client.collection('objects').initializeUnorderedBulkOp(); - keys.forEach((key, i) => bulk.find({ _key: key }).upsert().updateOne({ $set: writeData[i] })); - await bulk.execute(); + let bulk; + keys.forEach((key, i) => { + if (Object.keys(writeData[i]).length) { + if (!bulk) { + bulk = module.client.collection('objects').initializeUnorderedBulkOp(); + } + bulk.find({ _key: key }).upsert().updateOne({ $set: writeData[i] }); + } + }); + if (bulk) { + await bulk.execute(); + } } catch (err) { if (err && err.message.startsWith('E11000 duplicate key error')) { return await module.setObjectBulk(keys, data); diff --git a/src/database/postgres/hash.js b/src/database/postgres/hash.js index 1a733a3518..04b38713c2 100644 --- a/src/database/postgres/hash.js +++ b/src/database/postgres/hash.js @@ -11,7 +11,9 @@ module.exports = function (module) { if (data.hasOwnProperty('')) { delete data['']; } - + if (!Object.keys(data).length) { + return; + } await module.transaction(async (client) => { const dataString = JSON.stringify(data); async function setOne(key) { diff --git a/src/database/redis/hash.js b/src/database/redis/hash.js index 103cbc4a81..966a36eddd 100644 --- a/src/database/redis/hash.js +++ b/src/database/redis/hash.js @@ -41,7 +41,11 @@ module.exports = function (module) { return; } const batch = module.client.batch(); - keys.forEach((k, i) => batch.hmset(k, data[i])); + keys.forEach((k, i) => { + if (Object.keys(data[i]).length) { + batch.hmset(k, data[i]); + } + }); await helpers.execBatch(batch); cache.del(keys); }; diff --git a/test/database/hash.js b/test/database/hash.js index 39c4e39624..650afae8bf 100644 --- a/test/database/hash.js +++ b/test/database/hash.js @@ -72,7 +72,7 @@ describe('Hash methods', () => { }); }); - it('should set multiple keys to different okjects', async () => { + it('should set multiple keys to different objects', async () => { const keys = ['bulkKey1', 'bulkKey2']; const data = [{ foo: '1' }, { baz: 'baz' }]; @@ -80,6 +80,39 @@ describe('Hash methods', () => { const result = await db.getObjects(keys); assert.deepStrictEqual(result, data); }); + + it('should not error if object is empty', async () => { + const keys = ['bulkKey3', 'bulkKey4']; + const data = [{ foo: '1' }, { }]; + + await db.setObjectBulk(keys, data); + const result = await db.getObjects(keys); + assert.deepStrictEqual(result, [{ foo: '1' }, null]); + }); + + it('should not error if object is empty', async () => { + const keys = ['bulkKey5']; + const data = [{ }]; + + await db.setObjectBulk(keys, data); + const result = await db.getObjects(keys); + assert.deepStrictEqual(result, [null]); + }); + + it('should not error if object is empty', async () => { + const keys = ['bulkKey6', 'bulkKey7']; + const data = {}; + + await db.setObject(keys, data); + const result = await db.getObjects(keys); + assert.deepStrictEqual(result, [null, null]); + }); + + it('should not error if object is empty', async () => { + await db.setObject('emptykey', {}); + const result = await db.getObject('emptykey'); + assert.deepStrictEqual(result, null); + }); }); describe('setObjectField()', () => { From 2e1b99f504d67014a23e47b3573a351808b3dc55 Mon Sep 17 00:00:00 2001 From: "Misty (Bot)" Date: Sun, 5 Sep 2021 09:06:12 +0000 Subject: [PATCH 22/30] Latest translations and fallbacks --- public/language/fr/admin/manage/uploads.json | 4 ++-- public/language/fr/error.json | 6 +++--- public/language/vi/admin/manage/privileges.json | 2 +- 3 files changed, 6 insertions(+), 6 deletions(-) diff --git a/public/language/fr/admin/manage/uploads.json b/public/language/fr/admin/manage/uploads.json index a0a8608e07..8f1e276a6f 100644 --- a/public/language/fr/admin/manage/uploads.json +++ b/public/language/fr/admin/manage/uploads.json @@ -6,6 +6,6 @@ "size/filecount": "Taille / nombre de fichiers", "confirm-delete": "Voulez-vous vraiment supprimer ce fichier?", "filecount": "%1 fichiers", - "new-folder": "New Folder", - "name-new-folder": "Enter a name for new the folder" + "new-folder": "Nouveau Dossier", + "name-new-folder": "Entrez un nom pour le nouveau dossier" } \ No newline at end of file diff --git a/public/language/fr/error.json b/public/language/fr/error.json index 4ee0be6ce4..a3c870ca55 100644 --- a/public/language/fr/error.json +++ b/public/language/fr/error.json @@ -25,14 +25,14 @@ "invalid-event": "Événement non valide: %1", "local-login-disabled": "Le système de connexion local a été désactivé pour les comptes sans privilèges.", "csrf-invalid": "Nous ne pouvons pas vous connectez, probablement car votre session a expiré. Merci de réessayer.", - "invalid-path": "Invalid path", - "folder-exists": "Folder exists", + "invalid-path": "Chemin invalide", + "folder-exists": "Le dossier existe", "invalid-pagination-value": "Valeur de pagination invalide. Celle-ci doit être comprise entre %1 et %2.", "username-taken": "Nom d’utilisateur déjà utilisé", "email-taken": "Email déjà utilisé", "email-nochange": "Le mail saisi est déjà enregistré.", "email-invited": "Cet utilisateur a déjà été invité.", - "email-not-confirmed": "Posting in some categories or topics is enabled once your email is confirmed, please click here to send a confirmation email.", + "email-not-confirmed": "La publication dans certaines catégories ou sujets sera activée après confirmation de e-mail, veuillez cliquer ici pour envoyer un e-mail de confirmation.", "email-not-confirmed-chat": "Il ne vous est pas possible d'utiliser le chat tant que votre adresse email n'a pas été vérifiée. Veuillez cliquer ici pour confirmer votre adresse email.", "email-not-confirmed-email-sent": "Votre email n'a pas encore été confirmé, veuillez vérifier votre boîte mail. Vous ne pourrez pas poster ou discuter avant que votre email ne soit confirmé.", "no-email-to-confirm": "Votre compte n'a pas d'adresse mail définie. Un mail est nécessaire pour la récupération du compte. Veuillez cliquer ici pour entrer un courriel.", diff --git a/public/language/vi/admin/manage/privileges.json b/public/language/vi/admin/manage/privileges.json index 15ae622bc9..a41a2edd82 100644 --- a/public/language/vi/admin/manage/privileges.json +++ b/public/language/vi/admin/manage/privileges.json @@ -59,5 +59,5 @@ "alert.admin-warning": "Quản trị viên ngầm có tất cả các đặc quyền", "alert.copyPrivilegesFrom-title": "Chọn một danh mục để sao chép từ", "alert.copyPrivilegesFrom-warning": "Điều này sẽ sao chép %1 từ danh mục đã chọn.", - "alert.copyPrivilegesFromGroup-warning": "This will copy this group's set of %1 from the selected category." + "alert.copyPrivilegesFromGroup-warning": "Thao tác này sẽ sao chép cài đặt %1 của nhóm này từ danh mục đã chọn." } \ No newline at end of file From 90845200278c16ebf0a8ff15ada39f95c4fe7f7b Mon Sep 17 00:00:00 2001 From: "Misty (Bot)" Date: Mon, 6 Sep 2021 09:06:27 +0000 Subject: [PATCH 23/30] Latest translations and fallbacks --- public/language/it/admin/manage/privileges.json | 14 +++++++------- public/language/it/admin/manage/uploads.json | 4 ++-- public/language/it/error.json | 6 +++--- 3 files changed, 12 insertions(+), 12 deletions(-) diff --git a/public/language/it/admin/manage/privileges.json b/public/language/it/admin/manage/privileges.json index 032e6a844a..0da351c033 100644 --- a/public/language/it/admin/manage/privileges.json +++ b/public/language/it/admin/manage/privileges.json @@ -51,13 +51,13 @@ "alert.saved": "Modifiche ai privilegi salvate e applicate", "alert.confirm-discard": "Sei sicuro di voler annullare le modifiche ai privilegi?", "alert.discarded": "Modifiche ai privilegi ignorate", - "alert.confirm-copyToAll": "Are you sure you wish to apply this set of %1 to all categories?", - "alert.confirm-copyToAllGroup": "Are you sure you wish to apply this group's set of %1 to all categories?", - "alert.confirm-copyToChildren": "Are you sure you wish to apply this set of %1 to all descendant (child) categories?", - "alert.confirm-copyToChildrenGroup": "Are you sure you wish to apply this group's set of %1 to all descendant (child) categories?", + "alert.confirm-copyToAll": "Sei sicuro di voler applicare questa serie di %1 a tutte le categorie?", + "alert.confirm-copyToAllGroup": "Sei sicuro di voler applicare questa serie di %1 del gruppo a tutte le categorie?", + "alert.confirm-copyToChildren": "Sei sicuro di voler applicare questa serie di %1 a tutte le categorie discendenti (figli)?", + "alert.confirm-copyToChildrenGroup": "Sei sicuro di voler applicare questa serie di %1 del questo gruppo a tutte le categorie discendenti (figli)?", "alert.no-undo": "Questa azione non può essere annullata.", "alert.admin-warning": "Gli amministratori ottengono implicitamente tutti i privilegi", - "alert.copyPrivilegesFrom-title": "Select a category to copy from", - "alert.copyPrivilegesFrom-warning": "This will copy %1 from the selected category.", - "alert.copyPrivilegesFromGroup-warning": "This will copy this group's set of %1 from the selected category." + "alert.copyPrivilegesFrom-title": "Seleziona una categoria da cui copiare", + "alert.copyPrivilegesFrom-warning": "Questo copierà 1% dalla categoria selezionata.", + "alert.copyPrivilegesFromGroup-warning": "Questo copierà la serie di %1 da questo gruppo dalla categoria selezionata." } \ No newline at end of file diff --git a/public/language/it/admin/manage/uploads.json b/public/language/it/admin/manage/uploads.json index 7d12c43dd0..5d992eec52 100644 --- a/public/language/it/admin/manage/uploads.json +++ b/public/language/it/admin/manage/uploads.json @@ -6,6 +6,6 @@ "size/filecount": "Dimensione / Numero file", "confirm-delete": "Vuoi davvero cancellare questo file?", "filecount": "%1 file", - "new-folder": "New Folder", - "name-new-folder": "Enter a name for new the folder" + "new-folder": "Nuova cartella", + "name-new-folder": "Inserisci un nome per la nuova cartella" } \ No newline at end of file diff --git a/public/language/it/error.json b/public/language/it/error.json index 166ee800fa..c4a2350d94 100644 --- a/public/language/it/error.json +++ b/public/language/it/error.json @@ -25,14 +25,14 @@ "invalid-event": "Evento non valido: %1", "local-login-disabled": "Il sistema di accesso locale è stato disabilitato per gli account senza privilegi.", "csrf-invalid": "Non siamo riusciti a farti accedere, probabilmente perché la sessione è scaduta. Per favore riprova.", - "invalid-path": "Invalid path", - "folder-exists": "Folder exists", + "invalid-path": "Percorso non valido", + "folder-exists": "La cartella esiste", "invalid-pagination-value": "Valore di impaginazione non valido, deve essere almeno %1 ed al massimo %2", "username-taken": "Nome utente già esistente", "email-taken": "Email già esistente", "email-nochange": "L'email inserita è la stessa dell'email già presente in archivio.", "email-invited": "L'email è già stata invitata", - "email-not-confirmed": "Posting in some categories or topics is enabled once your email is confirmed, please click here to send a confirmation email.", + "email-not-confirmed": "Sarai abilitato a postare in alcune categorie o discussioni una volta che la tua email sarà confermata, per favore clicca qui per inviare una email di conferma.", "email-not-confirmed-chat": "Non puoi chattare finché non confermi la tua email, per favore clicca qui per confermare la tua email.", "email-not-confirmed-email-sent": "La tua email non è stata ancora confermata, controlla la tua casella di posta per l'email di conferma. Non potrai pubblicare post o chattare fino a quando la tua email non sarà confermata.", "no-email-to-confirm": "Il tuo account non ha un'email impostata. Un'email è necessaria per il recupero dell'account. Clicca qui per inserire un'email.", From 338f90fc5ef1aebee090a98e9ccc03ea27bf0996 Mon Sep 17 00:00:00 2001 From: Renovate Bot Date: Mon, 6 Sep 2021 18:38:20 +0000 Subject: [PATCH 24/30] fix(deps): update dependency nodebb-plugin-dbsearch to v5.0.3 --- install/package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/install/package.json b/install/package.json index 4cf3e48156..2dce79299b 100644 --- a/install/package.json +++ b/install/package.json @@ -85,7 +85,7 @@ "@nodebb/bootswatch": "3.4.2", "nconf": "^0.11.2", "nodebb-plugin-composer-default": "7.0.2", - "nodebb-plugin-dbsearch": "5.0.2", + "nodebb-plugin-dbsearch": "5.0.3", "nodebb-plugin-emoji": "^3.5.0", "nodebb-plugin-emoji-android": "2.0.5", "nodebb-plugin-markdown": "8.14.3", From a17ffcd094114f525eae3729de8186c98e3fd5ff Mon Sep 17 00:00:00 2001 From: "Misty (Bot)" Date: Tue, 7 Sep 2021 09:06:24 +0000 Subject: [PATCH 25/30] Latest translations and fallbacks --- public/language/sl/admin/admin.json | 6 +++--- public/language/sl/category.json | 4 ++-- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/public/language/sl/admin/admin.json b/public/language/sl/admin/admin.json index 36f0fdde60..3afbbf5ab7 100644 --- a/public/language/sl/admin/admin.json +++ b/public/language/sl/admin/admin.json @@ -1,7 +1,7 @@ { - "alert.confirm-rebuild-and-restart": "Are you sure you wish to rebuild and restart NodeBB?", - "alert.confirm-restart": "Are you sure you wish to restart NodeBB?", + "alert.confirm-rebuild-and-restart": "Ste prepričani, da želite znova zagnati NodeBB?", + "alert.confirm-restart": "Ste prepričani, da želite znova zagnati NodeBB?", - "acp-title": "%1 | NodeBB Admin Control Panel", + "acp-title": "NodeBB administracijska nadzorna plošča", "settings-header-contents": "Contents" } \ No newline at end of file diff --git a/public/language/sl/category.json b/public/language/sl/category.json index 6a7fda2a16..e96e8805f9 100644 --- a/public/language/sl/category.json +++ b/public/language/sl/category.json @@ -10,9 +10,9 @@ "watch": "Spremljaj.", "ignore": "Prezri.", "watching": "Spremljano", - "not-watching": "Not Watching", + "not-watching": "Ni spremljano", "ignoring": "Prezrto", - "watching.description": "Show topics in unread and recent", + "watching.description": "Prikaži teme v nedavno in nazadnje", "not-watching.description": "Do not show topics in unread, show in recent", "ignoring.description": "Do not show topics in unread and recent", "watching.message": "You are now watching updates from this category and all subcategories", From ac6cd02fa2a582de4c0209a92cc1be556ff3cafe Mon Sep 17 00:00:00 2001 From: Renovate Bot Date: Tue, 7 Sep 2021 10:58:58 +0000 Subject: [PATCH 26/30] fix(deps): update dependency sharp to v0.29.1 --- install/package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/install/package.json b/install/package.json index 2dce79299b..1cb2211274 100644 --- a/install/package.json +++ b/install/package.json @@ -116,7 +116,7 @@ "sanitize-html": "^2.3.2", "semver": "^7.3.4", "serve-favicon": "^2.5.0", - "sharp": "0.29.0", + "sharp": "0.29.1", "sitemap": "^7.0.0", "slideout": "1.0.1", "socket.io": "4.2.0", From 580a016b0ecc5e503f82dd9279066f16aeb1427c Mon Sep 17 00:00:00 2001 From: psychobunny Date: Tue, 7 Sep 2021 10:22:09 -0400 Subject: [PATCH 27/30] fix: #9767 ACP change group icon fix --- public/less/admin/manage/groups.less | 14 ++++++++++++++ 1 file changed, 14 insertions(+) diff --git a/public/less/admin/manage/groups.less b/public/less/admin/manage/groups.less index dda50c5c54..2183cc748c 100644 --- a/public/less/admin/manage/groups.less +++ b/public/less/admin/manage/groups.less @@ -35,4 +35,18 @@ [component="category/list"] li { cursor: pointer; } + + .fa-nbb-none { + border: 1px dotted black; + height: 35px; + width: 35px; + } + + .fa-icons .fa-nbb-none { + vertical-align: -6px; + } + + #group-icon-preview.fa-nbb-none { + display: none; + } } \ No newline at end of file From a7855c4cc4993b30ceaed6bc658bddfd70ba6b03 Mon Sep 17 00:00:00 2001 From: psychobunny Date: Tue, 7 Sep 2021 10:48:03 -0400 Subject: [PATCH 28/30] fix: dashboard graph controls --- src/views/admin/partials/dashboard/graph.tpl | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/src/views/admin/partials/dashboard/graph.tpl b/src/views/admin/partials/dashboard/graph.tpl index d2604f2332..ee55cd7ce1 100644 --- a/src/views/admin/partials/dashboard/graph.tpl +++ b/src/views/admin/partials/dashboard/graph.tpl @@ -2,8 +2,10 @@
[[admin/dashboard:forum-traffic]]
- - + +
+
+
From bf0c02a71e744d349fe17bc7b89159c9d6cd3ce7 Mon Sep 17 00:00:00 2001 From: psychobunny Date: Tue, 7 Sep 2021 11:49:43 -0400 Subject: [PATCH 29/30] feat: a slightly less ugly rewards panel --- .../language/en-GB/admin/extend/rewards.json | 2 - public/less/admin/extend/rewards.less | 30 ++++ public/src/admin/extend/rewards.js | 4 +- src/views/admin/extend/rewards.tpl | 144 +++++++++--------- 4 files changed, 107 insertions(+), 73 deletions(-) diff --git a/public/language/en-GB/admin/extend/rewards.json b/public/language/en-GB/admin/extend/rewards.json index 5383a90b33..df89d441a7 100644 --- a/public/language/en-GB/admin/extend/rewards.json +++ b/public/language/en-GB/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Delete", "enable": "Enable", "disable": "Disable", - "control-panel": "Rewards Control", - "new-reward": "New Reward", "alert.delete-success": "Successfully deleted reward", "alert.no-inputs-found": "Illegal reward - no inputs found!", diff --git a/public/less/admin/extend/rewards.less b/public/less/admin/extend/rewards.less index 2dc84b5bc3..3972b16de3 100644 --- a/public/less/admin/extend/rewards.less +++ b/public/less/admin/extend/rewards.less @@ -16,6 +16,36 @@ > li { border-bottom: 1px solid #ddd; margin-bottom: 20px; + &:last-child { + border-bottom: 0; + } + } + } + + .rewards { width: 100%; } + + .well { + border-radius: 2px; + border-width: 2px; + color: #333; + + &.if-block { + border-color: @brand-primary; + } + &.this-block { + border-color: @brand-warning; + } + &.then-block { + border-color: @brand-success; + } + &.reward-block { + border-color: @brand-success; + background-color: lighten(@brand-success, 15%); + color: #fff; + a, select, input { color: #fff; } + select > option { color: #333; } + width: 100%; + min-height: 110px; } } } \ No newline at end of file diff --git a/public/src/admin/extend/rewards.js b/public/src/admin/extend/rewards.js index 3850b24017..7df62a7e15 100644 --- a/public/src/admin/extend/rewards.js +++ b/public/src/admin/extend/rewards.js @@ -95,13 +95,13 @@ define('admin/extend/rewards', [], function () { html += '
'; diff --git a/src/views/admin/extend/rewards.tpl b/src/views/admin/extend/rewards.tpl index bd226cc39d..456ab7d379 100644 --- a/src/views/admin/extend/rewards.tpl +++ b/src/views/admin/extend/rewards.tpl @@ -1,76 +1,82 @@ -
-
-
-
[[admin/extend/rewards:rewards]]
-
-
    - {{{ each active }}} -
  • -
    -
    -
    - -
    -
    -
    - - -
    -
    -
    - -
    -
    -
    -
    -
    -
    - -
    -
    -
    -
    - - [[admin/extend/rewards:zero-infinite]] -
    -
    -
    - - - - - - +
    +
      + {{{ each active }}} +
    • +
      +
      +
      +
      +
      + +
      +
      +
      +
      +
      + +
      +
      + +
      -
      -
    • - {{{ end }}} -
    +
    +
    + +
    + +
    +
    +
    +
    +
    +
    +
    + +
    +
    +
    +
    + +
    +
    -
    -
-
-
-
[[admin/extend/rewards:control-panel]]
-
- - +
+
+ + + + + + +
-
-
+
+ + {{{ end }}} + +
+ +
+ + +
\ No newline at end of file From 507517fce5248ad37f6a239fce16ae92d0e0f5b0 Mon Sep 17 00:00:00 2001 From: "Misty (Bot)" Date: Wed, 8 Sep 2021 09:06:50 +0000 Subject: [PATCH 30/30] Latest translations and fallbacks --- public/language/ar/admin/extend/rewards.json | 2 -- public/language/bg/admin/extend/rewards.json | 2 -- public/language/bn/admin/extend/rewards.json | 2 -- public/language/cs/admin/extend/rewards.json | 2 -- public/language/da/admin/extend/rewards.json | 2 -- public/language/de/admin/extend/rewards.json | 2 -- public/language/el/admin/extend/rewards.json | 2 -- public/language/en-US/admin/extend/rewards.json | 2 -- public/language/en-x-pirate/admin/extend/rewards.json | 2 -- public/language/es/admin/extend/rewards.json | 2 -- public/language/et/admin/extend/rewards.json | 2 -- public/language/fa-IR/admin/extend/rewards.json | 2 -- public/language/fi/admin/extend/rewards.json | 2 -- public/language/fr/admin/extend/rewards.json | 2 -- public/language/gl/admin/extend/rewards.json | 2 -- public/language/he/admin/extend/rewards.json | 2 -- public/language/hr/admin/extend/rewards.json | 2 -- public/language/hu/admin/extend/rewards.json | 2 -- public/language/id/admin/extend/rewards.json | 2 -- public/language/it/admin/extend/rewards.json | 2 -- public/language/ja/admin/extend/rewards.json | 2 -- public/language/ko/admin/extend/rewards.json | 2 -- public/language/lt/admin/extend/rewards.json | 2 -- public/language/lv/admin/extend/rewards.json | 2 -- public/language/ms/admin/extend/rewards.json | 2 -- public/language/nb/admin/extend/rewards.json | 2 -- public/language/nl/admin/extend/rewards.json | 2 -- public/language/pl/admin/extend/rewards.json | 2 -- public/language/pt-BR/admin/extend/rewards.json | 2 -- public/language/pt-PT/admin/extend/rewards.json | 2 -- public/language/ro/admin/extend/rewards.json | 2 -- public/language/ru/admin/extend/rewards.json | 2 -- public/language/rw/admin/extend/rewards.json | 2 -- public/language/sc/admin/extend/rewards.json | 2 -- public/language/sk/admin/extend/rewards.json | 2 -- public/language/sl/admin/extend/rewards.json | 2 -- public/language/sr/admin/extend/rewards.json | 2 -- public/language/sv/admin/extend/rewards.json | 2 -- public/language/th/admin/extend/rewards.json | 2 -- public/language/tr/admin/extend/rewards.json | 2 -- public/language/uk/admin/extend/rewards.json | 2 -- public/language/vi/admin/extend/rewards.json | 2 -- public/language/zh-CN/admin/extend/rewards.json | 2 -- public/language/zh-TW/admin/extend/rewards.json | 2 -- 44 files changed, 88 deletions(-) diff --git a/public/language/ar/admin/extend/rewards.json b/public/language/ar/admin/extend/rewards.json index 5383a90b33..df89d441a7 100644 --- a/public/language/ar/admin/extend/rewards.json +++ b/public/language/ar/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Delete", "enable": "Enable", "disable": "Disable", - "control-panel": "Rewards Control", - "new-reward": "New Reward", "alert.delete-success": "Successfully deleted reward", "alert.no-inputs-found": "Illegal reward - no inputs found!", diff --git a/public/language/bg/admin/extend/rewards.json b/public/language/bg/admin/extend/rewards.json index 890cc63d9e..d8860e3193 100644 --- a/public/language/bg/admin/extend/rewards.json +++ b/public/language/bg/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Изтриване", "enable": "Включване", "disable": "Изключване", - "control-panel": "Управление на наградите", - "new-reward": "Нова награда", "alert.delete-success": "Наградата е изтрита успешно", "alert.no-inputs-found": "Неправомерна награда — няма нищо въведено!", diff --git a/public/language/bn/admin/extend/rewards.json b/public/language/bn/admin/extend/rewards.json index 5383a90b33..df89d441a7 100644 --- a/public/language/bn/admin/extend/rewards.json +++ b/public/language/bn/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Delete", "enable": "Enable", "disable": "Disable", - "control-panel": "Rewards Control", - "new-reward": "New Reward", "alert.delete-success": "Successfully deleted reward", "alert.no-inputs-found": "Illegal reward - no inputs found!", diff --git a/public/language/cs/admin/extend/rewards.json b/public/language/cs/admin/extend/rewards.json index dd95f17371..9f0d26cfc3 100644 --- a/public/language/cs/admin/extend/rewards.json +++ b/public/language/cs/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Odstranit", "enable": "Povolit", "disable": "Zakázat", - "control-panel": "Ovládací panel odměn", - "new-reward": "Nová odměna", "alert.delete-success": "Odměna byla úspěšně smazána", "alert.no-inputs-found": "Nepovolená odměna – nebyl nalezen žádný záznam.", diff --git a/public/language/da/admin/extend/rewards.json b/public/language/da/admin/extend/rewards.json index 5383a90b33..df89d441a7 100644 --- a/public/language/da/admin/extend/rewards.json +++ b/public/language/da/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Delete", "enable": "Enable", "disable": "Disable", - "control-panel": "Rewards Control", - "new-reward": "New Reward", "alert.delete-success": "Successfully deleted reward", "alert.no-inputs-found": "Illegal reward - no inputs found!", diff --git a/public/language/de/admin/extend/rewards.json b/public/language/de/admin/extend/rewards.json index 38c39fcf44..7a6eef6513 100644 --- a/public/language/de/admin/extend/rewards.json +++ b/public/language/de/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Entfernen", "enable": "Aktivieren", "disable": "Deaktivieren", - "control-panel": "Belohnungseinstellungen", - "new-reward": "Neue Belohnung", "alert.delete-success": "Die Belohnung wurde erfolgreich gelöscht", "alert.no-inputs-found": "Ungültige Belohnung - keine Eingaben gefunden!", diff --git a/public/language/el/admin/extend/rewards.json b/public/language/el/admin/extend/rewards.json index 5383a90b33..df89d441a7 100644 --- a/public/language/el/admin/extend/rewards.json +++ b/public/language/el/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Delete", "enable": "Enable", "disable": "Disable", - "control-panel": "Rewards Control", - "new-reward": "New Reward", "alert.delete-success": "Successfully deleted reward", "alert.no-inputs-found": "Illegal reward - no inputs found!", diff --git a/public/language/en-US/admin/extend/rewards.json b/public/language/en-US/admin/extend/rewards.json index 5383a90b33..df89d441a7 100644 --- a/public/language/en-US/admin/extend/rewards.json +++ b/public/language/en-US/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Delete", "enable": "Enable", "disable": "Disable", - "control-panel": "Rewards Control", - "new-reward": "New Reward", "alert.delete-success": "Successfully deleted reward", "alert.no-inputs-found": "Illegal reward - no inputs found!", diff --git a/public/language/en-x-pirate/admin/extend/rewards.json b/public/language/en-x-pirate/admin/extend/rewards.json index 5383a90b33..df89d441a7 100644 --- a/public/language/en-x-pirate/admin/extend/rewards.json +++ b/public/language/en-x-pirate/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Delete", "enable": "Enable", "disable": "Disable", - "control-panel": "Rewards Control", - "new-reward": "New Reward", "alert.delete-success": "Successfully deleted reward", "alert.no-inputs-found": "Illegal reward - no inputs found!", diff --git a/public/language/es/admin/extend/rewards.json b/public/language/es/admin/extend/rewards.json index 44eb3f7108..98ded7cfa7 100644 --- a/public/language/es/admin/extend/rewards.json +++ b/public/language/es/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Eliminar", "enable": "Habilitar", "disable": "Deshabilitar", - "control-panel": "Control de recompensas", - "new-reward": "Nueva Recompensa", "alert.delete-success": "Recompensa eliminada con éxito", "alert.no-inputs-found": "¡Recompensa ilegal - no se encontraron inputs!", diff --git a/public/language/et/admin/extend/rewards.json b/public/language/et/admin/extend/rewards.json index 5383a90b33..df89d441a7 100644 --- a/public/language/et/admin/extend/rewards.json +++ b/public/language/et/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Delete", "enable": "Enable", "disable": "Disable", - "control-panel": "Rewards Control", - "new-reward": "New Reward", "alert.delete-success": "Successfully deleted reward", "alert.no-inputs-found": "Illegal reward - no inputs found!", diff --git a/public/language/fa-IR/admin/extend/rewards.json b/public/language/fa-IR/admin/extend/rewards.json index 5383a90b33..df89d441a7 100644 --- a/public/language/fa-IR/admin/extend/rewards.json +++ b/public/language/fa-IR/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Delete", "enable": "Enable", "disable": "Disable", - "control-panel": "Rewards Control", - "new-reward": "New Reward", "alert.delete-success": "Successfully deleted reward", "alert.no-inputs-found": "Illegal reward - no inputs found!", diff --git a/public/language/fi/admin/extend/rewards.json b/public/language/fi/admin/extend/rewards.json index 5383a90b33..df89d441a7 100644 --- a/public/language/fi/admin/extend/rewards.json +++ b/public/language/fi/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Delete", "enable": "Enable", "disable": "Disable", - "control-panel": "Rewards Control", - "new-reward": "New Reward", "alert.delete-success": "Successfully deleted reward", "alert.no-inputs-found": "Illegal reward - no inputs found!", diff --git a/public/language/fr/admin/extend/rewards.json b/public/language/fr/admin/extend/rewards.json index b1db437fc0..9fb342ce60 100644 --- a/public/language/fr/admin/extend/rewards.json +++ b/public/language/fr/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Supprimer", "enable": "Activer", "disable": "Désactiver", - "control-panel": "Contrôle des récompenses", - "new-reward": "Nouvelle récompense", "alert.delete-success": "Récompense supprimée", "alert.no-inputs-found": "Récompense invalide - aucune entrée trouvée !", diff --git a/public/language/gl/admin/extend/rewards.json b/public/language/gl/admin/extend/rewards.json index 5383a90b33..df89d441a7 100644 --- a/public/language/gl/admin/extend/rewards.json +++ b/public/language/gl/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Delete", "enable": "Enable", "disable": "Disable", - "control-panel": "Rewards Control", - "new-reward": "New Reward", "alert.delete-success": "Successfully deleted reward", "alert.no-inputs-found": "Illegal reward - no inputs found!", diff --git a/public/language/he/admin/extend/rewards.json b/public/language/he/admin/extend/rewards.json index 55adfcb6e2..12bc679568 100644 --- a/public/language/he/admin/extend/rewards.json +++ b/public/language/he/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "מחק", "enable": "הפעל", "disable": "השבת", - "control-panel": "בקרת תגמולים", - "new-reward": "תגמול חדש", "alert.delete-success": "תגמול נמחק בהצלחה", "alert.no-inputs-found": "תגמול לא חוקי - לא נמצא מידע!", diff --git a/public/language/hr/admin/extend/rewards.json b/public/language/hr/admin/extend/rewards.json index 5e20c3872f..d8198466a2 100644 --- a/public/language/hr/admin/extend/rewards.json +++ b/public/language/hr/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Obriši", "enable": "Omogući", "disable": "onemogući", - "control-panel": "Kontrola nagrada", - "new-reward": "Nova nagrada", "alert.delete-success": "Uspješno obrisana nagrada", "alert.no-inputs-found": "Ilegalna nagrada - nije pronađen unos!", diff --git a/public/language/hu/admin/extend/rewards.json b/public/language/hu/admin/extend/rewards.json index 1258e3a0c6..d5fe130fe8 100644 --- a/public/language/hu/admin/extend/rewards.json +++ b/public/language/hu/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Törlés", "enable": "Engedélyezés", "disable": "Tiltás", - "control-panel": "Jutalom vezérlés", - "new-reward": "Új jutalom", "alert.delete-success": "Jutalom sikeresen törölve", "alert.no-inputs-found": "Helytelen jutalom - nem található bevitel!", diff --git a/public/language/id/admin/extend/rewards.json b/public/language/id/admin/extend/rewards.json index 5383a90b33..df89d441a7 100644 --- a/public/language/id/admin/extend/rewards.json +++ b/public/language/id/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Delete", "enable": "Enable", "disable": "Disable", - "control-panel": "Rewards Control", - "new-reward": "New Reward", "alert.delete-success": "Successfully deleted reward", "alert.no-inputs-found": "Illegal reward - no inputs found!", diff --git a/public/language/it/admin/extend/rewards.json b/public/language/it/admin/extend/rewards.json index 1f1e6bc50f..7778999fbd 100644 --- a/public/language/it/admin/extend/rewards.json +++ b/public/language/it/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Elimina", "enable": "Abilita", "disable": "Disabilita", - "control-panel": "Controllo dei premi", - "new-reward": "Nuovo premio", "alert.delete-success": "Premi eliminati con successo", "alert.no-inputs-found": "Premio illegale - immissioni non trovate!", diff --git a/public/language/ja/admin/extend/rewards.json b/public/language/ja/admin/extend/rewards.json index 3023baeba3..72ef6500b8 100644 --- a/public/language/ja/admin/extend/rewards.json +++ b/public/language/ja/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "削除", "enable": "有効", "disable": "無効", - "control-panel": "報酬コントロール", - "new-reward": "新しい報酬", "alert.delete-success": "報酬を削除しました", "alert.no-inputs-found": "違法報酬 - 入力が見つかりません!", diff --git a/public/language/ko/admin/extend/rewards.json b/public/language/ko/admin/extend/rewards.json index ac23d6e380..be8bd8cf85 100644 --- a/public/language/ko/admin/extend/rewards.json +++ b/public/language/ko/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "삭제", "enable": "활성화", "disable": "비활성화", - "control-panel": "보상 제어판", - "new-reward": "새로운 보상", "alert.delete-success": "성공적으로 보상을 삭제했습니다.", "alert.no-inputs-found": "잘못된 보상 - 입력값이 없습니다!", diff --git a/public/language/lt/admin/extend/rewards.json b/public/language/lt/admin/extend/rewards.json index 5383a90b33..df89d441a7 100644 --- a/public/language/lt/admin/extend/rewards.json +++ b/public/language/lt/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Delete", "enable": "Enable", "disable": "Disable", - "control-panel": "Rewards Control", - "new-reward": "New Reward", "alert.delete-success": "Successfully deleted reward", "alert.no-inputs-found": "Illegal reward - no inputs found!", diff --git a/public/language/lv/admin/extend/rewards.json b/public/language/lv/admin/extend/rewards.json index ae99c8e088..97cf227477 100644 --- a/public/language/lv/admin/extend/rewards.json +++ b/public/language/lv/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Izdzēst", "enable": "Iespējot", "disable": "Atspējot", - "control-panel": "Balvu vadības panelis", - "new-reward": "Jauna balva", "alert.delete-success": "Veiksmīgi izdzēsta balva", "alert.no-inputs-found": "Nederīga balva - nav ievažu!", diff --git a/public/language/ms/admin/extend/rewards.json b/public/language/ms/admin/extend/rewards.json index 5383a90b33..df89d441a7 100644 --- a/public/language/ms/admin/extend/rewards.json +++ b/public/language/ms/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Delete", "enable": "Enable", "disable": "Disable", - "control-panel": "Rewards Control", - "new-reward": "New Reward", "alert.delete-success": "Successfully deleted reward", "alert.no-inputs-found": "Illegal reward - no inputs found!", diff --git a/public/language/nb/admin/extend/rewards.json b/public/language/nb/admin/extend/rewards.json index 5383a90b33..df89d441a7 100644 --- a/public/language/nb/admin/extend/rewards.json +++ b/public/language/nb/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Delete", "enable": "Enable", "disable": "Disable", - "control-panel": "Rewards Control", - "new-reward": "New Reward", "alert.delete-success": "Successfully deleted reward", "alert.no-inputs-found": "Illegal reward - no inputs found!", diff --git a/public/language/nl/admin/extend/rewards.json b/public/language/nl/admin/extend/rewards.json index 5383a90b33..df89d441a7 100644 --- a/public/language/nl/admin/extend/rewards.json +++ b/public/language/nl/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Delete", "enable": "Enable", "disable": "Disable", - "control-panel": "Rewards Control", - "new-reward": "New Reward", "alert.delete-success": "Successfully deleted reward", "alert.no-inputs-found": "Illegal reward - no inputs found!", diff --git a/public/language/pl/admin/extend/rewards.json b/public/language/pl/admin/extend/rewards.json index 41694a7ed8..afe04e15af 100644 --- a/public/language/pl/admin/extend/rewards.json +++ b/public/language/pl/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Usuń", "enable": "Włącz", "disable": "Wyłącz", - "control-panel": "Ustawienia nagród", - "new-reward": "Nowa nagroda", "alert.delete-success": "Pomyślnie usunięto nagrodę", "alert.no-inputs-found": "Niepoprawnie dodana nagroda ", diff --git a/public/language/pt-BR/admin/extend/rewards.json b/public/language/pt-BR/admin/extend/rewards.json index 4b9c21f169..08b1de8119 100644 --- a/public/language/pt-BR/admin/extend/rewards.json +++ b/public/language/pt-BR/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Deletar", "enable": "Ativar", "disable": "Desativar", - "control-panel": "Controle de Recompensas", - "new-reward": "Nova Recompensa", "alert.delete-success": "Recompensa excluída com sucesso", "alert.no-inputs-found": "Recompensa ilegal - nenhuma entrada encontrada!", diff --git a/public/language/pt-PT/admin/extend/rewards.json b/public/language/pt-PT/admin/extend/rewards.json index 7fab3c6679..346eb49e2a 100644 --- a/public/language/pt-PT/admin/extend/rewards.json +++ b/public/language/pt-PT/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Apagar", "enable": "Ativar", "disable": "Desativar", - "control-panel": "Controlo de Recompensas", - "new-reward": "Nova Recompensa", "alert.delete-success": "Recompensa apagada com sucesso", "alert.no-inputs-found": "Recompensa ilegal - não foram encontradas entradas!", diff --git a/public/language/ro/admin/extend/rewards.json b/public/language/ro/admin/extend/rewards.json index 5383a90b33..df89d441a7 100644 --- a/public/language/ro/admin/extend/rewards.json +++ b/public/language/ro/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Delete", "enable": "Enable", "disable": "Disable", - "control-panel": "Rewards Control", - "new-reward": "New Reward", "alert.delete-success": "Successfully deleted reward", "alert.no-inputs-found": "Illegal reward - no inputs found!", diff --git a/public/language/ru/admin/extend/rewards.json b/public/language/ru/admin/extend/rewards.json index 616afc7178..d6cc9c4623 100644 --- a/public/language/ru/admin/extend/rewards.json +++ b/public/language/ru/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Удалить", "enable": "Включить", "disable": "Выключить", - "control-panel": "Управление наградами", - "new-reward": "Новая награда", "alert.delete-success": "Награда успешно удалена", "alert.no-inputs-found": "Некорректная награда!", diff --git a/public/language/rw/admin/extend/rewards.json b/public/language/rw/admin/extend/rewards.json index 5383a90b33..df89d441a7 100644 --- a/public/language/rw/admin/extend/rewards.json +++ b/public/language/rw/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Delete", "enable": "Enable", "disable": "Disable", - "control-panel": "Rewards Control", - "new-reward": "New Reward", "alert.delete-success": "Successfully deleted reward", "alert.no-inputs-found": "Illegal reward - no inputs found!", diff --git a/public/language/sc/admin/extend/rewards.json b/public/language/sc/admin/extend/rewards.json index 5383a90b33..df89d441a7 100644 --- a/public/language/sc/admin/extend/rewards.json +++ b/public/language/sc/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Delete", "enable": "Enable", "disable": "Disable", - "control-panel": "Rewards Control", - "new-reward": "New Reward", "alert.delete-success": "Successfully deleted reward", "alert.no-inputs-found": "Illegal reward - no inputs found!", diff --git a/public/language/sk/admin/extend/rewards.json b/public/language/sk/admin/extend/rewards.json index e5a4a84acd..87a475ac61 100644 --- a/public/language/sk/admin/extend/rewards.json +++ b/public/language/sk/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Odstrániť", "enable": "Povoliť", "disable": "Zakázať", - "control-panel": "Kontrola odmien", - "new-reward": "Nová odmena", "alert.delete-success": "Odmena bola úspešne vymazaná", "alert.no-inputs-found": "Nepovolená odmena - nebol nájdený žiadny záznam.", diff --git a/public/language/sl/admin/extend/rewards.json b/public/language/sl/admin/extend/rewards.json index 5383a90b33..df89d441a7 100644 --- a/public/language/sl/admin/extend/rewards.json +++ b/public/language/sl/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Delete", "enable": "Enable", "disable": "Disable", - "control-panel": "Rewards Control", - "new-reward": "New Reward", "alert.delete-success": "Successfully deleted reward", "alert.no-inputs-found": "Illegal reward - no inputs found!", diff --git a/public/language/sr/admin/extend/rewards.json b/public/language/sr/admin/extend/rewards.json index 5383a90b33..df89d441a7 100644 --- a/public/language/sr/admin/extend/rewards.json +++ b/public/language/sr/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Delete", "enable": "Enable", "disable": "Disable", - "control-panel": "Rewards Control", - "new-reward": "New Reward", "alert.delete-success": "Successfully deleted reward", "alert.no-inputs-found": "Illegal reward - no inputs found!", diff --git a/public/language/sv/admin/extend/rewards.json b/public/language/sv/admin/extend/rewards.json index 5383a90b33..df89d441a7 100644 --- a/public/language/sv/admin/extend/rewards.json +++ b/public/language/sv/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Delete", "enable": "Enable", "disable": "Disable", - "control-panel": "Rewards Control", - "new-reward": "New Reward", "alert.delete-success": "Successfully deleted reward", "alert.no-inputs-found": "Illegal reward - no inputs found!", diff --git a/public/language/th/admin/extend/rewards.json b/public/language/th/admin/extend/rewards.json index 5383a90b33..df89d441a7 100644 --- a/public/language/th/admin/extend/rewards.json +++ b/public/language/th/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Delete", "enable": "Enable", "disable": "Disable", - "control-panel": "Rewards Control", - "new-reward": "New Reward", "alert.delete-success": "Successfully deleted reward", "alert.no-inputs-found": "Illegal reward - no inputs found!", diff --git a/public/language/tr/admin/extend/rewards.json b/public/language/tr/admin/extend/rewards.json index ff2dca964a..282c929757 100644 --- a/public/language/tr/admin/extend/rewards.json +++ b/public/language/tr/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Sil", "enable": "Etkinleştir", "disable": "Etkinsizleştir", - "control-panel": "Ödül Kontrol Paneli", - "new-reward": "Yeni Ödül Ekle", "alert.delete-success": "Ödül başarıyla silindi", "alert.no-inputs-found": "Usulsüz ödül - girdi bulunamadı!", diff --git a/public/language/uk/admin/extend/rewards.json b/public/language/uk/admin/extend/rewards.json index a3ba8e3b5c..47a0dd459d 100644 --- a/public/language/uk/admin/extend/rewards.json +++ b/public/language/uk/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Видалити", "enable": "Увімкнути", "disable": "Вимкнути", - "control-panel": "Керування нагородами", - "new-reward": "Нова нагорода", "alert.delete-success": "Нагороду успішно видалено", "alert.no-inputs-found": "Невірна нагорода — поля пусті!", diff --git a/public/language/vi/admin/extend/rewards.json b/public/language/vi/admin/extend/rewards.json index 89c006fe45..d7a803ae6a 100644 --- a/public/language/vi/admin/extend/rewards.json +++ b/public/language/vi/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "Xóa", "enable": "Bật", "disable": "Tắt", - "control-panel": "Kiểm Soát Phần Thưởng", - "new-reward": "Phần Thưởng Mới", "alert.delete-success": "Đã xóa thành công phần thưởng", "alert.no-inputs-found": "Phần thưởng không hợp lệ - không tìm thấy đầu vào!", diff --git a/public/language/zh-CN/admin/extend/rewards.json b/public/language/zh-CN/admin/extend/rewards.json index 12a4336ef0..7646b33976 100644 --- a/public/language/zh-CN/admin/extend/rewards.json +++ b/public/language/zh-CN/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "删除", "enable": "启用", "disable": "禁用", - "control-panel": "奖励控制", - "new-reward": "新奖励", "alert.delete-success": "已成功删除奖励", "alert.no-inputs-found": "非法奖励 - 输入为空!", diff --git a/public/language/zh-TW/admin/extend/rewards.json b/public/language/zh-TW/admin/extend/rewards.json index 19ef749362..924bc85f71 100644 --- a/public/language/zh-TW/admin/extend/rewards.json +++ b/public/language/zh-TW/admin/extend/rewards.json @@ -8,8 +8,6 @@ "delete": "刪除", "enable": "啟用", "disable": "禁用", - "control-panel": "獎勵控制", - "new-reward": "新獎勵", "alert.delete-success": "已成功刪除獎勵", "alert.no-inputs-found": "非法獎勵 - 輸入為空!",