Skip to content

Commit 849fcc6

Browse files
committed
Centralizes AuthData validation
1 parent 3c3768d commit 849fcc6

File tree

6 files changed

+104
-79
lines changed

6 files changed

+104
-79
lines changed

spec/RestCreate.spec.js

+2-1
Original file line numberDiff line numberDiff line change
@@ -148,7 +148,8 @@ describe('rest create', () => {
148148
});
149149

150150
it('handles no anonymous users config', (done) => {
151-
var NoAnnonConfig = Object.assign({}, config, {enableAnonymousUsers: false});
151+
var NoAnnonConfig = Object.assign({}, config);
152+
NoAnnonConfig.oauth.setEnableAnonymousUsers(false);
152153
var data1 = {
153154
authData: {
154155
anonymous: {

spec/helper.js

+2-1
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ var DatabaseAdapter = require('../src/DatabaseAdapter');
77
var express = require('express');
88
var facebook = require('../src/oauth/facebook');
99
var ParseServer = require('../src/index').ParseServer;
10+
var path = require('path');
1011

1112
var databaseURI = process.env.DATABASE_URI;
1213
var cloudMain = process.env.CLOUD_CODE_MAIN || '../spec/cloud/main.js';
@@ -36,7 +37,7 @@ var defaultConfiguration = {
3637
oauth: { // Override the facebook provider
3738
facebook: mockFacebook(),
3839
myoauth: {
39-
module: "../spec/myoauth" // relative path as it's run from src
40+
module: path.resolve(__dirname, "myoauth") // relative path as it's run from src
4041
}
4142
}
4243
};

src/Config.js

-1
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,6 @@ export class Config {
2020
this.restAPIKey = cacheInfo.restAPIKey;
2121
this.fileKey = cacheInfo.fileKey;
2222
this.facebookAppIds = cacheInfo.facebookAppIds;
23-
this.enableAnonymousUsers = cacheInfo.enableAnonymousUsers;
2423
this.allowClientClassCreation = cacheInfo.allowClientClassCreation;
2524
this.database = DatabaseAdapter.getDatabaseConnection(applicationId, cacheInfo.collectionPrefix);
2625

src/RestWrite.js

+6-51
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,6 @@ var Auth = require('./Auth');
99
var Config = require('./Config');
1010
var cryptoUtils = require('./cryptoUtils');
1111
var passwordCrypto = require('./password');
12-
var oauth = require("./oauth");
1312
var Parse = require('parse/node');
1413
var triggers = require('./triggers');
1514

@@ -213,13 +212,7 @@ RestWrite.prototype.validateAuthData = function() {
213212
var authData = this.data.authData;
214213
var providers = Object.keys(authData);
215214
if (providers.length == 1) {
216-
217-
var provider = providers[0];
218-
if (provider == 'anonymous' && !this.config.enableAnonymousUsers) {
219-
throw new Parse.Error(Parse.Error.UNSUPPORTED_SERVICE,
220-
'This authentication method is unsupported.');
221-
}
222-
215+
var provider = providers[0];
223216
var providerAuthData = authData[provider];
224217
var hasToken = (providerAuthData && providerAuthData.id);
225218
if (providerAuthData === null || hasToken) {
@@ -238,52 +231,15 @@ RestWrite.prototype.handleOAuthAuthData = function(provider) {
238231
return;
239232
}
240233

241-
var appIds;
242-
var oauthOptions = this.config.oauth[provider];
243-
if (oauthOptions) {
244-
appIds = oauthOptions.appIds;
245-
} else if (provider == "facebook") {
246-
appIds = this.config.facebookAppIds;
247-
}
234+
let validateAuthData = this.config.oauth.getValidatorForProvider(provider);
248235

249-
var validateAuthData;
250-
var validateAppId;
251-
252-
if (oauth[provider]) {
253-
validateAuthData = oauth[provider].validateAuthData;
254-
validateAppId = oauth[provider].validateAppId;
255-
}
256-
257-
// Try the configuration methods
258-
if (oauthOptions) {
259-
if (oauthOptions.module) {
260-
validateAuthData = require(oauthOptions.module).validateAuthData;
261-
validateAppId = require(oauthOptions.module).validateAppId;
262-
};
263-
264-
if (oauthOptions.validateAuthData) {
265-
validateAuthData = oauthOptions.validateAuthData;
266-
}
267-
if (oauthOptions.validateAppId) {
268-
validateAppId = oauthOptions.validateAppId;
269-
}
270-
}
271-
// try the custom provider first, fallback on the oauth implementation
272-
273-
if (!validateAuthData || !validateAppId) {
274-
return false;
236+
if (!validateAuthData) {
237+
throw new Parse.Error(Parse.Error.UNSUPPORTED_SERVICE,
238+
'This authentication method is unsupported.');
275239
};
276240

277-
return validateAuthData(authData, oauthOptions)
241+
return validateAuthData(authData)
278242
.then(() => {
279-
if (appIds && typeof validateAppId === "function") {
280-
return validateAppId(appIds, authData, oauthOptions);
281-
}
282-
283-
// No validation required by the developer
284-
return Promise.resolve();
285-
286-
}).then(() => {
287243
// Check if this user already exists
288244
// TODO: does this handle re-linking correctly?
289245
var query = {};
@@ -314,7 +270,6 @@ RestWrite.prototype.handleOAuthAuthData = function(provider) {
314270
// are different
315271
if (results[0].objectId !== this.query.objectId) {
316272
delete this.data["_auth_data_" + provider ];
317-
console.log("alerady linked!");
318273
throw new Parse.Error(Parse.Error.ACCOUNT_ALREADY_LINKED,
319274
'this auth is already used');
320275
}

src/index.js

+3-3
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,8 @@ var batch = require('./batch'),
88
express = require('express'),
99
middlewares = require('./middlewares'),
1010
multer = require('multer'),
11-
Parse = require('parse/node').Parse;
11+
Parse = require('parse/node').Parse,
12+
oauthManager = require('./oauth');
1213

1314
//import passwordReset from './passwordReset';
1415
import cache from './cache';
@@ -163,9 +164,8 @@ function ParseServer({
163164
hooksController: hooksController,
164165
userController: userController,
165166
verifyUserEmails: verifyUserEmails,
166-
enableAnonymousUsers: enableAnonymousUsers,
167167
allowClientClassCreation: allowClientClassCreation,
168-
oauth: oauth,
168+
oauth: oauthManager(oauth, enableAnonymousUsers),
169169
appName: appName,
170170
publicServerURL: publicServerURL,
171171
customPages: customPages,

src/oauth/index.js

+91-22
Original file line numberDiff line numberDiff line change
@@ -1,25 +1,94 @@
1-
var facebook = require('./facebook');
2-
var instagram = require("./instagram");
3-
var linkedin = require("./linkedin");
4-
var meetup = require("./meetup");
5-
var google = require("./google");
6-
var github = require("./github");
7-
var twitter = require("./twitter");
8-
9-
module.exports = {
10-
facebook: facebook,
11-
github: github,
12-
google: google,
13-
instagram: instagram,
14-
linkedin: linkedin,
15-
meetup: meetup,
16-
twitter: twitter,
17-
anonymous: {
18-
validateAuthData: function() {
19-
return Promise.resolve();
20-
},
21-
validateAppId: function() {
22-
return Promise.resolve();
1+
let facebook = require('./facebook');
2+
let instagram = require("./instagram");
3+
let linkedin = require("./linkedin");
4+
let meetup = require("./meetup");
5+
let google = require("./google");
6+
let github = require("./github");
7+
let twitter = require("./twitter");
8+
9+
let anonymous = {
10+
validateAuthData: () => {
11+
return Promise.resolve();
12+
},
13+
validateAppId: () => {
14+
return Promise.resolve();
15+
}
16+
}
17+
18+
let providers = {
19+
facebook,
20+
instagram,
21+
linkedin,
22+
meetup,
23+
google,
24+
github,
25+
twitter,
26+
anonymous
27+
}
28+
29+
module.exports = function(oauthOptions = {}, enableAnonymousUsers = true) {
30+
let _enableAnonymousUsers = enableAnonymousUsers;
31+
let setEnableAnonymousUsers = function(enable) {
32+
_enableAnonymousUsers = enable;
33+
}
34+
// To handle the test cases on configuration
35+
let getValidatorForProvider = function(provider) {
36+
37+
if (provider === 'anonymous' && !_enableAnonymousUsers) {
38+
return;
39+
}
40+
41+
let defaultProvider = providers[provider];
42+
let optionalProvider = oauthOptions[provider];
43+
44+
if (!defaultProvider && !optionalProvider) {
45+
return;
46+
}
47+
48+
let appIds;
49+
if (optionalProvider) {
50+
appIds = optionalProvider.appIds;
51+
}
52+
53+
var validateAuthData;
54+
var validateAppId;
55+
56+
if (defaultProvider) {
57+
validateAuthData = defaultProvider.validateAuthData;
58+
validateAppId = defaultProvider.validateAppId;
59+
}
60+
61+
// Try the configuration methods
62+
if (optionalProvider) {
63+
if (optionalProvider.module) {
64+
validateAuthData = require(optionalProvider.module).validateAuthData;
65+
validateAppId = require(optionalProvider.module).validateAppId;
66+
};
67+
68+
if (optionalProvider.validateAuthData) {
69+
validateAuthData = optionalProvider.validateAuthData;
70+
}
71+
if (optionalProvider.validateAppId) {
72+
validateAppId = optionalProvider.validateAppId;
73+
}
74+
}
75+
76+
if (!validateAuthData || !validateAppId) {
77+
return;
78+
}
79+
80+
return function(authData) {
81+
return validateAuthData(authData, optionalProvider).then(() => {
82+
if (appIds) {
83+
return validateAppId(appIds, authData, optionalProvider);
84+
}
85+
return Promise.resolve();
86+
})
2387
}
2488
}
89+
90+
return Object.freeze({
91+
getValidatorForProvider,
92+
setEnableAnonymousUsers,
93+
})
2594
}

0 commit comments

Comments
 (0)