first commit

This commit is contained in:
spiduler
2020-09-02 10:18:55 +09:00
commit 291eaf85a5
6 changed files with 267 additions and 0 deletions

3
.gitignore vendored Normal file
View File

@@ -0,0 +1,3 @@
node_modules/
package-lock.json

BIN
README.md Normal file

Binary file not shown.

89
app/services.js Normal file
View File

@@ -0,0 +1,89 @@
var uuid = require('node-uuid'),
authCodes = {},
accessTokens = {},
tokenHeartbeats = {},
clients = {
'F8Nbz9gGUvLgdn8T': {
id: '1',
secret: 'Fesmx7hHCCMx7Cby7FhV2fAtf2NYEFzP5fCKuwEEdpf8hpnsnnQn9qYhNHt6SsDD',
grantTypes: ['client_credentials']
},
'dev52VrnSufxEyKT': {
id: '2',
secret: 'nK2jnqhdWnrmAFDw9zWVueAqUQvSxmAyjf2Sz7ZrmYVSH5GSxER4rPQCuBUewF',
grantTypes: ['client_credentials']
}
};
const services = {
flushExpiredTokens: function (maxAge) {
let oldTokens = [];
let now = new Date().getTime();
for (let token in accessTokens) {
if (tokenHeartbeats[token] && tokenHeartbeats[token] < now - 1000 * maxAge) {
oldTokens.push(token)
delete accessTokens[token]
}
}
console.log('Flush expired tokens execution completed.', oldTokens)
},
getAccessTokens: function () {
return accessTokens;
},
getClients: function () {
return clients;
},
heartbeat: {
puls: function (token) {
tokenHeartbeats[token] = new Date().getTime();
},
signal: function (authHeader) {
if (authHeader) {
let token = authHeader.split(' ').pop()
if (accessTokens[token]) {
services.heartbeat.puls(token)
return tokenHeartbeats[token];
}
}
return false;
}
},
clientService: {
getById: function (id, callback) {
return callback(null, clients[id]);
},
isValidRedirectUri: function (/*client, requestedUri*/) {
return true;
}
},
tokenService: {
generateToken: function (callback) {
callback(null, uuid.v4());
},
generateAuthorizationCode: function (callback) {
callback(null, uuid.v4());
}
},
authorizationService: {
saveAuthorizationCode: function (codeData, callback) {
authCodes[codeData.code] = codeData;
return callback(null, authCodes[codeData.code]);
},
saveAccessToken: function (tokenData, callback) {
accessTokens[tokenData.access_token] = tokenData;
return callback(null, accessTokens[tokenData.access_token]);
},
getAuthorizationCode: function (code, callback) {
return callback(null, authCodes[code]);
},
getAccessToken: function (token, callback) {
return callback(null, accessTokens[token]);
}
},
membershipService: {
areUserCredentialsValid: function (userName, password, scope, callback) {
return callback(null, true);
}
}
}
module.exports = services

139
index.js Normal file
View File

