|
@@ -5,7 +5,7 @@ import (
|
|
|
"github.com/coreos/go-etcd/etcd"
|
|
"github.com/coreos/go-etcd/etcd"
|
|
|
"math/rand"
|
|
"math/rand"
|
|
|
"os"
|
|
"os"
|
|
|
- "strconv"
|
|
|
|
|
|
|
+ //"strconv"
|
|
|
"testing"
|
|
"testing"
|
|
|
"time"
|
|
"time"
|
|
|
)
|
|
)
|
|
@@ -14,7 +14,7 @@ import (
|
|
|
func TestSingleNode(t *testing.T) {
|
|
func TestSingleNode(t *testing.T) {
|
|
|
procAttr := new(os.ProcAttr)
|
|
procAttr := new(os.ProcAttr)
|
|
|
procAttr.Files = []*os.File{nil, os.Stdout, os.Stderr}
|
|
procAttr.Files = []*os.File{nil, os.Stdout, os.Stderr}
|
|
|
- args := []string{"etcd", "-i", "-v", "-d=/tmp/node1"}
|
|
|
|
|
|
|
+ args := []string{"etcd", "-i", "-d=/tmp/node1"}
|
|
|
|
|
|
|
|
process, err := os.StartProcess("etcd", args, procAttr)
|
|
process, err := os.StartProcess("etcd", args, procAttr)
|
|
|
if err != nil {
|
|
if err != nil {
|
|
@@ -49,6 +49,62 @@ func TestSingleNode(t *testing.T) {
|
|
|
}
|
|
}
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
+// This test creates a single node and then set a value to it.
|
|
|
|
|
+// Then this test kills the node and restart it and tries to get the value again.
|
|
|
|
|
+func TestSingleNodeRecovery(t *testing.T) {
|
|
|
|
|
+ procAttr := new(os.ProcAttr)
|
|
|
|
|
+ procAttr.Files = []*os.File{nil, os.Stdout, os.Stderr}
|
|
|
|
|
+ args := []string{"etcd", "-d=/tmp/node1"}
|
|
|
|
|
+
|
|
|
|
|
+ process, err := os.StartProcess("etcd", append(args, "-i"), procAttr)
|
|
|
|
|
+ if err != nil {
|
|
|
|
|
+ t.Fatal("start process failed:" + err.Error())
|
|
|
|
|
+ return
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ time.Sleep(time.Second)
|
|
|
|
|
+
|
|
|
|
|
+ etcd.SyncCluster()
|
|
|
|
|
+ // Test Set
|
|
|
|
|
+ result, err := etcd.Set("foo", "bar", 100)
|
|
|
|
|
+
|
|
|
|
|
+ if err != nil || result.Key != "/foo" || result.Value != "bar" || result.TTL != 99 {
|
|
|
|
|
+ if err != nil {
|
|
|
|
|
+ t.Fatal(err)
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ t.Fatalf("Set 1 failed with %s %s %v", result.Key, result.Value, result.TTL)
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ time.Sleep(time.Second)
|
|
|
|
|
+
|
|
|
|
|
+ process.Kill()
|
|
|
|
|
+
|
|
|
|
|
+ process, err = os.StartProcess("etcd", args, procAttr)
|
|
|
|
|
+ defer process.Kill()
|
|
|
|
|
+ if err != nil {
|
|
|
|
|
+ t.Fatal("start process failed:" + err.Error())
|
|
|
|
|
+ return
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ time.Sleep(time.Second)
|
|
|
|
|
+
|
|
|
|
|
+ results, err := etcd.Get("foo")
|
|
|
|
|
+ if err != nil {
|
|
|
|
|
+ t.Fatal("get fail: " + err.Error())
|
|
|
|
|
+ return
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ result = results[0]
|
|
|
|
|
+
|
|
|
|
|
+ if err != nil || result.Key != "/foo" || result.Value != "bar" || result.TTL > 99 {
|
|
|
|
|
+ if err != nil {
|
|
|
|
|
+ t.Fatal(err)
|
|
|
|
|
+ }
|
|
|
|
|
+ t.Fatalf("Recovery Get failed with %s %s %v", result.Key, result.Value, result.TTL)
|
|
|
|
|
+ }
|
|
|
|
|
+}
|
|
|
|
|
+
|
|
|
// Create a three nodes and try to set value
|
|
// Create a three nodes and try to set value
|
|
|
func TestSimpleMultiNode(t *testing.T) {
|
|
func TestSimpleMultiNode(t *testing.T) {
|
|
|
procAttr := new(os.ProcAttr)
|
|
procAttr := new(os.ProcAttr)
|
|
@@ -113,7 +169,7 @@ func TestMultiNodeRecovery(t *testing.T) {
|
|
|
|
|
|
|
|
stop := make(chan bool)
|
|
stop := make(chan bool)
|
|
|
// Test Set
|
|
// Test Set
|
|
|
- go set(t, stop)
|
|
|
|
|
|
|
+ go set(stop)
|
|
|
|
|
|
|
|
for i := 0; i < 10; i++ {
|
|
for i := 0; i < 10; i++ {
|
|
|
num := rand.Int() % clusterSize
|
|
num := rand.Int() % clusterSize
|
|
@@ -131,76 +187,7 @@ func TestMultiNodeRecovery(t *testing.T) {
|
|
|
}
|
|
}
|
|
|
time.Sleep(time.Second)
|
|
time.Sleep(time.Second)
|
|
|
}
|
|
}
|
|
|
-
|
|
|
|
|
|
|
+ fmt.Println("stop")
|
|
|
stop <- true
|
|
stop <- true
|
|
|
<-stop
|
|
<-stop
|
|
|
}
|
|
}
|
|
|
-
|
|
|
|
|
-// Sending set commands
|
|
|
|
|
-func set(t *testing.T, stop chan bool) {
|
|
|
|
|
-
|
|
|
|
|
- stopSet := false
|
|
|
|
|
- i := 0
|
|
|
|
|
-
|
|
|
|
|
- for {
|
|
|
|
|
- key := fmt.Sprintf("%s_%v", "foo", i)
|
|
|
|
|
-
|
|
|
|
|
- result, err := etcd.Set(key, "bar", 0)
|
|
|
|
|
-
|
|
|
|
|
- if err != nil || result.Key != "/"+key || result.Value != "bar" {
|
|
|
|
|
- if err != nil {
|
|
|
|
|
- t.Fatal(err)
|
|
|
|
|
- }
|
|
|
|
|
- t.Fatalf("Set failed with %s %s %v", result.Key, result.Value)
|
|
|
|
|
- }
|
|
|
|
|
-
|
|
|
|
|
- select {
|
|
|
|
|
- case <-stop:
|
|
|
|
|
- stopSet = true
|
|
|
|
|
-
|
|
|
|
|
- default:
|
|
|
|
|
- }
|
|
|
|
|
-
|
|
|
|
|
- if stopSet {
|
|
|
|
|
- break
|
|
|
|
|
- }
|
|
|
|
|
-
|
|
|
|
|
- i++
|
|
|
|
|
- }
|
|
|
|
|
-
|
|
|
|
|
- stop <- true
|
|
|
|
|
-}
|
|
|
|
|
-
|
|
|
|
|
-// Create a cluster of etcd nodes
|
|
|
|
|
-func createCluster(size int, procAttr *os.ProcAttr) ([][]string, []*os.Process, error) {
|
|
|
|
|
- argGroup := make([][]string, size)
|
|
|
|
|
- for i := 0; i < size; i++ {
|
|
|
|
|
- if i == 0 {
|
|
|
|
|
- argGroup[i] = []string{"etcd", "-d=/tmp/node1"}
|
|
|
|
|
- } else {
|
|
|
|
|
- strI := strconv.Itoa(i + 1)
|
|
|
|
|
- argGroup[i] = []string{"etcd", "-c=400" + strI, "-s=700" + strI, "-d=/tmp/node" + strI, "-C=127.0.0.1:7001"}
|
|
|
|
|
- }
|
|
|
|
|
- }
|
|
|
|
|
-
|
|
|
|
|
- etcds := make([]*os.Process, size)
|
|
|
|
|
-
|
|
|
|
|
- for i, _ := range etcds {
|
|
|
|
|
- var err error
|
|
|
|
|
- etcds[i], err = os.StartProcess("etcd", append(argGroup[i], "-i"), procAttr)
|
|
|
|
|
- if err != nil {
|
|
|
|
|
- return nil, nil, err
|
|
|
|
|
- }
|
|
|
|
|
- }
|
|
|
|
|
-
|
|
|
|
|
- return argGroup, etcds, nil
|
|
|
|
|
-}
|
|
|
|
|
-
|
|
|
|
|
-// Destroy all the nodes in the cluster
|
|
|
|
|
-func destroyCluster(etcds []*os.Process) error {
|
|
|
|
|
- for _, etcd := range etcds {
|
|
|
|
|
- etcd.Kill()
|
|
|
|
|
- etcd.Release()
|
|
|
|
|
- }
|
|
|
|
|
- return nil
|
|
|
|
|
-}
|
|
|