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.

149 lines
3.5 KiB

2 years ago
  1. package wdclient
  2. import (
  3. "fmt"
  4. "google.golang.org/grpc"
  5. "strconv"
  6. "sync"
  7. "testing"
  8. )
  9. func TestLocationIndex(t *testing.T) {
  10. vm := vidMap{}
  11. // test must be failed
  12. mustFailed := func(length int) {
  13. _, err := vm.getLocationIndex(length)
  14. if err == nil {
  15. t.Errorf("length %d must be failed", length)
  16. }
  17. if err.Error() != fmt.Sprintf("invalid length: %d", length) {
  18. t.Errorf("length %d must be failed. error: %v", length, err)
  19. }
  20. }
  21. mustFailed(-1)
  22. mustFailed(0)
  23. mustOk := func(length, cursor, expect int) {
  24. if length <= 0 {
  25. t.Fatal("please don't do this")
  26. }
  27. vm.cursor = int32(cursor)
  28. got, err := vm.getLocationIndex(length)
  29. if err != nil {
  30. t.Errorf("length: %d, why? %v\n", length, err)
  31. return
  32. }
  33. if got != expect {
  34. t.Errorf("cursor: %d, length: %d, expect: %d, got: %d\n", cursor, length, expect, got)
  35. return
  36. }
  37. }
  38. for i := -1; i < 100; i++ {
  39. mustOk(7, i, (i+1)%7)
  40. }
  41. // when cursor reaches MaxInt64
  42. mustOk(7, maxCursorIndex, 0)
  43. // test with constructor
  44. vm = newVidMap("")
  45. length := 7
  46. for i := 0; i < 100; i++ {
  47. got, err := vm.getLocationIndex(length)
  48. if err != nil {
  49. t.Errorf("length: %d, why? %v\n", length, err)
  50. return
  51. }
  52. if got != i%length {
  53. t.Errorf("length: %d, i: %d, got: %d\n", length, i, got)
  54. }
  55. }
  56. }
  57. func TestLookupFileId(t *testing.T) {
  58. mc := NewMasterClient(grpc.EmptyDialOption{}, "", "", "", "", "", nil)
  59. length := 5
  60. //Construct a cache linked list of length 5
  61. for i := 0; i < length; i++ {
  62. mc.addLocation(uint32(i), Location{Url: strconv.FormatInt(int64(i), 10)})
  63. mc.resetVidMap()
  64. }
  65. for i := 0; i < length; i++ {
  66. locations, found := mc.GetLocations(uint32(i))
  67. if !found || len(locations) != 1 || locations[0].Url != strconv.FormatInt(int64(i), 10) {
  68. t.Fatalf("urls of vid=%d is not valid.", i)
  69. }
  70. }
  71. //When continue to add nodes to the linked list, the previous node will be deleted, and the cache of the response will be gone.
  72. for i := length; i < length+5; i++ {
  73. mc.addLocation(uint32(i), Location{Url: strconv.FormatInt(int64(i), 10)})
  74. mc.resetVidMap()
  75. }
  76. for i := 0; i < length; i++ {
  77. locations, found := mc.GetLocations(uint32(i))
  78. if found {
  79. t.Fatalf("urls of vid[%d] should not exists, but found: %v", i, locations)
  80. }
  81. }
  82. //The delete operation will be applied to all cache nodes
  83. _, found := mc.GetLocations(uint32(length))
  84. if !found {
  85. t.Fatalf("urls of vid[%d] not found", length)
  86. }
  87. //If the locations of the current node exist, return directly
  88. newUrl := "abc"
  89. mc.addLocation(uint32(length), Location{Url: newUrl})
  90. locations, found := mc.GetLocations(uint32(length))
  91. if !found || locations[0].Url != newUrl {
  92. t.Fatalf("urls of vid[%d] not found", length)
  93. }
  94. //After delete `abc`, cache nodes are searched
  95. deleteLoc := Location{Url: newUrl}
  96. mc.deleteLocation(uint32(length), deleteLoc)
  97. locations, found = mc.GetLocations(uint32(length))
  98. if found && locations[0].Url != strconv.FormatInt(int64(length), 10) {
  99. t.Fatalf("urls of vid[%d] not expected", length)
  100. }
  101. //lock: concurrent test
  102. var wg sync.WaitGroup
  103. for i := 0; i < 20; i++ {
  104. wg.Add(1)
  105. go func() {
  106. defer wg.Done()
  107. for i := 0; i < 100; i++ {
  108. for i := 0; i < 20; i++ {
  109. _, _ = mc.GetLocations(uint32(i))
  110. }
  111. }
  112. }()
  113. }
  114. for i := 0; i < 100; i++ {
  115. mc.addLocation(uint32(i), Location{})
  116. }
  117. wg.Wait()
  118. }
  119. func BenchmarkLocationIndex(b *testing.B) {
  120. b.SetParallelism(8)
  121. vm := vidMap{
  122. cursor: maxCursorIndex - 4000,
  123. }
  124. b.ResetTimer()
  125. b.RunParallel(func(pb *testing.PB) {
  126. for pb.Next() {
  127. _, err := vm.getLocationIndex(3)
  128. if err != nil {
  129. b.Error(err)
  130. }
  131. }
  132. })
  133. }