@@ -0,0 +1,139 @@
var proxy = require('express-http-proxy'),
express = require('express'),
expressLogging = require('express-logging'),
logger = require('logops'),
port = 32100, hostname = '127.0.0.1',
supportedScopes = ['profile', 'status', 'avatar'],
expiresIn = 3600,
low = require('lowdb'),
FileSync = require('lowdb/adapters/FileSync'),
HttpStatus = require('http-status-codes'),
cron = require('node-cron');
const services = require('./app/services');
const adapter = new FileSync(__dirname + '/storage/db.json')
const db = low(adapter)
db.get('authCodes').value()
.forEach(codeData => {
codeData.expiresDate = function () {
var d = new Date();
d.setDate(d.getDate() + 2);
return d;
}();
services.authorizationService.saveAuthorizationCode(codeData, function (n, codeData) {
// console.log(codeData)
})
});
var OAuthServer = require('simple-oauth-server'),
oauthServer = new OAuthServer(
services.clientService,
services.tokenService,
services.authorizationService,
services.membershipService,
expiresIn,
supportedScopes
);
function authorize(request, response) {
response.statusCode = 403;
response.json({ code: 501, message: 'Not Implemented' });
return true;
oauthServer.authorizeRequest(request, 'accountid', function (error, authorizationResult) {
if (error) {
response.statusCode = 400;
return response.end(JSON.stringify(error));
}
// var code = require('url').parse(authorizationResult.redirectUri, true).query.code;
// response.statusCode = 302;
// response.setHeader('Location', 'http://localhost:8080/oauth/token?client_id=1&grant_type=authorization_code&client_secret=kittens&code=' + code);
response.end(JSON.stringify(authorizationResult));
});
}
function grantToken(request, response) {
oauthServer.grantAccessToken(request, function (error, token) {
if (error) {
console.log(error)
response.statusCode = 400;
return response.json(error);
}
if (services.getClients()[request.query.client_id].id == 1) {
services.heartbeat.puls(token.access_token);
}
response.json(token);
});
}
function apiEndpoint(request, response) {
console.log(oauthServer.validateAccessToken(request, function (error, validationResult) {
if (error) {
response.statusCode = 401;
return response.json(error);
}
response.json(validationResult);
}));
}
function heartbeat(request, response) {
let updated = services.heartbeat.signal(request.headers.authorization);
response.json({ code: updated ? 200 : 400, data: updated });
}
cron.schedule('0 * * * * *', () => {
services.flushExpiredTokens(300);
});
const app = express()
app.use(expressLogging(logger));
const proxyFilter = function (req, res) {
return req.hostname == hostname ? true : new Promise(function (resolve) {
resolve(function () {
if (req.headers.authorization) {
let tokenData = services.getAccessTokens()[req.headers.authorization.split(' ').pop()];
// console.log('App token data', tokenData)
if (!tokenData || !tokenData.access_token) {
res.json({ code: HttpStatus.NOT_ACCEPTABLE })
return false;
}
if (tokenData.expiresDate < new Date()) {
res.json({ code: HttpStatus.NOT_ACCEPTABLE })
return false;
}
return true;
}
return false;
}());
});
}
app.use('/api/v1/headless', proxy('127.0.0.1:32101', {
filter: proxyFilter
}));
app.use('/api/v1/spider', proxy('127.0.0.1:32102', {
filter: proxyFilter
}));
app.use('/api/v1/spiduler', proxy('127.0.0.1:32103', {
filter: proxyFilter
}));
app.get('/oauth/authorize', authorize)
app.get('/api/v1/oauth/token', grantToken)
app.get('/oauth/token', grantToken)
app.get('/api/test', apiEndpoint)
app.listen(port)
console.log('Server starting port ' + port)

25
package.json Normal file
View File

@@ -0,0 +1,25 @@
{
"name": "cm-auth",
"version": "1.0.0",
"description": "",
"main": "index.js",
"dependencies": {
"express": "^4.17.1",
"express-http-proxy": "^1.5.1",
"express-logging": "^1.1.1",
"http-status-codes": "^1.3.2",
"kgo": "^4.0.3",
"logops": "^2.1.1",
"lowdb": "^1.0.0",
"node-cron": "^2.0.3",
"node-uuid": "^1.4.8",
"simple-oauth-server": "^1.0.6"
},
"devDependencies": {},
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1",
"start": "node app/index.js"
},
"author": "",
"license": "ISC"
}

11
storage/db.json Normal file
View File

@@ -0,0 +1,11 @@
{
"authCodes": [
{
"code": "a9c6380a-9e34-467f-a1ae-514bb51a7724",
"redirectUri": "http://google.com",
"clientId": "F8Nbz9gGUvLgdn8T",
"expiresDate": null,
"accountId": "accountid"
}
]
}