From bb90900046e151cc6e642ed17a6a2fdbb63bcfe0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Pradel=20Le=CC=81o?= Date: Wed, 1 Feb 2017 22:41:26 +0100 Subject: [PATCH 1/5] verifyEmail server logic --- packages/common/src/config.js | 2 ++ packages/server/src/AccountsServer.js | 25 ++++++++++++++++++++++--- packages/server/src/DBInterface.js | 1 + 3 files changed, 25 insertions(+), 3 deletions(-) diff --git a/packages/common/src/config.js b/packages/common/src/config.js index 1073ea944..6b8e08688 100644 --- a/packages/common/src/config.js +++ b/packages/common/src/config.js @@ -3,6 +3,8 @@ import { EMAIL_ONLY } from './passwordSignupFields'; export default { sendVerificationEmail: false, + sendEnrollmentEmail: false, + sendWelcomeEmail: false, forbidClientAccountCreation: false, restrictCreationByEmailDomain: null, loginExpirationInDays: 90, diff --git a/packages/server/src/AccountsServer.js b/packages/server/src/AccountsServer.js index 4f288b471..51431605a 100644 --- a/packages/server/src/AccountsServer.js +++ b/packages/server/src/AccountsServer.js @@ -1,6 +1,6 @@ // @flow -import { isString, isPlainObject } from 'lodash'; +import { isString, isPlainObject, find } from 'lodash'; import jwt from 'jsonwebtoken'; import { AccountsError, @@ -242,8 +242,27 @@ export class AccountsServer { removeEmail(userId: string, email: string): Promise { return this.db.removeEmail(userId, email); } - verifyEmail(userId: string, email: string): Promise { - return this.db.verifyEmail(userId, email); + async verifyEmail(token: string): Promise { + const user = await this.db.findUserByEmailVerificationToken(); + if (!user) { + throw new AccountsError({ + message: 'Verify email link expired', + }); + } + const tokenRecord = find(user.services.email.verificationTokens, + (t : Object) => t.token === token); + if (!tokenRecord) { + throw new AccountsError({ + message: 'Verify email link expired', + }); + } + const emailRecord = find(user.emails, (e: Object) => e.address === tokenRecord.address); + if (!emailRecord) { + throw new AccountsError({ + message: 'Verify email link is for unknown address', + }); + } + await this.db.verifyEmail(user.id, emailRecord); } setPassword(userId: string, newPassword: string): Promise { return this.db.setPasssword(userId, newPassword); diff --git a/packages/server/src/DBInterface.js b/packages/server/src/DBInterface.js index 2698fc945..3a98e1521 100644 --- a/packages/server/src/DBInterface.js +++ b/packages/server/src/DBInterface.js @@ -12,6 +12,7 @@ export interface DBInterface { findUserByEmail(email: string) : Promise, findUserByUsername(username: string) : Promise, findUserById(userId: string) : Promise, + findUserByEmailVerificationToken(token: string) : Promise, setUsername(userId: string, newUsername: string) : Promise, addEmail(userId: string, newEmail: string, verified: boolean) : Promise, removeEmail(userId: string, email: string) : Promise, From c677342c45c6e4ef8b23e41a079d82e599e2fcc4 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Pradel=20Le=CC=81o?= Date: Wed, 1 Feb 2017 22:44:33 +0100 Subject: [PATCH 2/5] Fix lint --- packages/server/src/AccountsServer.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/server/src/AccountsServer.js b/packages/server/src/AccountsServer.js index 51431605a..fcf2f9ffd 100644 --- a/packages/server/src/AccountsServer.js +++ b/packages/server/src/AccountsServer.js @@ -250,7 +250,7 @@ export class AccountsServer { }); } const tokenRecord = find(user.services.email.verificationTokens, - (t : Object) => t.token === token); + (t: Object) => t.token === token); if (!tokenRecord) { throw new AccountsError({ message: 'Verify email link expired', From 0187e35f51a55196245986890fa395e560bafee9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Pradel=20Le=CC=81o?= Date: Wed, 1 Feb 2017 22:46:58 +0100 Subject: [PATCH 3/5] Add changes to Accounts --- packages/server/src/AccountsServer.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/packages/server/src/AccountsServer.js b/packages/server/src/AccountsServer.js index fcf2f9ffd..830111218 100644 --- a/packages/server/src/AccountsServer.js +++ b/packages/server/src/AccountsServer.js @@ -322,8 +322,8 @@ const Accounts = { removeEmail(userId: string, newEmail: string): Promise { return this.instance.removeEmail(userId, newEmail); }, - verifyEmail(userId: string, email: string): Promise { - return this.instance.verifyEmail(userId, email); + verifyEmail(token: string): Promise { + return this.instance.verifyEmail(token); }, setPassword(userId: string, newPassword: string): Promise { return this.instance.setPassword(userId, newPassword); From d761cdc216c8cb77376bd3d71e357b09c938074f Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Pradel=20Le=CC=81o?= Date: Wed, 1 Feb 2017 23:00:37 +0100 Subject: [PATCH 4/5] Add generateToken functions for the dbs packages --- packages/server/package.json | 1 + packages/server/src/tokens.js | 3 +++ 2 files changed, 4 insertions(+) diff --git a/packages/server/package.json b/packages/server/package.json index 9907c0d6b..7001de357 100644 --- a/packages/server/package.json +++ b/packages/server/package.json @@ -41,6 +41,7 @@ "@accounts/common": "^0.0.2", "apollo-errors": "^1.2.1", "bcryptjs": "^2.4.0", + "crypto": "^0.0.3", "jsonwebtoken": "^7.2.1", "jwt-decode": "^2.1.0", "lodash": "^4.16.4" diff --git a/packages/server/src/tokens.js b/packages/server/src/tokens.js index 4aa6ca78e..c4eff3073 100644 --- a/packages/server/src/tokens.js +++ b/packages/server/src/tokens.js @@ -1,5 +1,8 @@ // @flow import jwt from 'jsonwebtoken'; +import crypto from 'crypto'; + +export const generateToken = (length: Int = 43) => crypto.randomBytes(length).toString('hex'); export const generateAccessToken = ({ secret, From 3174d2f0c57a61779372f95c201a2d82c43110b8 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Pradel=20Le=CC=81o?= Date: Sat, 4 Feb 2017 14:28:30 +0100 Subject: [PATCH 5/5] Add services to UserObjectType and change generateToken name --- packages/common/src/types.js | 3 ++- packages/server/src/tokens.js | 2 +- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/packages/common/src/types.js b/packages/common/src/types.js index 0816832ad..f481a17f7 100644 --- a/packages/common/src/types.js +++ b/packages/common/src/types.js @@ -4,7 +4,8 @@ export type UserObjectType = { username: ?string, email: ?string, id: ?string, - profile: ?Object + profile: ?Object, + services: ?Object }; export type CreateUserType = { diff --git a/packages/server/src/tokens.js b/packages/server/src/tokens.js index c4eff3073..999a53ff7 100644 --- a/packages/server/src/tokens.js +++ b/packages/server/src/tokens.js @@ -2,7 +2,7 @@ import jwt from 'jsonwebtoken'; import crypto from 'crypto'; -export const generateToken = (length: Int = 43) => crypto.randomBytes(length).toString('hex'); +export const generateEmailToken = (length: Int = 43) => crypto.randomBytes(length).toString('hex'); export const generateAccessToken = ({ secret,