You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

limiter_test.go 2.2KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495
  1. // Copyright (c) 2018 Shivaram Lingamneni
  2. // released under the MIT license
  3. package connection_limits
  4. import (
  5. "crypto/md5"
  6. "testing"
  7. "time"
  8. "github.com/ergochat/ergo/irc/flatip"
  9. )
  10. func easyParseIP(ipstr string) (result flatip.IP) {
  11. result, err := flatip.ParseIP(ipstr)
  12. if err != nil {
  13. panic(err)
  14. }
  15. return
  16. }
  17. var baseConfig = LimiterConfig{
  18. rawLimiterConfig: rawLimiterConfig{
  19. Count: true,
  20. MaxConcurrent: 4,
  21. Throttle: true,
  22. Window: time.Second * 600,
  23. MaxPerWindow: 8,
  24. CidrLenIPv4: 32,
  25. CidrLenIPv6: 64,
  26. Exempted: []string{"localhost"},
  27. CustomLimits: map[string]CustomLimitConfig{
  28. "google": {
  29. Nets: []string{"8.8.0.0/16"},
  30. MaxConcurrent: 128,
  31. MaxPerWindow: 256,
  32. },
  33. },
  34. },
  35. }
  36. func TestKeying(t *testing.T) {
  37. config := baseConfig
  38. config.postprocess()
  39. var limiter Limiter
  40. limiter.ApplyConfig(&config)
  41. // an ipv4 /32 looks like a /128 to us after applying the 4-in-6 mapping
  42. key, _, maxConc, maxWin := limiter.addrToKey(easyParseIP("1.1.1.1"))
  43. assertEqual(key.prefixLen, uint8(128), t)
  44. assertEqual(key.maskedIP[12:], []byte{1, 1, 1, 1}, t)
  45. assertEqual(maxConc, 4, t)
  46. assertEqual(maxWin, 8, t)
  47. testIPv6 := easyParseIP("2607:5301:201:3100::7426")
  48. key, _, maxConc, maxWin = limiter.addrToKey(testIPv6)
  49. assertEqual(key.prefixLen, uint8(64), t)
  50. assertEqual(flatip.IP(key.maskedIP), easyParseIP("2607:5301:201:3100::"), t)
  51. assertEqual(maxConc, 4, t)
  52. assertEqual(maxWin, 8, t)
  53. key, _, maxConc, maxWin = limiter.addrToKey(easyParseIP("8.8.4.4"))
  54. assertEqual(key.prefixLen, uint8(0), t)
  55. assertEqual([16]byte(key.maskedIP), md5.Sum([]byte("google")), t)
  56. assertEqual(maxConc, 128, t)
  57. assertEqual(maxWin, 256, t)
  58. }
  59. func TestLimits(t *testing.T) {
  60. regularIP := easyParseIP("2607:5301:201:3100::7426")
  61. config := baseConfig
  62. config.postprocess()
  63. var limiter Limiter
  64. limiter.ApplyConfig(&config)
  65. for i := 0; i < 4; i++ {
  66. err := limiter.AddClient(regularIP)
  67. if err != nil {
  68. t.Errorf("ip should not be blocked, but %v", err)
  69. }
  70. }
  71. err := limiter.AddClient(regularIP)
  72. if err != ErrLimitExceeded {
  73. t.Errorf("ip should be blocked, but %v", err)
  74. }
  75. limiter.RemoveClient(regularIP)
  76. err = limiter.AddClient(regularIP)
  77. if err != nil {
  78. t.Errorf("ip should not be blocked, but %v", err)
  79. }
  80. }