From 83bb43ab4619f6c904bf1411a5d344fefde78be2 Mon Sep 17 00:00:00 2001 From: Charlie DeTar Date: Mon, 6 Oct 2014 17:11:43 -0600 Subject: [PATCH 1/2] Add hooks so packages can modify profiles Add the following hooks: - ``addToUserSchema``: fields to add to the (currently unused) user Schema - ``postAuthor``: templates to use when rendering the post author in the byline - ``userProfileDisplay``: additional templates to add to the user profile display. - ``userProfileEdit``: additional templates to add to the user profile editing form. - ``userProfileFinishSignup``: additional templates to show in the view for completing user signup (adding email, username, etc). - ``userEditRenderedCallbacks``: Callbacks executed on "rendered" for user_edit view. - ``userEditClientCallbacks``: Callbacks used to further process user properties before saving changes in user_edit view. - ``userProfileCompleteChecks``: Functions called to determine whether a user profile is "complete" (e.g. has email, username, and whatever else). These hooks facilitate package authors changing which profile fields are displayed, which profile fields are required, and how to display usernames next to posts. --- client/main.js | 6 ++++++ client/views/posts/modules/post_info.html | 10 +++++++++- client/views/posts/modules/post_info.js | 17 ++++++++++++---- client/views/users/user_edit.html | 3 +++ client/views/users/user_edit.js | 15 +++++++++++++- client/views/users/user_email.html | 5 ++++- client/views/users/user_email.js | 6 ++++++ client/views/users/user_profile.html | 3 +++ client/views/users/user_profile.js | 6 ++++++ collections/users.js | 10 ++++++++-- lib/users.js | 7 ++++++- packages/telescope-base/lib/base.js | 24 +++++++++++++++++++++++ packages/telescope-base/package.js | 11 ++++++++++- 13 files changed, 112 insertions(+), 11 deletions(-) diff --git a/client/main.js b/client/main.js index fdb32ce02..1b486ea55 100644 --- a/client/main.js +++ b/client/main.js @@ -35,6 +35,12 @@ postHeading = _.sortBy(postHeading, 'order'); postMeta = _.sortBy(postMeta, 'order'); +postAuthor = _.sortBy(postAuthor, 'order'); + +userProfileDisplay = _.sortBy(userProfileDisplay, 'order'); +userProfileEdit = _.sortBy(userProfileEdit, 'order'); +userProfileFinishSignup = _.sortBy(userProfileFinishSignup, 'order'); + Meteor.startup(function () { $('#rss-link').attr('title', i18n.t('New Posts')); }); \ No newline at end of file diff --git a/client/views/posts/modules/post_info.html b/client/views/posts/modules/post_info.html index ee3791e5a..8206482a7 100644 --- a/client/views/posts/modules/post_info.html +++ b/client/views/posts/modules/post_info.html @@ -1,8 +1,16 @@ + + \ No newline at end of file diff --git a/client/views/posts/modules/post_info.js b/client/views/posts/modules/post_info.js index 7698c4dee..9eacf0e85 100644 --- a/client/views/posts/modules/post_info.js +++ b/client/views/posts/modules/post_info.js @@ -5,18 +5,27 @@ Template[getTemplate('postInfo')].helpers({ can_edit: function(){ return canEdit(Meteor.user(), this); }, - authorName: function(){ - return getAuthorName(this); - }, ago: function(){ // if post is approved show submission time, else show creation time. time = this.status == STATUS_APPROVED ? this.postedAt : this.createdAt; return moment(time).fromNow(); }, + postAuthor: function() { + return postAuthor + }, + getTemplate: function() { + return getTemplate(this.template); + } +}); + +Template[getTemplate('postAuthorName')].helpers({ + authorName: function(){ + return getAuthorName(this); + }, profileUrl: function(){ // note: we don't want the post to be re-rendered every time user properties change var user = Meteor.users.findOne(this.userId, {reactive: false}); if(user) return getProfileUrl(user); } -}); \ No newline at end of file +}) \ No newline at end of file diff --git a/client/views/users/user_edit.html b/client/views/users/user_edit.html index 65f5198ad..ac6407939 100644 --- a/client/views/users/user_edit.html +++ b/client/views/users/user_edit.html @@ -55,6 +55,9 @@ + {{#each userProfileEdit}} + {{> UI.dynamic template=getTemplate data=..}} + {{/each}} {{#if hasPassword}}

{{i18n "Change Password?"}}

diff --git a/client/views/users/user_edit.js b/client/views/users/user_edit.js index 39ced76bd..482df4461 100644 --- a/client/views/users/user_edit.js +++ b/client/views/users/user_edit.js @@ -31,9 +31,22 @@ Template[getTemplate('user_edit')].helpers({ }, hasPassword: function () { return hasPassword(Meteor.user()); + }, + getTemplate: function() { + return getTemplate(this.template); + }, + userProfileEdit: function() { + return userProfileEdit; } }); +Template[getTemplate('user_edit')].rendered = function() { + var instance = this; + userEditRenderedCallbacks.forEach(function(callback) { + callback(instance); + }); +}; + Template[getTemplate('user_edit')].events({ 'submit #account-form': function(e){ e.preventDefault(); @@ -89,4 +102,4 @@ Template[getTemplate('user_edit')].events({ } -}); \ No newline at end of file +}); diff --git a/client/views/users/user_email.html b/client/views/users/user_email.html index a852db352..f1c9e3cc9 100644 --- a/client/views/users/user_email.html +++ b/client/views/users/user_email.html @@ -16,10 +16,13 @@
+ {{#each userProfileFinishSignup}} + {{> UI.dynamic template=getTemplate data=..}} + {{/each}}
{{/with}} - \ No newline at end of file + diff --git a/client/views/users/user_email.js b/client/views/users/user_email.js index ca915deda..09d9cd54b 100644 --- a/client/views/users/user_email.js +++ b/client/views/users/user_email.js @@ -4,6 +4,12 @@ Template[getTemplate('user_email')].helpers({ }, username: function () { return getUserName(Meteor.user()); + }, + getTemplate: function() { + return getTemplate(this.template); + }, + userProfileFinishSignup: function() { + return userProfileFinishSignup; } }); diff --git a/client/views/users/user_profile.html b/client/views/users/user_profile.html index af42c18b2..0d81495fa 100644 --- a/client/views/users/user_profile.html +++ b/client/views/users/user_profile.html @@ -41,6 +41,9 @@ {{profile.site}} {{/if}} + {{#each userProfileDisplay}} + {{> UI.dynamic template=getTemplate data=..}} + {{/each}} {{#if canEditProfile}} {{i18n "Edit profile"}} diff --git a/client/views/users/user_profile.js b/client/views/users/user_profile.js index ade940fbb..ffeb6e9a7 100644 --- a/client/views/users/user_profile.js +++ b/client/views/users/user_profile.js @@ -73,6 +73,12 @@ Template[getTemplate('user_profile')].helpers({ }, hasMoreComments: function () { return Comments.find({userId: this._id}).count() > Session.get('commentsShown'); + }, + getTemplate: function() { + return getTemplate(this.template); + }, + userProfileDisplay: function() { + return userProfileDisplay; } }); diff --git a/collections/users.js b/collections/users.js index 08ec26688..3aeab271a 100644 --- a/collections/users.js +++ b/collections/users.js @@ -1,6 +1,5 @@ var Schema = {}; - -Schema.User = new SimpleSchema({ +var userSchemaObj = { _id: { type: String, optional: true @@ -42,7 +41,14 @@ Schema.User = new SimpleSchema({ optional: true, blackbox: true } +}; + + +// add any extra properties to postSchemaObject (provided by packages for example) +_.each(addToUserSchema, function(item){ + userSchemaObj[item.propertyName] = item.propertySchema; }); +Schema.User = new SimpleSchema(userSchemaObj); // Meteor.users.attachSchema(Schema.User); diff --git a/lib/users.js b/lib/users.js index e4aec0856..b7234abbb 100644 --- a/lib/users.js +++ b/lib/users.js @@ -93,7 +93,12 @@ getCurrentUserEmail = function(){ return Meteor.user() ? getEmail(Meteor.user()) : ''; }; userProfileComplete = function(user) { - return !!getEmail(user); + for (var i = 0; i < userProfileCompleteChecks.length; i++) { + if (!userProfileCompleteChecks[i](user)) { + return false; + } + } + return true; }; findLast = function(user, collection){ diff --git a/packages/telescope-base/lib/base.js b/packages/telescope-base/lib/base.js index 8e2ec6c79..d45b5551d 100644 --- a/packages/telescope-base/lib/base.js +++ b/packages/telescope-base/lib/base.js @@ -4,6 +4,7 @@ addToPostSchema = []; addToCommentsSchema = []; addToSettingsSchema = []; +addToUserSchema = []; // ------------------------------------- Navigation -------------------------------- // @@ -146,6 +147,19 @@ postMeta = [ order: 5 } ] + +postAuthor = [ + { + template: 'postAuthorName', + order: 1 + } +] + +// Additional form fields for display and editing of user profiles. +userProfileDisplay = []; +userProfileEdit = []; +userProfileFinishSignup = []; + // ------------------------------ Callbacks ------------------------------ // postSubmitRenderedCallbacks = []; @@ -168,6 +182,16 @@ commentEditClientCallbacks = []; commentEditMethodCallbacks = []; // not used yet commentAfterEditMethodCallbacks = []; // not used yet +userEditRenderedCallbacks = []; +userEditClientCallbacks = []; + +userProfileCompleteChecks = [ + function(user) { + return !!getEmail(user) && !!user.username; + } +]; + + // ------------------------------ Dynamic Templates ------------------------------ // diff --git a/packages/telescope-base/package.js b/packages/telescope-base/package.js index 080e02859..e2f2f58b1 100644 --- a/packages/telescope-base/package.js +++ b/packages/telescope-base/package.js @@ -14,6 +14,7 @@ Package.onUse(function (api) { 'addToPostSchema', 'addToCommentsSchema', 'addToSettingsSchema', + 'addToUserSchema', 'preloadSubscriptions', 'primaryNav', 'secondaryNav', @@ -23,7 +24,11 @@ Package.onUse(function (api) { 'postModules', 'postHeading', 'postMeta', + 'postAuthor', 'modulePositions', + 'userProfileDisplay', + 'userProfileEdit', + 'userProfileFinishSignup', 'postSubmitRenderedCallbacks', 'postSubmitClientCallbacks', @@ -44,10 +49,14 @@ Package.onUse(function (api) { 'commentEditClientCallbacks', 'commentEditMethodCallbacks', 'commentAfterEditMethodCallbacks', + + 'userEditRenderedCallbacks', + 'userEditClientCallbacks', + 'userProfileCompleteChecks', 'getTemplate', 'templates', 'themeSettings' ]); -}); \ No newline at end of file +}); From 50dd3ccecef69579d595f5e4d85eeca69d16092d Mon Sep 17 00:00:00 2001 From: Charlie DeTar Date: Mon, 17 Nov 2014 17:11:13 -0700 Subject: [PATCH 2/2] Add accumulator for userEditClientCallbacks --- client/views/users/user_edit.js | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/client/views/users/user_edit.js b/client/views/users/user_edit.js index 482df4461..260fd44af 100644 --- a/client/views/users/user_edit.js +++ b/client/views/users/user_edit.js @@ -84,6 +84,10 @@ Template[getTemplate('user_edit')].events({ }); } + update = userEditClientCallbacks.reduce(function(result, currentFunction) { + return currentFunction(user, result); + }, update); + Meteor.users.update(user._id, { $set: update }, function(error){