singledo_test.go 1.2 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970
  1. package singledo
  2. import (
  3. "sync"
  4. "testing"
  5. "time"
  6. "github.com/metacubex/mihomo/common/atomic"
  7. "github.com/stretchr/testify/assert"
  8. )
  9. func TestBasic(t *testing.T) {
  10. single := NewSingle[int](time.Millisecond * 30)
  11. foo := 0
  12. shardCount := atomic.NewInt32(0)
  13. call := func() (int, error) {
  14. foo++
  15. time.Sleep(time.Millisecond * 5)
  16. return 0, nil
  17. }
  18. var wg sync.WaitGroup
  19. const n = 5
  20. wg.Add(n)
  21. for i := 0; i < n; i++ {
  22. go func() {
  23. _, _, shard := single.Do(call)
  24. if shard {
  25. shardCount.Add(1)
  26. }
  27. wg.Done()
  28. }()
  29. }
  30. wg.Wait()
  31. assert.Equal(t, 1, foo)
  32. assert.Equal(t, int32(4), shardCount.Load())
  33. }
  34. func TestTimer(t *testing.T) {
  35. single := NewSingle[int](time.Millisecond * 30)
  36. foo := 0
  37. callM := func() (int, error) {
  38. foo++
  39. return 0, nil
  40. }
  41. _, _, _ = single.Do(callM)
  42. time.Sleep(10 * time.Millisecond)
  43. _, _, shard := single.Do(callM)
  44. assert.Equal(t, 1, foo)
  45. assert.True(t, shard)
  46. }
  47. func TestReset(t *testing.T) {
  48. single := NewSingle[int](time.Millisecond * 30)
  49. foo := 0
  50. callM := func() (int, error) {
  51. foo++
  52. return 0, nil
  53. }
  54. _, _, _ = single.Do(callM)
  55. single.Reset()
  56. _, _, _ = single.Do(callM)
  57. assert.Equal(t, 2, foo)
  58. }