From d12c585e0cb188cb9a8a22574af7872152240c0d Mon Sep 17 00:00:00 2001 From: Sacha Greif Date: Thu, 4 Jul 2013 12:51:26 +0900 Subject: [PATCH] refactoring allow/deny code --- History.md | 2 + client/views/posts/post_item.html | 2 +- client/views/posts/post_item.js | 10 +++- collections/categories.js | 6 +++ collections/comments.js | 15 ++++++ collections/notifications.js | 9 ++++ collections/posts.js | 18 +++++++ collections/settings.js | 7 +++ collections/users.js | 11 +++++ server/publications.js | 78 ++----------------------------- 10 files changed, 80 insertions(+), 78 deletions(-) create mode 100644 collections/users.js diff --git a/History.md b/History.md index 82d5f4921..e0063c89b 100644 --- a/History.md +++ b/History.md @@ -2,6 +2,8 @@ * Added Bitly integration * Fixed Twitter avatars +* Refactoring allow/deny code +* Added click tracking on links ## v0.6 diff --git a/client/views/posts/post_item.html b/client/views/posts/post_item.html index d2b257a1d..c80752563 100644 --- a/client/views/posts/post_item.html +++ b/client/views/posts/post_item.html @@ -43,7 +43,7 @@ | Edit {{/if}} {{#if currentUser.isAdmin}} - | status: {{status}}, votes: {{votes}}, baseScore: {{baseScore}}, score: {{short_score}} + | status: {{status}}, votes: {{votes}}, baseScore: {{baseScore}}, score: {{short_score}}, clicks: {{clicks}} {{/if}}

