From 85da50cbc814cb65dd93e9013304f3f825def314 Mon Sep 17 00:00:00 2001 From: Adrien Kiren Date: Fri, 11 Nov 2016 14:28:49 +0100 Subject: [PATCH] Add templateFn option to User#verify() --- common/models/user.js | 32 +++++++++++++++++++++++++++----- test/user.test.js | 39 +++++++++++++++++++++++++++++++++++++++ 2 files changed, 66 insertions(+), 5 deletions(-) diff --git a/common/models/user.js b/common/models/user.js index 5d24bcea..d9bd69e4 100644 --- a/common/models/user.js +++ b/common/models/user.js @@ -364,6 +364,10 @@ module.exports = function(User) { * @property {String} text Text of email. * @property {String} template Name of template that displays verification * page, for example, `'verify.ejs'. + * @property {Function} templateFn A function generating the email HTML body + * from `verify()` options object and generated attributes like `options.verifyHref`. + * It must accept the option object and a callback function with `(err, html)` + * as parameters * @property {String} redirect Page to which user will be redirected after * they verify their email, for example `'/'` for root URI. * @property {Function} generateVerificationToken A function to be used to @@ -424,6 +428,8 @@ module.exports = function(User) { '&redirect=' + options.redirect; + options.templateFn = options.templateFn || createVerificationEmailBody; + // Email model var Email = options.mailer || this.constructor.email || registry.getModelByType(loopback.Email); @@ -458,20 +464,36 @@ module.exports = function(User) { options.headers = options.headers || {}; - var template = loopback.template(options.template); - options.html = template(options); - - Email.send(options, function(err, email) { + options.templateFn(options, function(err, html) { if (err) { fn(err); } else { - fn(null, { email: email, token: user.verificationToken, uid: user.id }); + setHtmlContentAndSend(html); } }); + + function setHtmlContentAndSend(html) { + options.html = html; + + Email.send(options, function(err, email) { + if (err) { + fn(err); + } else { + fn(null, { email: email, token: user.verificationToken, uid: user.id }); + } + }); + } } return fn.promise; }; + function createVerificationEmailBody(options, cb) { + var template = loopback.template(options.template); + var body = template(options); + cb(null, body); + } + + /** * A default verification token generator which accepts the user the token is * being generated for and a callback function to indicate completion. diff --git a/test/user.test.js b/test/user.test.js index 25004daf..397d4439 100644 --- a/test/user.test.js +++ b/test/user.test.js @@ -1365,6 +1365,45 @@ describe('User', function() { }); }); + it('Verify a user\'s email address with custom template function', function(done) { + User.afterRemote('create', function(ctx, user, next) { + assert(user, 'afterRemote should include result'); + + var options = { + type: 'email', + to: user.email, + from: 'noreply@myapp.org', + redirect: '/', + protocol: ctx.req.protocol, + host: ctx.req.get('host'), + templateFn: function(options, cb) { + cb(null, 'custom template - verify url: ' + options.verifyHref); + }, + }; + + user.verify(options, function(err, result) { + assert(result.email); + assert(result.email.response); + assert(result.token); + var msg = result.email.response.toString('utf-8'); + assert(~msg.indexOf('/api/test-users/confirm')); + assert(~msg.indexOf('custom template')); + assert(~msg.indexOf('To: bar@bat.com')); + + done(); + }); + }); + + request(app) + .post('/test-users') + .expect('Content-Type', /json/) + .expect(200) + .send({ email: 'bar@bat.com', password: 'bar' }) + .end(function(err, res) { + if (err) return done(err); + }); + }); + it('Verify a user\'s email address with custom token generator', function(done) { User.afterRemote('create', function(ctx, user, next) { assert(user, 'afterRemote should include result');