stub out keys and token parsing

This commit is contained in:
AJ ONeal 2015-12-04 07:00:30 +00:00
parent 8cc7234d64
commit 5cecf3ea45
4 changed files with 139 additions and 15 deletions

View File

@ -10,7 +10,6 @@ console.info('platform:', process.platform);
console.info('\n\n\n[MASTER] Welcome to WALNUT!');
var cluster = require('cluster');
var path = require('path');
//var minWorkers = 2;
var numCores = 2; // Math.max(minWorkers, require('os').cpus().length);
var workers = [];
@ -31,10 +30,6 @@ var conf = {
var state = {};
var caddy;
if (useCaddy) {
conf.caddypath = caddypath;
}
function fork() {
if (workers.length < numCores) {
workers.push(cluster.fork());
@ -42,7 +37,6 @@ function fork() {
}
cluster.on('online', function (worker) {
var path = require('path');
// TODO XXX Should these be configurable? If so, where?
var certPaths = config.certPaths;
var info;
@ -66,6 +60,9 @@ cluster.on('online', function (worker) {
// TODO let this load after server is listening
, redirects: config.redirects
, ddns: config.ddns
, 'org.oauth3.consumer': config['org.oauth3.consumer']
, 'org.oauth3.provider': config['org.oauth3.provider']
, keys: config.keys
}
};
worker.send(info);

95
lib/oauth3-auth.js Normal file
View File

@ -0,0 +1,95 @@
'use strict';
var PromiseA = require('bluebird');
module.exports.inject = function (app) {
//var jwsUtils = require('./lib/jws-utils').create(signer);
var CORS = require('connect-cors');
// Allows CORS access to API with ?access_token=
// TODO Access-Control-Max-Age: 600
// TODO How can we help apps handle this? token?
// TODO allow apps to configure trustedDomains, auth, etc
app.use('/', CORS({ credentials: true, headers: [
'X-Requested-With'
, 'X-HTTP-Method-Override'
, 'Content-Type'
, 'Accept'
, 'Authorization'
], methods: [ "GET", "POST", "PATCH", "PUT", "DELETE" ] }));
//function weakDecipher(secret, val) { return require('./weak-crypt').weakDecipher(val, secret); }
//
// Generic Session / Login / Account Routes
//
function parseAccessToken(req, opts) {
var token;
var parts;
var scheme;
var credentials;
if (req.headers && req.headers.authorization) {
parts = req.headers.authorization.split(' ');
if (parts.length !== 2) {
return PromiseA.reject(new Error("malformed Authorization header"));
}
scheme = parts[0];
credentials = parts[1];
if (-1 !== (opts && opts.schemes || ['token', 'bearer']).indexOf(scheme.toLowerCase())) {
token = credentials;
}
}
if (req.body && req.body.access_token) {
if (token) { PromiseA.reject(new Error("token exists in header and body")); }
token = req.body.access_token;
}
// TODO disallow query with req.method === 'GET'
// (cookies should be used for protected static assets)
if (req.query && req.query.access_token) {
if (token) { PromiseA.reject(new Error("token already exists in either header or body and also in query")); }
token = req.query.access_token;
}
/*
err = new Error(challenge());
err.code = 'E_BEARER_REALM';
if (!token) { return PromiseA.reject(err); }
*/
return PromiseA.resolve(token);
}
function getToken(req, res, next) {
req.oauth3 = {};
parseAccessToken(req).then(function (token) {
if (!token) {
next();
return;
}
var jwt = require('jsonwebtoken');
var data = jwt.decode(token);
var err;
if (!data) {
err = new Error('not a json web token');
err.code = 'E_NOT_JWT';
return PromiseA.reject(err);
}
req.oauth3.token = token;
next();
});
}
app.use('/', getToken);
};

View File

@ -143,7 +143,7 @@ function getApi(pkgConf, pkgDeps, packagedApi) {
if (packagedApi._apipkg.walnut) {
pkgpath += '/' + packagedApi._apipkg.walnut;
}
promise = require(pkgpath).create(pkgConf, pkgDeps, myApp);
promise = PromiseA.resolve(require(pkgpath).create(pkgConf, pkgDeps, myApp));
} catch(e) {
reject(e);
return;
@ -152,22 +152,39 @@ function getApi(pkgConf, pkgDeps, packagedApi) {
promise.then(function () {
// TODO give pub/priv pair for app and all public keys
// packagedApi._api = require(pkgpath).create(pkgConf, pkgDeps, myApp);
packagedApi._api = require('express')();
packagedApi._api = require('express-lazy')();
packagedApi._api_app = myApp;
require('./oauth3-auth').inject(packagedApi._api, pkgConf, pkgDeps);
// DEBUG
packagedApi._api.use('/', function (req, res, next) {
console.log('[DEBUG pkgsrv]', req.method, req.hostname, req.url);
next();
});
// TODO fix backwards compat
// /api/com.example.foo (no change)
packagedApi._api.use('/', packagedApi._api_app);
// /api/com.example.foo => /
packagedApi._api.use('/api/' + packagedApi.id, function (req, res, next) {
//console.log('api mangle 2:', '/api/' + packagedApi.api.id, req.url);
packagedApi._api_app(req, res, next);
});
// /api/com.example.foo => /api
packagedApi._api.use('/', function (req, res, next) {
var priorUrl = req.url;
req.url = '/api' + req.url.slice(('/api/' + packagedApi.id).length);
//console.log('api mangle 3:', req.url);
packagedApi._api_app(req, res, function (err) {
req.url = priorUrl;
next(err);
});
});
// /api/com.example.foo => /
packagedApi._api.use('/api/' + packagedApi.id, function (req, res, next) {
// console.log('api mangle 2:', '/api/' + packagedApi.id, req.url);
packagedApi._api_app(req, res, next);
});
resolve(packagedApi._api);
}, reject);
});
@ -289,7 +306,7 @@ function runApi(opts, router, req, res, next) {
return;
}
console.log("pkgpath", pkgConf.apipath, packagedApi.id);
console.log("[DEBUG pkgpath]", pkgConf.apipath, packagedApi.id);
loadApi(pkgConf, pkgDeps, packagedApi).then(function (api) {
api(req, res, next);
}, function (err) {

View File

@ -178,6 +178,9 @@ module.exports.create = function (webserver, info, state) {
, pubkey: info.conf.pubkey
, redirects: info.conf.redirects
, apiPrefix: '/api'
, 'org.oauth3.consumer': info.conf['org.oauth3.consumer']
, 'org.oauth3.provider': info.conf['org.oauth3.provider']
, keys: info.conf.keys
};
var pkgDeps = {
memstore: memstore
@ -198,6 +201,16 @@ module.exports.create = function (webserver, info, state) {
, systemSqlFactory: systemFactory
, Promise: PromiseA
});
var recase = require('connect-recase')({
// TODO allow explicit and or default flag
explicit: false
, default: 'snake'
, prefixes: ['/api']
// TODO allow exclude
//, exclusions: [config.oauthPrefix]
, exceptions: {}
//, cancelParam: 'camel'
});
function handlePackages(req, res, next) {
// TODO move to caddy parser?
@ -221,7 +234,7 @@ module.exports.create = function (webserver, info, state) {
// Generic Template API
//
app
.use(require('body-parser').json({
.use('/api', require('body-parser').json({
strict: true // only objects and arrays
, inflate: true
// limited to due performance issues with JSON.parse and JSON.stringify
@ -243,6 +256,8 @@ module.exports.create = function (webserver, info, state) {
.use(require('connect-send-error').error())
;
app.use('/api', recase);
app.use('/', handlePackages);
app.use('/', function (err, req, res, next) {
console.error('[Error Handler]');