Vulcan/lib/vote.js

177 lines
5.8 KiB
JavaScript
Raw Normal View History

2012-09-27 13:13:55 -07:00
// returns how much "power" a user's votes have
var getVotePower = function(user){
2013-11-08 10:12:00 +09:00
// return (user && user.isAdmin) ? 5 : 1;
return 1; // for now, leave everybody at 1 including admins; 5 is too unbalanced
2012-09-18 10:04:26 +10:00
};
2012-09-27 13:13:55 -07:00
2013-10-29 13:39:28 +09:00
var modifyKarma = function(userId, karma){
Meteor.users.update({_id: userId}, {$inc: {karma: karma}});
2012-09-28 09:57:03 +09:00
};
var hasUpvotedItem= function(item, user){
return item.upvoters && item.upvoters.indexOf(user._id) != -1;
};
2012-09-29 13:51:55 +09:00
var hasDownvotedItem= function(item, user){
return item.downvoters && item.downvoters.indexOf(user._id) != -1;
};
2012-09-29 13:51:55 +09:00
var upvoteItem = function(collection, item) {
var user = Meteor.user(),
votePower = getVotePower(user);
2013-01-15 08:46:00 +09:00
// make sure user has rights to upvote first
2013-10-29 15:47:20 +09:00
if (!user || !canUpvote(user, collection, true) || hasUpvotedItem(item, user))
2012-09-27 13:13:55 -07:00
return false;
// if user is upvoting a previously downvoted item, cancel downvote first
if (hasDownvotedItem(item, user))
cancelDownvote(collection, item, user);
2012-09-29 13:51:55 +09:00
// Votes & Score
var result = collection.update({_id: item && item._id},{
$addToSet: {upvoters: user._id},
$pull: {downvoters: user._id},
$inc: {votes: 1, baseScore: votePower},
$set: {inactive: false}
});
2013-10-29 18:02:10 +09:00
// extend item with baseScore to help calculate newScore
item = _.extend(item, {baseScore: (item.baseScore + votePower)});
updateScore({collection: collection, item: item, forceUpdate: true});
2013-10-29 13:39:28 +09:00
// if the item is being upvoted by its own author, don't give karma
2013-11-08 10:12:00 +09:00
if (item.userId != user._id){
modifyKarma(item.userId, votePower);
2013-11-08 10:12:00 +09:00
// if karma redistribution is enabled, give karma to all previous upvoters of the post
// (but not to the person doing the upvoting)
if(getSetting('redistributeKarma', false)){
_.each(item.upvoters, function(upvoterId){
// share the karma equally among all upvoters, but cap the value at 0.1
var karmaIncrease = Math.min(0.1, votePower/item.upvoters.length);
2013-11-08 10:12:00 +09:00
modifyKarma(upvoterId, 0.1);
});
}
}
2012-09-27 13:13:55 -07:00
return true;
2012-09-18 10:04:26 +10:00
};
2012-09-27 13:13:55 -07:00
var downvoteItem = function(collection, item) {
var user = Meteor.user(),
votePower = getVotePower(user);
2013-01-15 08:46:00 +09:00
// make sure user has rights to downvote first
2013-10-29 15:47:20 +09:00
if (!user || !canDownvote(user, collection, true) || hasDownvotedItem(item, user))
2012-09-27 13:13:55 -07:00
return false;
// if user is downvoting a previously upvoted item, cancel upvote first
if (hasUpvotedItem(item, user))
cancelUpvote(collection, item, user);
2012-09-29 13:51:55 +09:00
// Votes & Score
collection.update({_id: item && item._id},{
$addToSet: {downvoters: user._id},
$pull: {upvoters: user._id},
$inc: {votes: -1, baseScore: -votePower},
$set: {inactive: false}
});
2012-09-27 13:13:55 -07:00
2013-10-29 18:02:10 +09:00
// extend item with baseScore to help calculate newScore
item = _.extend(item, {baseScore: (item.baseScore + votePower)});
updateScore({collection: collection, item: item, forceUpdate: true});
// if the item is being upvoted by its own author, don't give karma
if (item.userId != user._id)
modifyKarma(item.userId, votePower);
2012-09-29 13:51:55 +09:00
2012-09-27 13:13:55 -07:00
return true;
2012-09-18 10:04:26 +10:00
};
2012-09-27 13:13:55 -07:00
var cancelUpvote = function(collection, item) {
var user = Meteor.user();
votePower = getVotePower(user);
// if user isn't among the upvoters, abort
if(!hasUpvotedItem(item, user))
return false;
2013-01-15 08:46:00 +09:00
2012-09-29 13:51:55 +09:00
// Votes & Score
collection.update({_id: item && item._id},{
$pull: {upvoters: user._id},
$inc: {votes: -1, baseScore: -votePower},
$set: {inactive: false}
});
2012-09-27 13:13:55 -07:00
2013-10-29 18:02:10 +09:00
// extend item with baseScore to help calculate newScore
item = _.extend(item, {baseScore: (item.baseScore + votePower)});
updateScore({collection: collection, item: item, forceUpdate: true});
// if the item is being upvoted by its own author, don't give karma
if (item.userId != user._id)
modifyKarma(item.userId, votePower);
2012-09-29 13:51:55 +09:00
2012-09-27 13:13:55 -07:00
return true;
2012-09-18 10:04:26 +10:00
};
2012-09-27 13:13:55 -07:00
var cancelDownvote = function(collection, item) {
var user = Meteor.user(),
votePower = getVotePower(user);
2012-09-27 13:13:55 -07:00
// if user isn't among the downvoters, abort
if(!hasUpvotedItem(item, user))
return false;
2012-09-28 15:07:25 +02:00
2012-09-29 13:51:55 +09:00
// Votes & Score
collection.update({_id: item && item._id},{
$pull: {downvoters: user._id},
$inc: {votes: 1, baseScore: votePower},
$set: {inactive: false}
});
2013-10-29 18:02:10 +09:00
// extend item with baseScore to help calculate newScore
item = _.extend(item, {baseScore: (item.baseScore + votePower)});
updateScore({collection: collection, item: item, forceUpdate: true});
// if the item is being upvoted by its own author, don't give karma
if (item.userId != user._id)
modifyKarma(item.userId, votePower);
2012-09-29 13:51:55 +09:00
2012-09-27 13:13:55 -07:00
return true;
2012-09-18 10:04:26 +10:00
};
2012-09-27 13:13:55 -07:00
// note: doesn't actually seem very useful to enable admins to vote for other users. Remove this?
2013-02-04 12:04:01 +09:00
var getUser = function(user){
// only let admins specify different users for voting
// if no user is specified, use current user by default
return (isAdmin(Meteor.user()) && typeof user !== 'undefined') ? user : Meteor.user();
};
2013-01-15 08:46:00 +09:00
2012-09-18 10:04:26 +10:00
Meteor.methods({
upvotePost: function(post, user){
return upvoteItem.call(this, Posts, post);
2012-09-18 10:04:26 +10:00
},
downvotePost: function(post, user){
return downvoteItem.call(this, Posts, post);
2012-09-18 10:04:26 +10:00
},
cancelUpvotePost: function(post, user){
2013-10-29 17:54:45 +09:00
return cancelUpvote.call(this, Posts, post);
2012-09-18 10:04:26 +10:00
},
cancelDownvotePost: function(post, user){
return cancelDownvote.call(this, Posts, post);
2012-09-18 10:04:26 +10:00
},
upvoteComment: function(comment, user){
return upvoteItem.call(this, Comments, comment);
2012-09-18 10:04:26 +10:00
},
downvoteComment: function(comment, user){
2014-05-08 19:35:24 -04:00
return downvoteItem.call(this, Comments, comment);
2012-09-18 10:04:26 +10:00
},
cancelUpvoteComment: function(comment, user){
return cancelUpvote.call(this, Comments, comment);
2012-09-18 10:04:26 +10:00
},
cancelDownvoteComment: function(comment, user){
return cancelDownvote.call(this, Comments, comment);
}
2012-09-18 10:04:26 +10:00
});