github.com/Iqoqo/consul@v1.4.5/agent/ui_endpoint_test.go (about) 1 package agent 2 3 import ( 4 "bytes" 5 "fmt" 6 "io" 7 "io/ioutil" 8 "net/http" 9 "net/http/httptest" 10 "os" 11 "path/filepath" 12 "reflect" 13 "testing" 14 15 "github.com/hashicorp/consul/testrpc" 16 17 "github.com/hashicorp/consul/agent/structs" 18 "github.com/hashicorp/consul/api" 19 "github.com/hashicorp/consul/testutil" 20 cleanhttp "github.com/hashicorp/go-cleanhttp" 21 ) 22 23 func TestUiIndex(t *testing.T) { 24 t.Parallel() 25 // Make a test dir to serve UI files 26 uiDir := testutil.TempDir(t, "consul") 27 defer os.RemoveAll(uiDir) 28 29 // Make the server 30 a := NewTestAgent(t, t.Name(), ` 31 ui_dir = "`+uiDir+`" 32 `) 33 defer a.Shutdown() 34 testrpc.WaitForLeader(t, a.RPC, "dc1") 35 36 // Create file 37 path := filepath.Join(a.Config.UIDir, "my-file") 38 if err := ioutil.WriteFile(path, []byte("test"), 777); err != nil { 39 t.Fatalf("err: %v", err) 40 } 41 42 // Register node 43 req, _ := http.NewRequest("GET", "/ui/my-file", nil) 44 req.URL.Scheme = "http" 45 req.URL.Host = a.srv.Addr 46 47 // Make the request 48 client := cleanhttp.DefaultClient() 49 resp, err := client.Do(req) 50 if err != nil { 51 t.Fatalf("err: %v", err) 52 } 53 54 // Verify the response 55 if resp.StatusCode != 200 { 56 t.Fatalf("bad: %v", resp) 57 } 58 59 // Verify the body 60 out := bytes.NewBuffer(nil) 61 io.Copy(out, resp.Body) 62 if string(out.Bytes()) != "test" { 63 t.Fatalf("bad: %s", out.Bytes()) 64 } 65 } 66 67 func TestUiNodes(t *testing.T) { 68 t.Parallel() 69 a := NewTestAgent(t, t.Name(), "") 70 defer a.Shutdown() 71 testrpc.WaitForTestAgent(t, a.RPC, "dc1") 72 73 args := &structs.RegisterRequest{ 74 Datacenter: "dc1", 75 Node: "test", 76 Address: "127.0.0.1", 77 } 78 79 var out struct{} 80 if err := a.RPC("Catalog.Register", args, &out); err != nil { 81 t.Fatalf("err: %v", err) 82 } 83 84 req, _ := http.NewRequest("GET", "/v1/internal/ui/nodes/dc1", nil) 85 resp := httptest.NewRecorder() 86 obj, err := a.srv.UINodes(resp, req) 87 if err != nil { 88 t.Fatalf("err: %v", err) 89 } 90 assertIndex(t, resp) 91 92 // Should be 2 nodes, and all the empty lists should be non-nil 93 nodes := obj.(structs.NodeDump) 94 if len(nodes) != 2 || 95 nodes[0].Node != a.Config.NodeName || 96 nodes[0].Services == nil || len(nodes[0].Services) != 1 || 97 nodes[0].Checks == nil || len(nodes[0].Checks) != 1 || 98 nodes[1].Node != "test" || 99 nodes[1].Services == nil || len(nodes[1].Services) != 0 || 100 nodes[1].Checks == nil || len(nodes[1].Checks) != 0 { 101 t.Fatalf("bad: %v", obj) 102 } 103 } 104 105 func TestUiNodeInfo(t *testing.T) { 106 t.Parallel() 107 a := NewTestAgent(t, t.Name(), "") 108 defer a.Shutdown() 109 testrpc.WaitForLeader(t, a.RPC, "dc1") 110 111 req, _ := http.NewRequest("GET", fmt.Sprintf("/v1/internal/ui/node/%s", a.Config.NodeName), nil) 112 resp := httptest.NewRecorder() 113 obj, err := a.srv.UINodeInfo(resp, req) 114 if err != nil { 115 t.Fatalf("err: %v", err) 116 } 117 118 assertIndex(t, resp) 119 120 // Should be 1 node for the server 121 node := obj.(*structs.NodeInfo) 122 if node.Node != a.Config.NodeName { 123 t.Fatalf("bad: %v", node) 124 } 125 126 args := &structs.RegisterRequest{ 127 Datacenter: "dc1", 128 Node: "test", 129 Address: "127.0.0.1", 130 } 131 132 var out struct{} 133 if err := a.RPC("Catalog.Register", args, &out); err != nil { 134 t.Fatalf("err: %v", err) 135 } 136 137 req, _ = http.NewRequest("GET", "/v1/internal/ui/node/test", nil) 138 resp = httptest.NewRecorder() 139 obj, err = a.srv.UINodeInfo(resp, req) 140 if err != nil { 141 t.Fatalf("err: %v", err) 142 } 143 144 assertIndex(t, resp) 145 146 // Should be non-nil empty lists for services and checks 147 node = obj.(*structs.NodeInfo) 148 if node.Node != "test" || 149 node.Services == nil || len(node.Services) != 0 || 150 node.Checks == nil || len(node.Checks) != 0 { 151 t.Fatalf("bad: %v", node) 152 } 153 } 154 155 func TestSummarizeServices(t *testing.T) { 156 t.Parallel() 157 dump := structs.NodeDump{ 158 &structs.NodeInfo{ 159 Node: "foo", 160 Address: "127.0.0.1", 161 Services: []*structs.NodeService{ 162 &structs.NodeService{ 163 Kind: structs.ServiceKindTypical, 164 Service: "api", 165 Tags: []string{"tag1", "tag2"}, 166 }, 167 &structs.NodeService{ 168 Kind: structs.ServiceKindConnectProxy, 169 Service: "web", 170 Tags: []string{}, 171 Meta: map[string]string{metaExternalSource: "k8s"}, 172 }, 173 }, 174 Checks: []*structs.HealthCheck{ 175 &structs.HealthCheck{ 176 Status: api.HealthPassing, 177 ServiceName: "", 178 }, 179 &structs.HealthCheck{ 180 Status: api.HealthPassing, 181 ServiceName: "web", 182 }, 183 &structs.HealthCheck{ 184 Status: api.HealthWarning, 185 ServiceName: "api", 186 }, 187 }, 188 }, 189 &structs.NodeInfo{ 190 Node: "bar", 191 Address: "127.0.0.2", 192 Services: []*structs.NodeService{ 193 &structs.NodeService{ 194 Kind: structs.ServiceKindConnectProxy, 195 Service: "web", 196 Tags: []string{}, 197 Meta: map[string]string{metaExternalSource: "k8s"}, 198 }, 199 }, 200 Checks: []*structs.HealthCheck{ 201 &structs.HealthCheck{ 202 Status: api.HealthCritical, 203 ServiceName: "web", 204 }, 205 }, 206 }, 207 &structs.NodeInfo{ 208 Node: "zip", 209 Address: "127.0.0.3", 210 Services: []*structs.NodeService{ 211 &structs.NodeService{ 212 Service: "cache", 213 Tags: []string{}, 214 }, 215 }, 216 }, 217 } 218 219 summary := summarizeServices(dump) 220 if len(summary) != 3 { 221 t.Fatalf("bad: %v", summary) 222 } 223 224 expectAPI := &ServiceSummary{ 225 Kind: structs.ServiceKindTypical, 226 Name: "api", 227 Tags: []string{"tag1", "tag2"}, 228 Nodes: []string{"foo"}, 229 ChecksPassing: 1, 230 ChecksWarning: 1, 231 ChecksCritical: 0, 232 } 233 if !reflect.DeepEqual(summary[0], expectAPI) { 234 t.Fatalf("bad: %v", summary[0]) 235 } 236 237 expectCache := &ServiceSummary{ 238 Kind: structs.ServiceKindTypical, 239 Name: "cache", 240 Tags: []string{}, 241 Nodes: []string{"zip"}, 242 ChecksPassing: 0, 243 ChecksWarning: 0, 244 ChecksCritical: 0, 245 } 246 if !reflect.DeepEqual(summary[1], expectCache) { 247 t.Fatalf("bad: %v", summary[1]) 248 } 249 250 expectWeb := &ServiceSummary{ 251 Kind: structs.ServiceKindConnectProxy, 252 Name: "web", 253 Tags: []string{}, 254 Nodes: []string{"bar", "foo"}, 255 ChecksPassing: 2, 256 ChecksWarning: 0, 257 ChecksCritical: 1, 258 ExternalSources: []string{"k8s"}, 259 } 260 summary[2].externalSourceSet = nil 261 if !reflect.DeepEqual(summary[2], expectWeb) { 262 t.Fatalf("bad: %v", summary[2]) 263 } 264 }