Added a comment to volume Delete() about race condition.
[arvados.git] / services / keepstore / pull_worker_integration_test.go
1 package main
2
3 import (
4         "git.curoverse.com/arvados.git/sdk/go/arvadosclient"
5         "git.curoverse.com/arvados.git/sdk/go/arvadostest"
6         "git.curoverse.com/arvados.git/sdk/go/keepclient"
7         "net/http"
8         "os"
9         "strings"
10         "testing"
11 )
12
13 var keepClient keepclient.KeepClient
14
15 type PullWorkIntegrationTestData struct {
16         Name     string
17         Locator  string
18         Content  string
19         GetError string
20 }
21
22 func SetupPullWorkerIntegrationTest(t *testing.T, testData PullWorkIntegrationTestData, wantData bool) PullRequest {
23         os.Setenv("ARVADOS_API_HOST_INSECURE", "true")
24
25         // start api and keep servers
26         arvadostest.StartAPI()
27         arvadostest.StartKeep()
28
29         // make arvadosclient
30         arv, err := arvadosclient.MakeArvadosClient()
31         if err != nil {
32                 t.Error("Error creating arv")
33         }
34
35         // keep client
36         keepClient = keepclient.KeepClient{
37                 Arvados:       &arv,
38                 Want_replicas: 1,
39                 Using_proxy:   true,
40                 Client:        &http.Client{},
41         }
42
43         // discover keep services
44         var servers []string
45         service_roots, err := keepClient.DiscoverKeepServers()
46         if err != nil {
47                 t.Error("Error discovering keep services")
48         }
49         for _, host := range service_roots {
50                 servers = append(servers, host)
51         }
52
53         // Put content if the test needs it
54         if wantData {
55                 keepClient.SetServiceRoots(service_roots)
56                 locator, _, err := keepClient.PutB([]byte(testData.Content))
57                 if err != nil {
58                         t.Errorf("Error putting test data in setup for %s %s %v", testData.Content, locator, err)
59                 }
60                 if locator == "" {
61                         t.Errorf("No locator found after putting test data")
62                 }
63         }
64
65         // Create pullRequest for the test
66         pullRequest := PullRequest{
67                 Locator: testData.Locator,
68                 Servers: servers,
69         }
70         return pullRequest
71 }
72
73 // Do a get on a block that is not existing in any of the keep servers.
74 // Expect "block not found" error.
75 func TestPullWorkerIntegration_GetNonExistingLocator(t *testing.T) {
76         testData := PullWorkIntegrationTestData{
77                 Name:     "TestPullWorkerIntegration_GetLocator",
78                 Locator:  "5d41402abc4b2a76b9719d911017c592",
79                 Content:  "hello",
80                 GetError: "Block not found",
81         }
82
83         pullRequest := SetupPullWorkerIntegrationTest(t, testData, false)
84
85         performPullWorkerIntegrationTest(testData, pullRequest, t)
86 }
87
88 // Do a get on a block that exists on one of the keep servers.
89 // The setup method will create this block before doing the get.
90 func TestPullWorkerIntegration_GetExistingLocator(t *testing.T) {
91         testData := PullWorkIntegrationTestData{
92                 Name:     "TestPullWorkerIntegration_GetLocator",
93                 Locator:  "5d41402abc4b2a76b9719d911017c592",
94                 Content:  "hello",
95                 GetError: "",
96         }
97
98         pullRequest := SetupPullWorkerIntegrationTest(t, testData, true)
99
100         performPullWorkerIntegrationTest(testData, pullRequest, t)
101 }
102
103 // Perform the test.
104 // The test directly invokes the "PullItemAndProcess" rather than
105 // putting an item on the pullq so that the errors can be verified.
106 func performPullWorkerIntegrationTest(testData PullWorkIntegrationTestData, pullRequest PullRequest, t *testing.T) {
107
108         // Override PutContent to mock PutBlock functionality
109         PutContent = func(content []byte, locator string) (err error) {
110                 if string(content) != testData.Content {
111                         t.Errorf("PutContent invoked with unexpected data. Expected: %s; Found: %s", testData.Content, content)
112                 }
113                 return
114         }
115
116         keepClient.Arvados.ApiToken = GenerateRandomApiToken()
117         err := PullItemAndProcess(pullRequest, keepClient.Arvados.ApiToken, keepClient)
118
119         if len(testData.GetError) > 0 {
120                 if (err == nil) || (!strings.Contains(err.Error(), testData.GetError)) {
121                         t.Errorf("Got error %v", err)
122                 }
123         } else {
124                 if err != nil {
125                         t.Errorf("Got error %v", err)
126                 }
127         }
128 }