diff --git a/client/views/posts/post_item.js b/client/views/posts/post_item.js index 4b6ea5c24..cb7274c1f 100644 --- a/client/views/posts/post_item.js +++ b/client/views/posts/post_item.js @@ -103,8 +103,8 @@ Template.post_item.events = { Meteor.call('upvotePost', post._id, function(error, result){ trackEvent("post upvoted", {'_id': post._id}); }); - } - , 'click .share-link': function(e){ + }, + 'click .share-link': function(e){ var $this = $(e.target).parents('.post-share').find('.share-link'); var $share = $this.parents('.post-share').find('.share-options'); e.preventDefault(); @@ -113,5 +113,11 @@ Template.post_item.events = { $this.toggleClass("active"); $share.toggleClass("hidden"); $share.find('.share-replace').sharrre(SharrreOptions); + }, + 'click .post-title': function(e){ + Meteor.call('clickedPost', this, function(error, result){ + if(error) + console.log(error); + }); } }; \ No newline at end of file diff --git a/collections/categories.js b/collections/categories.js index e2f900f18..2b60b0ae7 100644 --- a/collections/categories.js +++ b/collections/categories.js @@ -1,5 +1,11 @@ Categories = new Meteor.Collection('categories'); +Categories.allow({ + insert: isAdminById +, update: isAdminById +, remove: isAdminById +}); + Meteor.methods({ category: function(category){ var user = Meteor.user(); diff --git a/collections/comments.js b/collections/comments.js index 6bfe6be79..d8b358e88 100644 --- a/collections/comments.js +++ b/collections/comments.js @@ -1,5 +1,20 @@ Comments = new Meteor.Collection('comments'); +Comments.allow({ + insert: canCommentById + , update: canEditById + , remove: canEditById +}); + +Comments.deny({ + update: function(userId, post, fieldNames) { + if(isAdminById(userId)) + return true; + // may only edit the following fields: + return (_.without(fieldNames, 'text').length > 0); + } +}); + Meteor.methods({ comment: function(postId, parentCommentId, text){ var user = Meteor.user(), diff --git a/collections/notifications.js b/collections/notifications.js index 4a61f66b0..06e3aa963 100644 --- a/collections/notifications.js +++ b/collections/notifications.js @@ -1,5 +1,14 @@ Notifications = new Meteor.Collection('notifications'); +Notifications.allow({ + insert: function(userId, doc){ + // new notifications can only be created via a Meteor method + return false; + } + , update: canEditById + , remove: canEditById +}); + getNotification = function(event, properties, context){ var notification = {}; // the default context to display notifications is the notification sidebar diff --git a/collections/posts.js b/collections/posts.js index 8c8e84bf3..8d1a6e0d5 100644 --- a/collections/posts.js +++ b/collections/posts.js @@ -4,6 +4,21 @@ STATUS_PENDING=1; STATUS_APPROVED=2; STATUS_REJECTED=3; +Posts.allow({ + insert: canPostById + , update: canEditById + , remove: canEditById +}); + +Posts.deny({ + update: function(userId, post, fieldNames) { + if(isAdminById(userId)) + return true; + // may only edit the following fields: + return (_.without(fieldNames, 'headline', 'url', 'body', 'shortUrl', 'shortTitle', 'categories').length > 0); + } +}); + Meteor.methods({ post: function(post){ var headline = cleanUp(post.headline), @@ -110,5 +125,8 @@ Meteor.methods({ }, post_edit: function(post){ //TO-DO: make post_edit server-side? + }, + clickedPost: function(post){ + Posts.update(post._id, { $inc: { clicks: 1 }}); } }); \ No newline at end of file diff --git a/collections/settings.js b/collections/settings.js index e9846c1fd..c90b4e3bb 100644 --- a/collections/settings.js +++ b/collections/settings.js @@ -1 +1,8 @@ Settings = new Meteor.Collection('settings'); + +Settings.allow({ + insert: isAdminById +, update: isAdminById +, remove: isAdminById +}); + diff --git a/collections/users.js b/collections/users.js new file mode 100644 index 000000000..ddbb801ea --- /dev/null +++ b/collections/users.js @@ -0,0 +1,11 @@ +Meteor.users.allow({ + insert: function(userId, doc){ + return true; + } +, update: function(userId, doc, fields, modifier){ + return isAdminById(userId) || (doc._id && doc._id === userId); + } +, remove: function(userId, doc){ + return isAdminById(userId) || (doc._id && doc._id === userId); + } +}); \ No newline at end of file diff --git a/server/publications.js b/server/publications.js index aefa11b6b..f56baab07 100644 --- a/server/publications.js +++ b/server/publications.js @@ -1,3 +1,5 @@ +// Users + Meteor.publish('currentUser', function() { return Meteor.users.find(this.userId); }); @@ -21,23 +23,8 @@ Meteor.publish('allUsers', function() { } }); -Meteor.startup(function(){ - Meteor.users.allow({ - insert: function(userId, doc){ - return true; - } - , update: function(userId, doc, fields, modifier){ - return isAdminById(userId) || (doc._id && doc._id === userId); - } - , remove: function(userId, doc){ - return isAdminById(userId) || (doc._id && doc._id === userId); - } - }); -}); - // Posts - // a single post, identified by id Meteor.publish('singlePost', function(id) { return Posts.find(id); @@ -46,88 +33,29 @@ Meteor.publish('singlePost', function(id) { Meteor.publish('paginatedPosts', function(find, options, limit) { options = options || {}; options.limit = limit; - - // console.log('subscribing to paginated posts', find, options, limit); - return Posts.find(find || {}, options); }); - Meteor.publish('postDigest', function(date) { var mDate = moment(date); return findDigestPosts(mDate); }); - -Meteor.startup(function(){ - Posts.allow({ - insert: canPostById - , update: canEditById - , remove: canEditById - }); -}); - -// Comments - +// Other Publications Meteor.publish('comments', function(query) { return Comments.find(query); }); -Meteor.startup(function(){ - Comments.allow({ - insert: canCommentById - , update: canEditById - , remove: canEditById - }); -}); - -// Settings - - Meteor.publish('settings', function() { return Settings.find(); }); -Meteor.startup(function(){ - Settings.allow({ - insert: isAdminById - , update: isAdminById - , remove: isAdminById - }); -}); - - -// Notifications - - Meteor.publish('notifications', function() { // only publish notifications belonging to the current user return Notifications.find({userId:this.userId}); }); -Meteor.startup(function(){ - Notifications.allow({ - insert: function(userId, doc){ - // new notifications can only be created via a Meteor method - return false; - } - , update: canEditById - , remove: canEditById - }); -}); - -// Categories - - Meteor.publish('categories', function() { return Categories.find(); -}); - -Meteor.startup(function(){ - Categories.allow({ - insert: isAdminById - , update: isAdminById - , remove: isAdminById - }); }); \ No newline at end of file