73 lines
2.2 KiB
TypeScript
73 lines
2.2 KiB
TypeScript
import { InferSchemaType, Model, Schema, StringSchemaDefinition, Types } from 'mongoose';
|
|
|
|
import { TokenType } from '@mifi/auth-common/lib/enums/tokens';
|
|
import { getDefaultExpiresFor } from '@mifi/auth-common/lib/helpers/getDefaultExpiresFor';
|
|
import { sign, verify } from '@mifi/auth-common/lib/utils/jwt';
|
|
import { SignProps } from '@mifi/auth-common/lib/utils/jwt/sign';
|
|
|
|
export interface Token {
|
|
auth: StringSchemaDefinition;
|
|
expires?: number;
|
|
type: TokenType;
|
|
}
|
|
|
|
export interface TokenModel extends Model<Token> {
|
|
cleanupExpiredTokens(): { success: boolean; deletedCount: number };
|
|
getToken(type: TokenType, auth: Types.ObjectId, expires?: number): string;
|
|
validateResetToken(token: string): Types.ObjectId | false;
|
|
}
|
|
|
|
export const TokenSchema = new Schema<Token, TokenModel>(
|
|
{
|
|
auth: { type: Types.ObjectId, index: true },
|
|
expires: { type: Number, required: true },
|
|
type: { type: String, enum: TokenType, required: true },
|
|
},
|
|
{
|
|
minimize: true,
|
|
timestamps: true,
|
|
},
|
|
);
|
|
|
|
TokenSchema.statics = {
|
|
async cleanupExpiredTokens() {
|
|
const { acknowledged, deletedCount } = await this.deleteMany({
|
|
expires: { $lte: Date.now() },
|
|
});
|
|
return { success: acknowledged, deletedCount };
|
|
},
|
|
|
|
async getToken(type: TokenType, auth: StringSchemaDefinition, expires?: number) {
|
|
const existing = await this.findOne({ type, auth });
|
|
if (existing) {
|
|
await existing.deleteOne();
|
|
}
|
|
|
|
const doc = await this.create({
|
|
type,
|
|
auth,
|
|
expires: expires || getDefaultExpiresFor(type),
|
|
});
|
|
return sign({
|
|
sub: `${doc._id}`,
|
|
exp: doc.expires,
|
|
} as SignProps);
|
|
},
|
|
|
|
async validateResetToken(token: string) {
|
|
const { sub } = verify(token);
|
|
|
|
if (sub) {
|
|
const record = await this.findById(sub);
|
|
if (record) {
|
|
await record.deleteOne();
|
|
return !!record?.expires && record.expires >= Date.now() && record.auth;
|
|
}
|
|
}
|
|
|
|
return false;
|
|
},
|
|
};
|
|
|
|
export type TokenSchema = InferSchemaType<typeof TokenSchema>;
|