File size: 4,574 Bytes
f0743f4 | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 | const mongoose = require('mongoose');
const { MongoMemoryServer } = require('mongodb-memory-server');
const banViolation = require('./banViolation');
// Mock deleteAllUserSessions since we're testing ban logic, not session deletion
jest.mock('~/models', () => ({
...jest.requireActual('~/models'),
deleteAllUserSessions: jest.fn().mockResolvedValue(true),
}));
describe('banViolation', () => {
let mongoServer;
let req, res, errorMessage;
beforeAll(async () => {
mongoServer = await MongoMemoryServer.create();
const mongoUri = mongoServer.getUri();
await mongoose.connect(mongoUri);
});
afterAll(async () => {
await mongoose.disconnect();
await mongoServer.stop();
});
beforeEach(() => {
req = {
ip: '127.0.0.1',
cookies: {
refreshToken: 'someToken',
},
};
res = {
clearCookie: jest.fn(),
};
errorMessage = {
type: 'someViolation',
user_id: new mongoose.Types.ObjectId().toString(), // Use valid ObjectId
prev_count: 0,
violation_count: 0,
};
process.env.BAN_VIOLATIONS = 'true';
process.env.BAN_DURATION = '7200000'; // 2 hours in ms
process.env.BAN_INTERVAL = '20';
});
afterEach(() => {
jest.clearAllMocks();
});
it('should not ban if BAN_VIOLATIONS are not enabled', async () => {
process.env.BAN_VIOLATIONS = 'false';
await banViolation(req, res, errorMessage);
expect(errorMessage.ban).toBeFalsy();
});
it('should not ban if errorMessage is not provided', async () => {
await banViolation(req, res, null);
expect(errorMessage.ban).toBeFalsy();
});
it('[1/3] should ban if violation_count crosses the interval threshold: 19 -> 39', async () => {
errorMessage.prev_count = 19;
errorMessage.violation_count = 39;
await banViolation(req, res, errorMessage);
expect(errorMessage.ban).toBeTruthy();
});
it('[2/3] should ban if violation_count crosses the interval threshold: 19 -> 20', async () => {
errorMessage.prev_count = 19;
errorMessage.violation_count = 20;
await banViolation(req, res, errorMessage);
expect(errorMessage.ban).toBeTruthy();
});
const randomValueAbove = Math.floor(20 + Math.random() * 100);
it(`[3/3] should ban if violation_count crosses the interval threshold: 19 -> ${randomValueAbove}`, async () => {
errorMessage.prev_count = 19;
errorMessage.violation_count = randomValueAbove;
await banViolation(req, res, errorMessage);
expect(errorMessage.ban).toBeTruthy();
});
it('should handle invalid BAN_INTERVAL and default to 20', async () => {
process.env.BAN_INTERVAL = 'invalid';
errorMessage.prev_count = 19;
errorMessage.violation_count = 39;
await banViolation(req, res, errorMessage);
expect(errorMessage.ban).toBeTruthy();
});
it('should ban if BAN_DURATION is invalid as default is 2 hours', async () => {
process.env.BAN_DURATION = 'invalid';
errorMessage.prev_count = 19;
errorMessage.violation_count = 39;
await banViolation(req, res, errorMessage);
expect(errorMessage.ban).toBeTruthy();
});
it('should not ban if BAN_DURATION is 0 but should clear cookies', async () => {
process.env.BAN_DURATION = '0';
errorMessage.prev_count = 19;
errorMessage.violation_count = 39;
await banViolation(req, res, errorMessage);
expect(res.clearCookie).toHaveBeenCalledWith('refreshToken');
});
it('should not ban if violation_count does not change', async () => {
errorMessage.prev_count = 0;
errorMessage.violation_count = 0;
await banViolation(req, res, errorMessage);
expect(errorMessage.ban).toBeFalsy();
});
it('[1/2] should not ban if violation_count does not cross the interval threshold: 0 -> 19', async () => {
errorMessage.prev_count = 0;
errorMessage.violation_count = 19;
await banViolation(req, res, errorMessage);
expect(errorMessage.ban).toBeFalsy();
});
const randomValueUnder = Math.floor(1 + Math.random() * 19);
it(`[2/2] should not ban if violation_count does not cross the interval threshold: 0 -> ${randomValueUnder}`, async () => {
errorMessage.prev_count = 0;
errorMessage.violation_count = randomValueUnder;
await banViolation(req, res, errorMessage);
expect(errorMessage.ban).toBeFalsy();
});
it('[EDGE CASE] should not ban if violation_count is lower', async () => {
errorMessage.prev_count = 0;
errorMessage.violation_count = -10;
await banViolation(req, res, errorMessage);
expect(errorMessage.ban).toBeFalsy();
});
});
|