Solve the problem that LookupFileId lookup urls is empty due to leader switching
The vidMap structure is modified to a linked list structure (the length is limited to 5). When the vidMap is reset, the current vidMap is added to the new vidMap as a cache node. When the query locations is empty, the cache node is searched to avoid problems when the master switches leaders.
This commit is contained in:
@@ -2,6 +2,8 @@ package wdclient
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"google.golang.org/grpc"
|
||||
"strconv"
|
||||
"testing"
|
||||
)
|
||||
|
||||
@@ -59,6 +61,71 @@ func TestLocationIndex(t *testing.T) {
|
||||
}
|
||||
}
|
||||
|
||||
func TestLookupFileId(t *testing.T) {
|
||||
mc := NewMasterClient(grpc.EmptyDialOption{}, "", "", "", "", nil)
|
||||
length := 5
|
||||
|
||||
//Construct a cache linked list of length 5
|
||||
for i := 0; i < length; i++ {
|
||||
mc.addLocation(uint32(i), Location{Url: strconv.FormatInt(int64(i), 10)})
|
||||
mc.resetVidMap()
|
||||
}
|
||||
for i := 0; i < length; i++ {
|
||||
locations, found := mc.GetLocations(uint32(i))
|
||||
if !found || len(locations) != 1 || locations[0].Url != strconv.FormatInt(int64(i), 10) {
|
||||
t.Fatalf("urls of vid=%d is not valid.", i)
|
||||
}
|
||||
}
|
||||
|
||||
//When continue to add nodes to the linked list, the previous node will be deleted, and the cache of the response will be gone.
|
||||
for i := length; i < length+5; i++ {
|
||||
mc.addLocation(uint32(i), Location{Url: strconv.FormatInt(int64(i), 10)})
|
||||
mc.resetVidMap()
|
||||
}
|
||||
for i := 0; i < length; i++ {
|
||||
locations, found := mc.GetLocations(uint32(i))
|
||||
if found {
|
||||
t.Fatalf("urls of vid[%d] should not exists, but found: %v", i, locations)
|
||||
}
|
||||
}
|
||||
|
||||
//The delete operation will be applied to all cache nodes
|
||||
_, found := mc.GetLocations(uint32(length))
|
||||
if !found {
|
||||
t.Fatalf("urls of vid[%d] not found", length)
|
||||
}
|
||||
|
||||
//If the locations of the current node exist, return directly
|
||||
newUrl := "abc"
|
||||
mc.addLocation(uint32(length), Location{Url: newUrl})
|
||||
locations, found := mc.GetLocations(uint32(length))
|
||||
if !found || locations[0].Url != newUrl {
|
||||
t.Fatalf("urls of vid[%d] not found", length)
|
||||
}
|
||||
|
||||
//After delete `abc`, cache nodes are searched
|
||||
deleteLoc := Location{Url: newUrl}
|
||||
mc.deleteLocation(uint32(length), deleteLoc)
|
||||
locations, found = mc.GetLocations(uint32(length))
|
||||
if found && locations[0].Url != strconv.FormatInt(int64(length), 10) {
|
||||
t.Fatalf("urls of vid[%d] not expected", length)
|
||||
}
|
||||
|
||||
//lock: concurrent test
|
||||
go func() {
|
||||
for i := 0; i < 100; i++ {
|
||||
mc.addLocation(uint32(i), Location{})
|
||||
}
|
||||
}()
|
||||
for i := 0; i < 10; i++ {
|
||||
for i := 0; i < 100; i++ {
|
||||
for i := 0; i < 20; i++ {
|
||||
_, _ = mc.GetLocations(uint32(i))
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func BenchmarkLocationIndex(b *testing.B) {
|
||||
b.SetParallelism(8)
|
||||
vm := vidMap{
|
||||
|
||||
Reference in New Issue
Block a user