mirror of
				https://github.com/NodeBB/NodeBB.git
				synced 2025-10-31 02:55:58 +01:00 
			
		
		
		
	| @@ -38,5 +38,5 @@ | ||||
|     "bookmarkThreshold": 5, | ||||
|     "topicsPerList": 20, | ||||
|     "autoDetectLang": 1, | ||||
|     "privileges:flag": 0 | ||||
|     "min:rep:flag": 0 | ||||
| } | ||||
|   | ||||
| @@ -69,9 +69,9 @@ | ||||
|         "nodebb-plugin-spam-be-gone": "0.5.1", | ||||
|         "nodebb-rewards-essentials": "0.0.9", | ||||
|         "nodebb-theme-lavender": "5.0.0", | ||||
|         "nodebb-theme-persona": "7.2.11", | ||||
|         "nodebb-theme-persona": "7.2.12", | ||||
|         "nodebb-theme-slick": "1.1.2", | ||||
|         "nodebb-theme-vanilla": "8.1.5", | ||||
|         "nodebb-theme-vanilla": "8.1.6", | ||||
|         "nodebb-widget-essentials": "4.0.1", | ||||
|         "nodemailer": "4.4.1", | ||||
|         "passport": "^0.4.0", | ||||
|   | ||||
| @@ -5,5 +5,8 @@ | ||||
| 	"votes-are-public": "All Votes Are Public", | ||||
| 	"thresholds": "Activity Thresholds", | ||||
| 	"min-rep-downvote": "Minimum reputation to downvote posts", | ||||
| 	"min-rep-flag": "Minimum reputation to flag posts" | ||||
| 	"min-rep-flag": "Minimum reputation to flag posts", | ||||
| 	"min-rep-website": "Minimum reputation to add \"Website\" to user profile", | ||||
| 	"min-rep-aboutme": "Minimum reputation to add \"About me\" to user profile", | ||||
| 	"min-rep-signature": "Minimum reputation to add \"Signature\" to user profile" | ||||
| } | ||||
| @@ -146,6 +146,9 @@ | ||||
| 	"downvoting-disabled": "Downvoting is disabled", | ||||
| 	"not-enough-reputation-to-downvote": "You do not have enough reputation to downvote this post", | ||||
| 	"not-enough-reputation-to-flag": "You do not have enough reputation to flag this post", | ||||
| 	"not-enough-reputation-min-rep-website": "You do not have enough reputation to add a website", | ||||
| 	"not-enough-reputation-min-rep-aboutme": "You do not have enough reputation to add an about me", | ||||
| 	"not-enough-reputation-min-rep-signature": "You do not have enough reputation to add a signature", | ||||
| 	"already-flagged": "You have already flagged this post", | ||||
| 	"self-vote": "You cannot vote on your own post", | ||||
|  | ||||
|   | ||||
| @@ -28,6 +28,9 @@ editController.get = function (req, res, callback) { | ||||
| 			userData.maximumProfileImageSize = parseInt(meta.config.maximumProfileImageSize, 10); | ||||
| 			userData.allowProfileImageUploads = parseInt(meta.config.allowProfileImageUploads, 10) === 1; | ||||
| 			userData.allowAccountDelete = parseInt(meta.config.allowAccountDelete, 10) === 1; | ||||
| 			userData.allowWebsite = !userData.isSelf || parseInt(userData.reputation, 10) >= (parseInt(meta.config['min:rep:website'], 10) || 0); | ||||
| 			userData.allowAboutMe = !userData.isSelf || parseInt(userData.reputation, 10) >= (parseInt(meta.config['min:rep:aboutme'], 10) || 0); | ||||
| 			userData.allowSignature = !userData.isSelf || parseInt(userData.reputation, 10) >= (parseInt(meta.config['min:rep:signature'], 10) || 0); | ||||
| 			userData.profileImageDimension = parseInt(meta.config.profileImageDimension, 10) || 200; | ||||
| 			userData.defaultAvatar = user.getDefaultAvatar(); | ||||
|  | ||||
|   | ||||
| @@ -241,7 +241,7 @@ Flags.validate = function (payload, callback) { | ||||
| 					return callback(err); | ||||
| 				} | ||||
|  | ||||
| 				var minimumReputation = utils.isNumber(meta.config['privileges:flag']) ? parseInt(meta.config['privileges:flag'], 10) : 0; | ||||
| 				var minimumReputation = utils.isNumber(meta.config['min:rep:flag']) ? parseInt(meta.config['min:rep:flag'], 10) : 0; | ||||
| 				// Check if reporter meets rep threshold (or can edit the target post, in which case threshold does not apply) | ||||
| 				if (!editable.flag && parseInt(data.reporter.reputation, 10) < minimumReputation) { | ||||
| 					return callback(new Error('[[error:not-enough-reputation-to-flag]]')); | ||||
| @@ -257,7 +257,7 @@ Flags.validate = function (payload, callback) { | ||||
| 					return callback(err); | ||||
| 				} | ||||
|  | ||||
| 				var minimumReputation = utils.isNumber(meta.config['privileges:flag']) ? parseInt(meta.config['privileges:flag'], 10) : 0; | ||||
| 				var minimumReputation = utils.isNumber(meta.config['min:rep:flag']) ? parseInt(meta.config['min:rep:flag'], 10) : 0; | ||||
| 				// Check if reporter meets rep threshold (or can edit the target user, in which case threshold does not apply) | ||||
| 				if (!editable && parseInt(data.reporter.reputation, 10) < minimumReputation) { | ||||
| 					return callback(new Error('[[error:not-enough-reputation-to-flag]]')); | ||||
|   | ||||
| @@ -179,7 +179,7 @@ module.exports = function (Posts) { | ||||
| 					return callback(new Error('[[error:self-vote]]')); | ||||
| 				} | ||||
|  | ||||
| 				if (command === 'downvote' && parseInt(results.reputation, 10) < parseInt(meta.config['privileges:downvote'], 10)) { | ||||
| 				if (command === 'downvote' && parseInt(results.reputation, 10) < parseInt(meta.config['min:rep:downvote'], 10)) { | ||||
| 					return callback(new Error('[[error:not-enough-reputation-to-downvote]]')); | ||||
| 				} | ||||
|  | ||||
|   | ||||
| @@ -200,7 +200,7 @@ module.exports = function (privileges) { | ||||
| 				}, next); | ||||
| 			}, | ||||
| 			function (results, next) { | ||||
| 				var minimumReputation = utils.isNumber(meta.config['privileges:flag']) ? parseInt(meta.config['privileges:flag'], 10) : 0; | ||||
| 				var minimumReputation = utils.isNumber(meta.config['min:rep:flag']) ? parseInt(meta.config['min:rep:flag'], 10) : 0; | ||||
| 				var canFlag = results.isAdminOrMod || parseInt(results.userReputation, 10) >= minimumReputation; | ||||
| 				next(null, { flag: canFlag }); | ||||
| 			}, | ||||
|   | ||||
							
								
								
									
										25
									
								
								src/upgrades/1.8.0/rename_min_reputation_settings.js
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										25
									
								
								src/upgrades/1.8.0/rename_min_reputation_settings.js
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,25 @@ | ||||
| 'use strict'; | ||||
|  | ||||
| var db = require('../../database'); | ||||
|  | ||||
| module.exports = { | ||||
| 	name: 'Rename privileges:downvote and privileges:flag to min:rep:downvote, min:rep:flag respectively', | ||||
| 	timestamp: Date.UTC(2018, 0, 12), | ||||
| 	method: function (callback) { | ||||
| 		db.getObjectFields('config', ['privileges:downvote', 'privileges:flag'], function (err, config) { | ||||
| 			if (err) { | ||||
| 				return callback(err); | ||||
| 			} | ||||
|  | ||||
| 			db.setObject('config', { | ||||
| 				'min:rep:downvote': parseInt(config['privileges:downvote'], 10) || 0, | ||||
| 				'min:rep:flag': parseInt(config['privileges:downvote'], 10) || 0, | ||||
| 			}, function (err) { | ||||
| 				if (err) { | ||||
| 					return callback(err); | ||||
| 				} | ||||
| 				db.deleteObjectFields('config', ['privileges:downvote', 'privileges:flag'], callback); | ||||
| 			}); | ||||
| 		}); | ||||
| 	}, | ||||
| }; | ||||
| @@ -17,14 +17,6 @@ module.exports = function (User) { | ||||
| 		var updateUid = data.uid; | ||||
| 		var oldData; | ||||
|  | ||||
| 		if (data.aboutme !== undefined && data.aboutme.length > meta.config.maximumAboutMeLength) { | ||||
| 			return callback(new Error('[[error:about-me-too-long, ' + meta.config.maximumAboutMeLength + ']]')); | ||||
| 		} | ||||
|  | ||||
| 		if (data.signature !== undefined && data.signature.length > meta.config.maximumSignatureLength) { | ||||
| 			return callback(new Error('[[error:signature-too-long, ' + meta.config.maximumSignatureLength + ']]')); | ||||
| 		} | ||||
|  | ||||
| 		async.waterfall([ | ||||
| 			function (next) { | ||||
| 				plugins.fireHook('filter:user.updateProfile', { uid: uid, data: data, fields: fields }, next); | ||||
| @@ -33,13 +25,7 @@ module.exports = function (User) { | ||||
| 				fields = data.fields; | ||||
| 				data = data.data; | ||||
|  | ||||
| 				async.series([ | ||||
| 					async.apply(isEmailAvailable, data, updateUid), | ||||
| 					async.apply(isUsernameAvailable, data, updateUid), | ||||
| 					async.apply(isGroupTitleValid, data), | ||||
| 				], function (err) { | ||||
| 					next(err); | ||||
| 				}); | ||||
| 				validateData(uid, data, next); | ||||
| 			}, | ||||
| 			function (next) { | ||||
| 				User.getUserFields(updateUid, fields, next); | ||||
| @@ -73,6 +59,19 @@ module.exports = function (User) { | ||||
| 		], callback); | ||||
| 	}; | ||||
|  | ||||
| 	function validateData(callerUid, data, callback) { | ||||
| 		async.series([ | ||||
| 			async.apply(isEmailAvailable, data, data.uid), | ||||
| 			async.apply(isUsernameAvailable, data, data.uid), | ||||
| 			async.apply(isGroupTitleValid, data), | ||||
| 			async.apply(isWebsiteValid, callerUid, data), | ||||
| 			async.apply(isAboutMeValid, callerUid, data), | ||||
| 			async.apply(isSignatureValid, callerUid, data), | ||||
| 		], function (err) { | ||||
| 			callback(err); | ||||
| 		}); | ||||
| 	} | ||||
|  | ||||
| 	function isEmailAvailable(data, uid, callback) { | ||||
| 		if (!data.email) { | ||||
| 			return callback(); | ||||
| @@ -141,6 +140,52 @@ module.exports = function (User) { | ||||
| 		} | ||||
| 	} | ||||
|  | ||||
| 	function isWebsiteValid(callerUid, data, callback) { | ||||
| 		if (!data.website) { | ||||
| 			return setImmediate(callback); | ||||
| 		} | ||||
| 		checkMinReputation(callerUid, data.uid, 'min:rep:website', callback); | ||||
| 	} | ||||
|  | ||||
| 	function isAboutMeValid(callerUid, data, callback) { | ||||
| 		if (!data.aboutme) { | ||||
| 			return setImmediate(callback); | ||||
| 		} | ||||
| 		if (data.aboutme !== undefined && data.aboutme.length > meta.config.maximumAboutMeLength) { | ||||
| 			return callback(new Error('[[error:about-me-too-long, ' + meta.config.maximumAboutMeLength + ']]')); | ||||
| 		} | ||||
|  | ||||
| 		checkMinReputation(callerUid, data.uid, 'min:rep:aboutme', callback); | ||||
| 	} | ||||
|  | ||||
| 	function isSignatureValid(callerUid, data, callback) { | ||||
| 		if (!data.signature) { | ||||
| 			return setImmediate(callback); | ||||
| 		} | ||||
| 		if (data.signature !== undefined && data.signature.length > meta.config.maximumSignatureLength) { | ||||
| 			return callback(new Error('[[error:signature-too-long, ' + meta.config.maximumSignatureLength + ']]')); | ||||
| 		} | ||||
| 		checkMinReputation(callerUid, data.uid, 'min:rep:signature', callback); | ||||
| 	} | ||||
|  | ||||
| 	function checkMinReputation(callerUid, uid, setting, callback) { | ||||
| 		var isSelf = parseInt(callerUid, 10) === parseInt(uid, 10); | ||||
| 		if (!isSelf) { | ||||
| 			return setImmediate(callback); | ||||
| 		} | ||||
| 		async.waterfall([ | ||||
| 			function (next) { | ||||
| 				User.getUserField(uid, 'reputation', next); | ||||
| 			}, | ||||
| 			function (reputation, next) { | ||||
| 				if (parseInt(reputation, 10) < (parseInt(meta.config[setting], 10) || 0)) { | ||||
| 					return next(new Error('[[error:not-enough-reputation-' + setting.replace(/:/g, '-') + ']]')); | ||||
| 				} | ||||
| 				next(); | ||||
| 			}, | ||||
| 		], callback); | ||||
| 	} | ||||
|  | ||||
| 	function updateEmail(uid, newEmail, callback) { | ||||
| 		async.waterfall([ | ||||
| 			function (next) { | ||||
|   | ||||
| @@ -32,8 +32,11 @@ | ||||
| 	<div class="col-sm-2 col-xs-12 settings-header">[[admin/settings/reputation:thresholds]]</div> | ||||
| 	<div class="col-sm-10 col-xs-12"> | ||||
| 		<form> | ||||
| 			<strong>[[admin/settings/reputation:min-rep-downvote]]</strong><br /> <input type="text" class="form-control" placeholder="0" data-field="privileges:downvote"><br /> | ||||
| 			<strong>[[admin/settings/reputation:min-rep-flag]]</strong><br /> <input type="text" class="form-control" placeholder="0" data-field="privileges:flag"><br /> | ||||
| 			<strong>[[admin/settings/reputation:min-rep-downvote]]</strong><br /> <input type="text" class="form-control" placeholder="0" data-field="min:rep:downvote"><br /> | ||||
| 			<strong>[[admin/settings/reputation:min-rep-flag]]</strong><br /> <input type="text" class="form-control" placeholder="0" data-field="min:rep:flag"><br /> | ||||
| 			<strong>[[admin/settings/reputation:min-rep-website]]</strong><br /> <input type="text" class="form-control" placeholder="0" data-field="min:rep:website"><br /> | ||||
| 			<strong>[[admin/settings/reputation:min-rep-aboutme]]</strong><br /> <input type="text" class="form-control" placeholder="0" data-field="min:rep:aboutme"><br /> | ||||
| 			<strong>[[admin/settings/reputation:min-rep-signature]]</strong><br /> <input type="text" class="form-control" placeholder="0" data-field="min:rep:signature"><br /> | ||||
| 		</form> | ||||
| 	</div> | ||||
| </div> | ||||
|   | ||||
| @@ -591,21 +591,21 @@ describe('Admin Controllers', function () { | ||||
|  | ||||
| 		it('should error with not enough reputation to flag', function (done) { | ||||
| 			var socketFlags = require('../src/socket.io/flags'); | ||||
| 			var oldValue = meta.config['privileges:flag']; | ||||
| 			meta.config['privileges:flag'] = 1000; | ||||
| 			var oldValue = meta.config['min:rep:flag']; | ||||
| 			meta.config['min:rep:flag'] = 1000; | ||||
| 			socketFlags.create({ uid: regularUid }, { id: pid, type: 'post', reason: 'spam' }, function (err) { | ||||
| 				assert.equal(err.message, '[[error:not-enough-reputation-to-flag]]'); | ||||
| 				meta.config['privileges:flag'] = oldValue; | ||||
| 				meta.config['min:rep:flag'] = oldValue; | ||||
| 				done(); | ||||
| 			}); | ||||
| 		}); | ||||
|  | ||||
| 		it('should return flag details', function (done) { | ||||
| 			var socketFlags = require('../src/socket.io/flags'); | ||||
| 			var oldValue = meta.config['privileges:flag']; | ||||
| 			meta.config['privileges:flag'] = 0; | ||||
| 			var oldValue = meta.config['min:rep:flag']; | ||||
| 			meta.config['min:rep:flag'] = 0; | ||||
| 			socketFlags.create({ uid: regularUid }, { id: pid, type: 'post', reason: 'spam' }, function (err, data) { | ||||
| 				meta.config['privileges:flag'] = oldValue; | ||||
| 				meta.config['min:rep:flag'] = oldValue; | ||||
| 				assert.ifError(err); | ||||
| 				request(nconf.get('url') + '/api/flags/' + data.flagId, { jar: moderatorJar, json: true }, function (err, res, body) { | ||||
| 					assert.ifError(err); | ||||
|   | ||||
| @@ -364,7 +364,7 @@ describe('Flags', function () { | ||||
| 		}); | ||||
|  | ||||
| 		it('should not pass validation if flag threshold is set and user rep does not meet it', function (done) { | ||||
| 			Meta.configs.set('privileges:flag', '50', function (err) { | ||||
| 			Meta.configs.set('min:rep:flag', '50', function (err) { | ||||
| 				assert.ifError(err); | ||||
|  | ||||
| 				Flags.validate({ | ||||
| @@ -374,7 +374,7 @@ describe('Flags', function () { | ||||
| 				}, function (err) { | ||||
| 					assert.ok(err); | ||||
| 					assert.strictEqual('[[error:not-enough-reputation-to-flag]]', err.message); | ||||
| 					Meta.configs.set('privileges:flag', 0, done); | ||||
| 					Meta.configs.set('min:rep:flag', 0, done); | ||||
| 				}); | ||||
| 			}); | ||||
| 		}); | ||||
|   | ||||
		Reference in New Issue
	
	Block a user