Hi guys,
I have been using this plugin (like everyone else) [https://github.com/julianlam/nodebb-plugin-sso-oauth] to make a SSO plugin for Nodebb.
This particular variant will be for Magento 1 where they use OAuth 1.0. Generally speaking, the plugin works well with a few code tweaks. However, it always seems to request a new token rather then using the existing, or refreshing if needed. I can guarantee the issue is my code .. but I seem to be stuck on where to begin on figuring out what should be done here.
I have looked around, and in the other SSO plugins that are around, but it seems like it automagically happens without much code done to make it so. Everything else works but that last little step..
[code]
(function(module) {
"use strict";
var User = module.parent.require('./user'),
Groups = module.parent.require('./groups'),
meta = module.parent.require('./meta'),
db = module.parent.require('../src/database'),
passport = module.parent.require('passport'),
fs = module.parent.require('fs'),
path = module.parent.require('path'),
nconf = module.parent.require('nconf'),
winston = module.parent.require('winston'),
async = module.parent.require('async');
var authenticationController = module.parent.require('./controllers/authentication');
var constants = Object.freeze({
type: 'oauth',
name: 'Magento',
admin: {
'route': '/plugins/sso-magento',
'icon': 'fa-twitter-square'
},
});
var Magento = {}, passportOAuth, opts;
Magento.init = function(data, callback) {
function render(req, res, next) {
res.render('admin/plugins/sso-magento', {});
}
data.router.get('/admin/plugins/sso-magento', data.middleware.admin.buildHeader, render);
data.router.get('/api/admin/plugins/sso-magento', render);
callback();
};
Magento.getStrategy = function(strategies, callback) {
meta.settings.get('sso-magento', function(err, settings) {
if (!err && settings['key']
&& settings['secret']
&& settings['requesttoken']
&& settings['accesstoken']
&& settings['userauthorize']
&& settings['userroute'])
{
passportOAuth = require('passport-oauth')[constants.type === 'oauth' ? 'OAuthStrategy' : 'OAuth2Strategy'];
var oauth = {
requestTokenURL: settings['requesttoken'],
accessTokenURL: settings['accesstoken'],
userAuthorizationURL: settings['userauthorize'],
consumerKey: settings['key'],
consumerSecret: settings['secret'],
callbackURL: settings['callback']
};
if (constants.type === 'oauth') {
// OAuth options
opts = oauth;
passportOAuth.Strategy.prototype.userProfile = function(token, secret, params, done) {
this._oauth.get(settings['userroute'], token, secret, function(err, body, res) {
if (err) { return done(err); }
try {
var json = JSON.parse(body);
Magento.parseUserReturn(json, function(err, profile) {
if (err) return done(err);
profile.provider = constants.name;
done(null, profile);
});
} catch(e) {
done(e);
}
});
};
}
passport.use(constants.name, new passportOAuth(opts, function(token, secret, profile, done) {
Magento.login({
oAuthid: profile.id,
handle: profile.displayName,
email: profile.emails[0].value,
isAdmin: profile.isAdmin
}, function(err, user) {
if (err) {
return done(err);
}
done(null, user);
});
}));
strategies.push({
name: constants.name,
url: '/auth/' + constants.name,
callbackURL: '/auth/' + constants.name + '/callback',
icon: 'fa-check-square',
scope: (constants.scope || '').split(',')
});
callback(null, strategies);
} else {
callback(new Error('Magento OAuth Configuration is invalid'));
}
});
}
Magento.parseUserReturn = function(data, callback) {
for (var key in data) break;
var profile = {};
profile.id = key;
profile.displayName = data[key].firstname + data[key].lastname;
profile.emails = [{ value: data[key].email }];
callback(null, profile);
}
Magento.addMenuItem = function(custom_header, callback) {
custom_header.authentication.push({
"route": constants.admin.route,
"icon": constants.admin.icon,
"name": constants.name
});
callback(null, custom_header);
};
Magento.login = function(payload, callback) {
Magento.getUidByOAuthid(payload.oAuthid, function(err, uid) {
if(err) {
return callback(err);
}
if (uid !== null) {
// Existing User
callback(null, {
uid: uid
});
} else {
// New User
var success = function(uid) {
// Save provider-specific information to the user
User.setUserField(uid, constants.name + 'Id', payload.oAuthid);
db.setObjectField(constants.name + 'Id:uid', payload.oAuthid, uid);
if (payload.isAdmin) {
Groups.join('administrators', uid, function(err) {
callback(null, {
uid: uid
});
});
} else {
callback(null, {
uid: uid
});
}
};
User.getUidByEmail(payload.email, function(err, uid) {
if(err) {
return callback(err);
}
if (!uid) {
User.create({
username: payload.handle,
email: payload.email
}, function(err, uid) {
if(err) {
return callback(err);
}
success(uid);
});
} else {
success(uid); // Existing account -- merge
}
});
}
});
};
Magento.getUidByOAuthid = function(oAuthid, callback) {
db.getObjectField(constants.name + 'Id:uid', oAuthid, function(err, uid) {
if (err) {
return callback(err);
}
callback(null, uid);
});
};
Magento.deleteUserData = function(uid, callback) {
async.waterfall([
async.apply(User.getUserField, uid, constants.name + 'Id'),
function(oAuthIdToDelete, next) {
db.deleteObjectField(constants.name + 'Id:uid', oAuthIdToDelete, next);
}
], function(err) {
if (err) {
winston.error('[sso-oauth] Could not remove OAuthId data for uid ' + uid + '. Error: ' + err);
return callback(err);
}
callback(null, uid);
});
};
module.exports = Magento;
}(module));
[/code]