mirror of https://github.com/status-im/consul.git
Implementing the health methods with tests
This commit is contained in:
parent
c6c0f34fe8
commit
2b79c125f2
|
@ -388,7 +388,6 @@ func parseServiceNodes(tx *MDBTxn, table *MDBTable, res []interface{}, err error
|
|||
if err != nil {
|
||||
panic(fmt.Errorf("Failed to get node services: %v", err))
|
||||
}
|
||||
println(fmt.Sprintf("res: %#v", res))
|
||||
|
||||
nodes := make(structs.ServiceNodes, len(res))
|
||||
for i, r := range res {
|
||||
|
@ -408,8 +407,47 @@ func parseServiceNodes(tx *MDBTxn, table *MDBTable, res []interface{}, err error
|
|||
}
|
||||
|
||||
// EnsureCheck is used to create a check or updates it's state
|
||||
func (s *StateStore) EnsureCheck() error {
|
||||
return nil
|
||||
func (s *StateStore) EnsureCheck(check *structs.HealthCheck) error {
|
||||
// Ensure we have a status
|
||||
if check.Status == "" {
|
||||
check.Status = structs.HealthUnknown
|
||||
}
|
||||
|
||||
// Start the txn
|
||||
tx, err := s.tables.StartTxn(false)
|
||||
if err != nil {
|
||||
panic(fmt.Errorf("Failed to start txn: %v", err))
|
||||
}
|
||||
defer tx.Abort()
|
||||
|
||||
// Ensure the node exists
|
||||
res, err := s.nodeTable.GetTxn(tx, "id", check.Node)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
if len(res) == 0 {
|
||||
return fmt.Errorf("Missing node registration")
|
||||
}
|
||||
|
||||
// Ensure the service exists if specified
|
||||
if check.ServiceID != "" {
|
||||
res, err = s.serviceTable.GetTxn(tx, "id", check.Node, check.ServiceID)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
if len(res) == 0 {
|
||||
return fmt.Errorf("Missing service registration")
|
||||
}
|
||||
// Ensure we set the correct service
|
||||
srv := res[0].(*structs.ServiceNode)
|
||||
check.ServiceName = srv.ServiceName
|
||||
}
|
||||
|
||||
// Ensure the check is set
|
||||
if err := s.checkTable.InsertTxn(tx, check); err != nil {
|
||||
return err
|
||||
}
|
||||
return tx.Commit()
|
||||
}
|
||||
|
||||
// DeleteNodeCheck is used to delete a node health check
|
||||
|
@ -419,18 +457,31 @@ func (s *StateStore) DeleteNodeCheck(node, id string) error {
|
|||
}
|
||||
|
||||
// NodeChecks is used to get all the checks for a node
|
||||
func (s *StateStore) NodeChecks(name string) structs.HealthChecks {
|
||||
return nil
|
||||
func (s *StateStore) NodeChecks(node string) structs.HealthChecks {
|
||||
return parseHealthChecks(s.checkTable.Get("id", node))
|
||||
}
|
||||
|
||||
// ServiceChecks is used to get all the checks for a service
|
||||
func (s *StateStore) ServiceChecks(name string) structs.HealthChecks {
|
||||
return nil
|
||||
func (s *StateStore) ServiceChecks(service string) structs.HealthChecks {
|
||||
return parseHealthChecks(s.checkTable.Get("service", service))
|
||||
}
|
||||
|
||||
// CheckInState is used to get all the checks for a service in a given state
|
||||
func (s *StateStore) ChecksInState(name string) structs.HealthChecks {
|
||||
return nil
|
||||
func (s *StateStore) ChecksInState(state string) structs.HealthChecks {
|
||||
return parseHealthChecks(s.checkTable.Get("status", state))
|
||||
}
|
||||
|
||||
// parseHealthChecks is used to handle the resutls of a Get against
|
||||
// the checkTable
|
||||
func parseHealthChecks(res []interface{}, err error) structs.HealthChecks {
|
||||
if err != nil {
|
||||
panic(fmt.Errorf("Failed to get checks: %v", err))
|
||||
}
|
||||
results := make([]*structs.HealthCheck, len(res))
|
||||
for i, r := range res {
|
||||
results[i] = r.(*structs.HealthCheck)
|
||||
}
|
||||
return results
|
||||
}
|
||||
|
||||
// Snapshot is used to create a point in time snapshot
|
||||
|
|
|
@ -2,6 +2,7 @@ package consul
|
|||
|
||||
import (
|
||||
"github.com/hashicorp/consul/consul/structs"
|
||||
"reflect"
|
||||
"sort"
|
||||
"testing"
|
||||
)
|
||||
|
@ -163,6 +164,17 @@ func TestDeleteNodeService(t *testing.T) {
|
|||
t.Fatalf("err: %v", err)
|
||||
}
|
||||
|
||||
check := &structs.HealthCheck{
|
||||
Node: "foo",
|
||||
CheckID: "api",
|
||||
Name: "Can connect",
|
||||
Status: structs.HealthPassing,
|
||||
ServiceID: "api",
|
||||
}
|
||||
if err := store.EnsureCheck(check); err != nil {
|
||||
t.Fatalf("err: %v")
|
||||
}
|
||||
|
||||
if err := store.DeleteNodeService("foo", "api"); err != nil {
|
||||
t.Fatalf("err: %v", err)
|
||||
}
|
||||
|
@ -172,6 +184,11 @@ func TestDeleteNodeService(t *testing.T) {
|
|||
if ok {
|
||||
t.Fatalf("has api: %#v", services)
|
||||
}
|
||||
|
||||
checks := store.NodeChecks("foo")
|
||||
if len(checks) != 0 {
|
||||
t.Fatalf("has check: %#v", checks)
|
||||
}
|
||||
}
|
||||
|
||||
func TestDeleteNodeService_One(t *testing.T) {
|
||||
|
@ -223,8 +240,19 @@ func TestDeleteNode(t *testing.T) {
|
|||
t.Fatalf("err: %v")
|
||||
}
|
||||
|
||||
check := &structs.HealthCheck{
|
||||
Node: "foo",
|
||||
CheckID: "db",
|
||||
Name: "Can connect",
|
||||
Status: structs.HealthPassing,
|
||||
ServiceID: "api",
|
||||
}
|
||||
if err := store.EnsureCheck(check); err != nil {
|
||||
t.Fatalf("err: %v", err)
|
||||
}
|
||||
|
||||
if err := store.DeleteNode("foo"); err != nil {
|
||||
t.Fatalf("err: %v")
|
||||
t.Fatalf("err: %v", err)
|
||||
}
|
||||
|
||||
services := store.NodeServices("foo")
|
||||
|
@ -233,6 +261,11 @@ func TestDeleteNode(t *testing.T) {
|
|||
t.Fatalf("has api: %#v", services)
|
||||
}
|
||||
|
||||
checks := store.NodeChecks("foo")
|
||||
if len(checks) > 0 {
|
||||
t.Fatalf("has checks: %v", checks)
|
||||
}
|
||||
|
||||
found, _ := store.GetNode("foo")
|
||||
if found {
|
||||
t.Fatalf("found node")
|
||||
|
@ -504,3 +537,120 @@ func TestStoreSnapshot(t *testing.T) {
|
|||
t.Fatalf("bad: %v", services)
|
||||
}
|
||||
}
|
||||
|
||||
func TestEnsureCheck(t *testing.T) {
|
||||
store, err := NewStateStore()
|
||||
if err != nil {
|
||||
t.Fatalf("err: %v", err)
|
||||
}
|
||||
defer store.Close()
|
||||
|
||||
if err := store.EnsureNode(structs.Node{"foo", "127.0.0.1"}); err != nil {
|
||||
t.Fatalf("err: %v", err)
|
||||
}
|
||||
if err := store.EnsureService("foo", "db1", "db", "master", 8000); err != nil {
|
||||
t.Fatalf("err: %v")
|
||||
}
|
||||
check := &structs.HealthCheck{
|
||||
Node: "foo",
|
||||
CheckID: "db",
|
||||
Name: "Can connect",
|
||||
Status: structs.HealthPassing,
|
||||
ServiceID: "db1",
|
||||
}
|
||||
if err := store.EnsureCheck(check); err != nil {
|
||||
t.Fatalf("err: %v")
|
||||
}
|
||||
|
||||
check2 := &structs.HealthCheck{
|
||||
Node: "foo",
|
||||
CheckID: "memory",
|
||||
Name: "memory utilization",
|
||||
Status: structs.HealthWarning,
|
||||
}
|
||||
if err := store.EnsureCheck(check2); err != nil {
|
||||
t.Fatalf("err: %v")
|
||||
}
|
||||
|
||||
checks := store.NodeChecks("foo")
|
||||
if len(checks) != 2 {
|
||||
t.Fatalf("bad: %v", checks)
|
||||
}
|
||||
if !reflect.DeepEqual(checks[0], check) {
|
||||
t.Fatalf("bad: %v", checks[0])
|
||||
}
|
||||
if !reflect.DeepEqual(checks[1], check2) {
|
||||
t.Fatalf("bad: %v", checks[1])
|
||||
}
|
||||
|
||||
checks = store.ServiceChecks("db")
|
||||
if len(checks) != 1 {
|
||||
t.Fatalf("bad: %v", checks)
|
||||
}
|
||||
if !reflect.DeepEqual(checks[0], check) {
|
||||
t.Fatalf("bad: %v", checks[0])
|
||||
}
|
||||
|
||||
checks = store.ChecksInState(structs.HealthPassing)
|
||||
if len(checks) != 1 {
|
||||
t.Fatalf("bad: %v", checks)
|
||||
}
|
||||
if !reflect.DeepEqual(checks[0], check) {
|
||||
t.Fatalf("bad: %v", checks[0])
|
||||
}
|
||||
|
||||
checks = store.ChecksInState(structs.HealthWarning)
|
||||
if len(checks) != 1 {
|
||||
t.Fatalf("bad: %v", checks)
|
||||
}
|
||||
if !reflect.DeepEqual(checks[0], check2) {
|
||||
t.Fatalf("bad: %v", checks[0])
|
||||
}
|
||||
}
|
||||
|
||||
func TestDeleteNodeCheck(t *testing.T) {
|
||||
store, err := NewStateStore()
|
||||
if err != nil {
|
||||
t.Fatalf("err: %v", err)
|
||||
}
|
||||
defer store.Close()
|
||||
|
||||
if err := store.EnsureNode(structs.Node{"foo", "127.0.0.1"}); err != nil {
|
||||
t.Fatalf("err: %v", err)
|
||||
}
|
||||
if err := store.EnsureService("foo", "db1", "db", "master", 8000); err != nil {
|
||||
t.Fatalf("err: %v")
|
||||
}
|
||||
check := &structs.HealthCheck{
|
||||
Node: "foo",
|
||||
CheckID: "db",
|
||||
Name: "Can connect",
|
||||
Status: structs.HealthPassing,
|
||||
ServiceID: "db1",
|
||||
}
|
||||
if err := store.EnsureCheck(check); err != nil {
|
||||
t.Fatalf("err: %v")
|
||||
}
|
||||
|
||||
check2 := &structs.HealthCheck{
|
||||
Node: "foo",
|
||||
CheckID: "memory",
|
||||
Name: "memory utilization",
|
||||
Status: structs.HealthWarning,
|
||||
}
|
||||
if err := store.EnsureCheck(check2); err != nil {
|
||||
t.Fatalf("err: %v")
|
||||
}
|
||||
|
||||
if err := store.DeleteNodeCheck("foo", "db"); err != nil {
|
||||
t.Fatalf("err: %v", err)
|
||||
}
|
||||
|
||||
checks := store.NodeChecks("foo")
|
||||
if len(checks) != 1 {
|
||||
t.Fatalf("bad: %v", checks)
|
||||
}
|
||||
if !reflect.DeepEqual(checks[0], check2) {
|
||||
t.Fatalf("bad: %v", checks[0])
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue