@krypton-org/krypton-auth
Version:
Express authentication middleware, using GraphQL and JSON Web Tokens.
170 lines (169 loc) • 6.84 kB
JavaScript
"use strict";
/**
* Module returning the Mongoose schema merging the default one with the fields provided by the package user through the `extendedSchema` property.
* @module router/Router
*/
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
return new (P || (P = Promise))(function (resolve, reject) {
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
step((generator = generator.apply(thisArg, _arguments || [])).next());
});
};
var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod };
};
var __importStar = (this && this.__importStar) || function (mod) {
if (mod && mod.__esModule) return mod;
var result = {};
if (mod != null) for (var k in mod) if (Object.hasOwnProperty.call(mod, k)) result[k] = mod[k];
result["default"] = mod;
return result;
};
Object.defineProperty(exports, "__esModule", { value: true });
const accepts_1 = __importDefault(require("accepts"));
const body_parser_1 = __importDefault(require("body-parser"));
const cookie_1 = require("cookie");
const cookie_parser_1 = __importDefault(require("cookie-parser"));
const express_1 = __importDefault(require("express"));
const express_graphql_1 = __importDefault(require("express-graphql"));
const helmet_1 = __importDefault(require("helmet"));
const pem_jwk_1 = require("pem-jwk");
const socket_io_1 = __importDefault(require("socket.io"));
const config_1 = __importDefault(require("../config"));
const UserController = __importStar(require("../controller/UserController"));
const TokenGenerator_1 = __importDefault(require("../crypto/TokenGenerator"));
const ErrorHandler_1 = __importDefault(require("../error/ErrorHandler"));
const ErrorTypes_1 = __importDefault(require("../error/ErrorTypes"));
const renderGraphiQL_1 = __importDefault(require("../graphiql/renderGraphiQL"));
const Schema_1 = __importDefault(require("../graphql/Schema"));
const UserModel_1 = __importDefault(require("../model/UserModel"));
const router = express_1.default.Router();
router.use(cookie_parser_1.default());
router.use(body_parser_1.default.json());
router.use(body_parser_1.default.urlencoded({ extended: true }));
router.use(helmet_1.default());
router.use((req, res, next) => __awaiter(void 0, void 0, void 0, function* () {
const bearerHeader = req.headers.authorization;
if (typeof bearerHeader !== 'undefined') {
const bearer = bearerHeader.split(' ');
const bearerToken = bearer[1];
try {
const user = yield UserModel_1.default.verify(bearerToken, config_1.default.publicKey);
req.user = user;
}
catch (err) {
// Do nothing user has to log-in or refresh his auth token.
}
}
next();
}));
const jwk = pem_jwk_1.pem2jwk(config_1.default.publicKey);
router.get('/.well-known/jwks.json', (req, res, next) => {
res.json({
keys: [jwk],
});
});
router.get('/user/email/confirmation', UserController.confirmEmail);
router.get('/form/reset/password', UserController.resetPasswordForm);
if (config_1.default.graphiql) {
router.use('/', (req, res, next) => __awaiter(void 0, void 0, void 0, function* () {
if (!config_1.default.io && !config_1.default.nodemailerConfig) {
// @ts-ignore
config_1.default.io = socket_io_1.default(req.socket.server);
config_1.default.clientIdToSocket = new Map();
config_1.default.io.on('connection', socket => {
let clientId = null;
if (socket.handshake.headers.cookie) {
clientId = cookie_1.parse(socket.handshake.headers.cookie).clientId;
}
if (clientId) {
config_1.default.clientIdToSocket.set(clientId, socket);
socket.on('disconnect', () => {
if (config_1.default.clientIdToSocket.has(clientId)) {
config_1.default.clientIdToSocket.delete(clientId);
}
});
}
else {
socket.disconnect(true);
}
});
}
if (!req.cookies.clientId) {
const cookieParams = { httpOnly: true };
if (config_1.default.host) {
cookieParams.domain = '.' + config_1.default.getDomainAddress();
}
res.cookie('clientId', TokenGenerator_1.default(32), cookieParams);
}
const params = yield express_graphql_1.default.getGraphQLParams(req);
params.query = defaultQuery();
if (!params.raw && accepts_1.default(req).types(['json', 'html']) === 'html') {
res.setHeader('Content-Type', 'text/html; charset=utf-8');
res.send(renderGraphiQL_1.default(params));
}
else {
next();
}
}));
}
router.use('/', express_graphql_1.default((req, res) => __awaiter(void 0, void 0, void 0, function* () {
return {
context: { req, res },
customFormatErrorFn: (err) => {
// @ts-ignore
const operationalError = err.originalError;
if (operationalError instanceof ErrorTypes_1.default) {
return {
message: operationalError.message,
type: operationalError.type,
};
}
else {
// @ts-ignore
err.type = err.constructor.name;
return err;
}
},
graphiql: false,
schema: Schema_1.default,
};
})));
router.use(ErrorHandler_1.default);
function defaultQuery() {
return `# Welcome to Krypton Authentication
#
# You can use GraphiQL IDE to test GraphQL queries.
#
# Use this query to register.
#
# mutation{
# register(fields:{email: "your@mail.com" password:"yourpassword"})
# }
#
# Use this query to log-in.
#
# mutation{
# login(email: "your@mail.com", password:"yourpassword"){
# token
# expiryDate
# }
# }
#
# Keyboard shortcuts:
#
# Prettify Query: Shift-Ctrl-P (or press the prettify button above)
#
# Merge Query: Shift-Ctrl-M (or press the merge button above)
#
# Run Query: Ctrl-Enter (or press the play button above)
#
# Auto Complete: Ctrl-Space (or just start typing)
#
`;
}
exports.default = router;
//# sourceMappingURL=Router.js.map