aegis-auth
Version:
A credentials-based auth solution for Next.js (and other Node projects) with IP rate-limiting, account lockouts, and sessions in DB.
86 lines • 3.46 kB
JavaScript
var __rest = (this && this.__rest) || function (s, e) {
var t = {};
for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && e.indexOf(p) < 0)
t[p] = s[p];
if (s != null && typeof Object.getOwnPropertySymbols === "function")
for (var i = 0, p = Object.getOwnPropertySymbols(s); i < p.length; i++) {
if (e.indexOf(p[i]) < 0 && Object.prototype.propertyIsEnumerable.call(s, p[i]))
t[p[i]] = s[p[i]];
}
return t;
};
import { generateCsrfToken, generateSessionToken } from "../security";
import { ErrorCodes } from "../types";
import { clientSafeSession, createTime, } from "../utils";
import { createSessionSchema } from "../validations";
export async function createSession(context, input) {
const { prisma, config, parsedRequest } = context;
const _a = parsedRequest !== null && parsedRequest !== void 0 ? parsedRequest : {}, { sessionToken, csrfToken } = _a, sessionInfo = __rest(_a, ["sessionToken", "csrfToken"]);
try {
// Validate input
const validatedInput = createSessionSchema.safeParse(input);
if (!validatedInput.success) {
return {
success: false,
status: 400,
message: "Invalid input provided",
code: ErrorCodes.INVALID_INPUT,
data: null,
};
}
const { userId } = validatedInput.data;
const activeSessions = await prisma.session.count({
where: {
userId: userId,
isRevoked: false,
},
});
if (config.session.maxSessionsPerUser > 0 &&
activeSessions >= config.session.maxSessionsPerUser) {
config.logger.securityEvent("SESSION_LIMIT_REACHED", {
userId: userId,
maxSessionsPerUser: config.session.maxSessionsPerUser,
});
return {
success: false,
status: 400,
message: "Session limit reached",
code: ErrorCodes.SESSION_LIMIT_REACHED,
};
}
const sessionTokens = await generateSessionToken({ config });
const sessionExpiry = createTime(config.session.maxAgeSeconds, "s").getDate();
const csrfTokens = await generateCsrfToken({ config });
const session = await prisma.session.create({
data: Object.assign({ csrfTokenHash: csrfTokens.csrfTokenHash, tokenHash: sessionTokens.sessionTokenHash, expiresAt: sessionExpiry, userId: userId }, sessionInfo),
});
config.logger.securityEvent("SESSION_CREATED", {
sessionId: session.id,
userId: userId,
});
const clientSession = clientSafeSession({
session: session,
sessionToken: sessionTokens.sessionToken,
csrfToken: csrfTokens.csrfToken,
});
return {
success: true,
status: 200,
message: "Session created",
data: { session: clientSession },
};
}
catch (error) {
config.logger.error("Error creating session", {
error,
userId: input.userId,
});
return {
success: false,
status: 500,
message: "An unexpected error occurred.",
code: ErrorCodes.INTERNAL_SERVER_ERROR,
};
}
}
//# sourceMappingURL=createSession.js.map