diff --git a/common/app/routes/settings/components/Social-Settings.jsx b/common/app/routes/settings/components/Social-Settings.jsx index f1a3691ce7..23c3a49078 100644 --- a/common/app/routes/settings/components/Social-Settings.jsx +++ b/common/app/routes/settings/components/Social-Settings.jsx @@ -1,6 +1,7 @@ import React, { PropTypes } from 'react'; import { Button } from 'react-bootstrap'; import FA from 'react-fontawesome'; +import classnames from 'classnames'; export default function SocialSettings({ isGithubCool, @@ -22,33 +23,44 @@ export default function SocialSettings({ { githubCopy } ]; - if (isGithubCool && !isTwitter) { - buttons.push(( - - )); - } - if (isGithubCool && !isLinkedIn) { - buttons.push(( - - )); + const socials = [ + { + isActive: isTwitter, + identifier: 'twitter', + text: 'Twitter' + }, + { + isActive: isLinkedIn, + identifier: 'linkedin', + text: 'LinkedIn' + } + ]; + if (isGithubCool) { + socials.forEach(({ isActive, identifier, text }) => { + const socialClass = classnames( + 'btn-link-social', + `btn-${identifier}`, + { active: isActive } + ); + const socialLink = isActive ? + `/account/unlink/${identifier}` : + `/link/${identifier}`; + const socialText = isTwitter ? + `Remove my ${text} from my portfolio` : + `Add my ${text} to my portfolio`; + buttons.push(( + + )); + }); } return (
{ buttons }
); } diff --git a/server/boot/user.js b/server/boot/user.js index cc5ea1d664..e07e3639bd 100644 --- a/server/boot/user.js +++ b/server/boot/user.js @@ -184,6 +184,12 @@ module.exports = function(app) { getAccount ); + api.get( + '/account/unlink/:social', + sendNonUserToMap, + getUnlinkSocial + ); + // Ensure these are the last routes! api.get( '/:username/front-end-certification', @@ -266,6 +272,70 @@ module.exports = function(app) { return res.redirect('/' + username); } + function getUnlinkSocial(req, res, next) { + const { user } = req; + const { username } = user; + + let social = req.params.social; + if (!social) { + req.flash('errors', { + msg: 'No social account found' + }); + return res.redirect('/' + username); + } + + social = social.toLowerCase(); + const validSocialAccounts = ['twitter', 'linkedin']; + if (validSocialAccounts.indexOf(social) === -1) { + req.flash('errors', { + msg: 'Invalid social account' + }); + return res.redirect('/' + username); + } + + if (!user[social]) { + req.flash('errors', { + msg: `No ${social} account associated` + }); + return res.redirect('/' + username); + } + + const query = { + where: { + provider: social + } + }; + + return user.identities(query, function(err, identities) { + if (err) { return next(err); } + + // assumed user identity is unique by provider + let identity = identities.shift(); + if (!identity) { + req.flash('errors', { + msg: 'No social account found' + }); + return res.redirect('/' + username); + } + + return identity.destroy(function(err) { + if (err) { return next(err); } + + const updateData = { [social]: null }; + + return user.update$(updateData) + .subscribe(() => { + debug(`${social} has been unlinked successfully`); + + req.flash('info', { + msg: `You\'ve successfully unlinked your ${social}.` + }); + return res.redirect('/' + username); + }, next); + }); + }); + } + function showUserProfile(req, res, next) { const username = req.params.username.toLowerCase(); const { user } = req;