2015-08-18 21:48:22 +00:00
|
|
|
import{ Observable } from 'rx';
|
2015-11-04 05:51:16 +00:00
|
|
|
import debugFactory from 'debug';
|
|
|
|
import dedent from 'dedent';
|
|
|
|
|
2015-08-12 23:25:52 +00:00
|
|
|
import { observeMethod, observeQuery } from '../utils/rx';
|
2015-08-13 02:08:05 +00:00
|
|
|
import { getSocialProvider } from '../utils/auth';
|
2015-08-18 21:48:22 +00:00
|
|
|
|
|
|
|
const debug = debugFactory('fcc:userIdent');
|
2015-08-12 23:25:52 +00:00
|
|
|
|
|
|
|
export default function({ models }) {
|
|
|
|
const { User, UserIdentity, UserCredential } = models;
|
|
|
|
const findUserById = observeMethod(User, 'findById');
|
|
|
|
const findIdent = observeMethod(UserIdentity, 'findOne');
|
|
|
|
|
|
|
|
UserIdentity.link = function(
|
|
|
|
userId,
|
|
|
|
provider,
|
|
|
|
authScheme,
|
|
|
|
profile,
|
|
|
|
credentials,
|
|
|
|
options = {},
|
|
|
|
cb
|
|
|
|
) {
|
|
|
|
if (typeof options === 'function' && !cb) {
|
|
|
|
cb = options;
|
|
|
|
options = {};
|
|
|
|
}
|
|
|
|
const user$ = findUserById(userId);
|
2015-08-18 21:48:22 +00:00
|
|
|
const query = {
|
|
|
|
where: {
|
|
|
|
provider: getSocialProvider(provider),
|
|
|
|
externalId: profile.id
|
|
|
|
}
|
|
|
|
};
|
|
|
|
|
|
|
|
debug('link identity query', query);
|
|
|
|
findIdent(query)
|
2015-08-12 23:25:52 +00:00
|
|
|
.flatMap(identity => {
|
|
|
|
const modified = new Date();
|
2015-08-18 21:48:22 +00:00
|
|
|
if (!identity) {
|
2015-08-12 23:25:52 +00:00
|
|
|
return observeQuery(UserIdentity, 'create', {
|
2015-08-13 02:08:05 +00:00
|
|
|
provider: getSocialProvider(provider),
|
2015-08-12 23:25:52 +00:00
|
|
|
externalId: profile.id,
|
|
|
|
authScheme,
|
|
|
|
profile,
|
|
|
|
credentials,
|
|
|
|
userId,
|
|
|
|
created: modified,
|
|
|
|
modified
|
|
|
|
});
|
|
|
|
}
|
2015-08-18 22:22:28 +00:00
|
|
|
if (identity.userId.toString() !== userId.toString()) {
|
2015-08-18 21:48:22 +00:00
|
|
|
return Observable.throw(
|
2015-11-04 05:51:16 +00:00
|
|
|
new Error(
|
|
|
|
dedent`
|
|
|
|
It looks like you already have an account associated with that sign in method.
|
|
|
|
Here's what you can do: 1) Sign out of this account. 2) Use that sign in
|
|
|
|
method to sign into your other account. 3) Delete that account.
|
|
|
|
4) Then sign back into this account and you'll be able to link it here.
|
|
|
|
If you need help, send us an email at team@freecodecamp.com.
|
|
|
|
`.split('/n').join(' ')
|
|
|
|
)
|
2015-08-18 21:48:22 +00:00
|
|
|
);
|
|
|
|
}
|
2015-08-12 23:25:52 +00:00
|
|
|
identity.credentials = credentials;
|
|
|
|
return observeQuery(identity, 'updateAttributes', {
|
2015-08-21 23:08:49 +00:00
|
|
|
profile,
|
2015-08-12 23:25:52 +00:00
|
|
|
credentials,
|
|
|
|
modified
|
|
|
|
});
|
|
|
|
})
|
|
|
|
.withLatestFrom(user$, (identity, user) => ({ identity, user }))
|
|
|
|
.subscribe(
|
|
|
|
({ identity, user }) => {
|
|
|
|
cb(null, user, identity);
|
|
|
|
},
|
|
|
|
cb
|
|
|
|
);
|
|
|
|
};
|
|
|
|
|
|
|
|
UserCredential.link = UserIdentity.link.bind(UserIdentity);
|
|
|
|
}
|