first commit
This commit is contained in:
136
models/Session.js
Normal file
136
models/Session.js
Normal file
@@ -0,0 +1,136 @@
|
||||
import mongoose from 'mongoose';
|
||||
|
||||
const SessionSchema = new mongoose.Schema(
|
||||
{
|
||||
userId: {
|
||||
type: mongoose.Schema.Types.ObjectId,
|
||||
ref: 'User',
|
||||
required: true,
|
||||
index: true,
|
||||
},
|
||||
steamId: {
|
||||
type: String,
|
||||
required: true,
|
||||
index: true,
|
||||
},
|
||||
token: {
|
||||
type: String,
|
||||
required: true,
|
||||
unique: true,
|
||||
},
|
||||
refreshToken: {
|
||||
type: String,
|
||||
required: true,
|
||||
unique: true,
|
||||
},
|
||||
ip: {
|
||||
type: String,
|
||||
default: null,
|
||||
},
|
||||
userAgent: {
|
||||
type: String,
|
||||
default: null,
|
||||
},
|
||||
device: {
|
||||
type: String,
|
||||
default: null,
|
||||
},
|
||||
browser: {
|
||||
type: String,
|
||||
default: null,
|
||||
},
|
||||
os: {
|
||||
type: String,
|
||||
default: null,
|
||||
},
|
||||
location: {
|
||||
country: { type: String, default: null },
|
||||
city: { type: String, default: null },
|
||||
region: { type: String, default: null },
|
||||
},
|
||||
isActive: {
|
||||
type: Boolean,
|
||||
default: true,
|
||||
},
|
||||
lastActivity: {
|
||||
type: Date,
|
||||
default: Date.now,
|
||||
},
|
||||
expiresAt: {
|
||||
type: Date,
|
||||
required: true,
|
||||
index: { expires: 0 }, // TTL index - automatically delete expired sessions
|
||||
},
|
||||
},
|
||||
{
|
||||
timestamps: true,
|
||||
}
|
||||
);
|
||||
|
||||
// Index for cleaning up old sessions
|
||||
SessionSchema.index({ createdAt: 1 });
|
||||
SessionSchema.index({ userId: 1, isActive: 1 });
|
||||
|
||||
// Method to mark session as inactive
|
||||
SessionSchema.methods.deactivate = async function () {
|
||||
this.isActive = false;
|
||||
return this.save();
|
||||
};
|
||||
|
||||
// Method to update last activity
|
||||
SessionSchema.methods.updateActivity = async function () {
|
||||
this.lastActivity = Date.now();
|
||||
return this.save();
|
||||
};
|
||||
|
||||
// Static method to clean up inactive sessions for a user
|
||||
SessionSchema.statics.cleanupUserSessions = async function (userId, keepCurrent = null) {
|
||||
const query = {
|
||||
userId,
|
||||
isActive: false,
|
||||
};
|
||||
|
||||
if (keepCurrent) {
|
||||
query._id = { $ne: keepCurrent };
|
||||
}
|
||||
|
||||
return this.deleteMany(query);
|
||||
};
|
||||
|
||||
// Static method to get active sessions for a user
|
||||
SessionSchema.statics.getActiveSessions = async function (userId) {
|
||||
return this.find({
|
||||
userId,
|
||||
isActive: true,
|
||||
expiresAt: { $gt: new Date() },
|
||||
}).sort({ lastActivity: -1 });
|
||||
};
|
||||
|
||||
// Static method to revoke all sessions except current
|
||||
SessionSchema.statics.revokeAllExcept = async function (userId, currentSessionId) {
|
||||
return this.updateMany(
|
||||
{
|
||||
userId,
|
||||
_id: { $ne: currentSessionId },
|
||||
isActive: true,
|
||||
},
|
||||
{
|
||||
$set: { isActive: false },
|
||||
}
|
||||
);
|
||||
};
|
||||
|
||||
// Static method to revoke all sessions
|
||||
SessionSchema.statics.revokeAll = async function (userId) {
|
||||
return this.updateMany(
|
||||
{
|
||||
userId,
|
||||
isActive: true,
|
||||
},
|
||||
{
|
||||
$set: { isActive: false },
|
||||
}
|
||||
);
|
||||
};
|
||||
|
||||
export default mongoose.model('Session', SessionSchema);
|
||||
Reference in New Issue
Block a user