RateLimiter.test.mjs 2.9 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495
  1. import { vi, expect } from 'vitest'
  2. import sinon from 'sinon'
  3. const modulePath = '../../../../app/src/infrastructure/RateLimiter'
  4. describe('RateLimiter', function () {
  5. beforeEach(async function (ctx) {
  6. ctx.rclient = {}
  7. ctx.RedisWrapper = {
  8. client: sinon.stub().returns(ctx.rclient),
  9. }
  10. ctx.RateLimiter = {
  11. RateLimiter: sinon.stub().withArgs('login').returns(ctx.rateLimiter),
  12. }
  13. ctx.RateLimiterFlexible = {
  14. RateLimiterRedis: sinon.stub(),
  15. }
  16. ctx.Settings = {}
  17. vi.doMock('../../../../app/src/infrastructure/RedisWrapper', () => ({
  18. default: ctx.RedisWrapper,
  19. }))
  20. vi.doMock('rate-limiter-flexible', () => ({
  21. default: ctx.RateLimiterFlexible,
  22. }))
  23. vi.doMock('@overleaf/settings', () => ({
  24. default: ctx.Settings,
  25. }))
  26. ctx.RateLimiter = (await import(modulePath)).default
  27. })
  28. describe('getSubnetKeyFromIp', function () {
  29. beforeEach(function (ctx) {
  30. ctx.rateLimiter = new ctx.RateLimiter.RateLimiter('some-limit', {
  31. points: 20,
  32. subnetPoints: 200,
  33. duration: 60,
  34. })
  35. })
  36. it('should correctly extract a subnet key from an ip address', function (ctx) {
  37. expect(ctx.rateLimiter.getSubnetKeyFromIp('255.255.255.255')).to.equal(
  38. '255.255.255'
  39. )
  40. expect(ctx.rateLimiter.getSubnetKeyFromIp('127.0.0.1')).to.equal(
  41. '127.0.0'
  42. )
  43. expect(ctx.rateLimiter.getSubnetKeyFromIp('243.12.3.126')).to.equal(
  44. '243.12.3'
  45. )
  46. })
  47. it('should throw an error when given an incorrectly formatted ip', function (ctx) {
  48. expect(() => ctx.rateLimiter.getSubnetKeyFromIp(1)).to.throw()
  49. expect(() => ctx.rateLimiter.getSubnetKeyFromIp('Not an ip')).to.throw()
  50. expect(() =>
  51. ctx.rateLimiter.getSubnetKeyFromIp('255.255.255.255.255.255')
  52. ).to.throw()
  53. expect(() => ctx.rateLimiter.getSubnetKeyFromIp('255.255.255')).to.throw()
  54. })
  55. })
  56. describe('_subnetRateLimiter', function () {
  57. it('should be defined by default', function (ctx) {
  58. const rateLimiter = new ctx.RateLimiter.RateLimiter('some-limit', {
  59. points: 20,
  60. subnetPoints: 200,
  61. duration: 60,
  62. })
  63. expect(rateLimiter._subnetRateLimiter).not.to.be.undefined
  64. })
  65. it('should be undefined when subnet rate limiting is disabled', function (ctx) {
  66. ctx.Settings.rateLimit = { subnetRateLimiterDisabled: true }
  67. const rateLimiter = new ctx.RateLimiter.RateLimiter('some-limit', {
  68. points: 20,
  69. subnetPoints: 200,
  70. duration: 60,
  71. })
  72. expect(rateLimiter._subnetRateLimiter).to.be.undefined
  73. })
  74. it('should be undefined when subnetPoints are not passed as an option', function (ctx) {
  75. const rateLimiter = new ctx.RateLimiter.RateLimiter('some-limit', {
  76. points: 20,
  77. duration: 60,
  78. })
  79. expect(rateLimiter._subnetRateLimiter).to.be.undefined
  80. })
  81. })
  82. })