Beispiel #1
0
func TestEncrypt(t *testing.T) {
	shutdownCh := make(chan struct{})
	defer close(shutdownCh)

	ui := new(cli.MockUi)
	a := &AgentCommand{
		Ui:         ui,
		ShutdownCh: shutdownCh,
	}

	args := []string{
		"-bind", testutil.GetBindAddr().String(),
		"-node", "test1",
		"-server",
		"-tag", "role=test",
		"-encrypt", "kPpdjphiipNSsjd4QHWbkA==",
		"-log-level", logLevel,
	}

	go a.Run(args)
	time.Sleep(2 * time.Second)

	assert.True(t, a.serf.EncryptionEnabled())
	shutdownCh <- struct{}{}
}
Beispiel #2
0
func testConfig() *Config {
	config := DefaultConfig()
	config.Init()
	config.MemberlistConfig.BindAddr = testutil.GetBindAddr().String()

	// Set probe intervals that are aggressive for finding bad nodes
	config.MemberlistConfig.GossipInterval = 5 * time.Millisecond
	config.MemberlistConfig.ProbeInterval = 50 * time.Millisecond
	config.MemberlistConfig.ProbeTimeout = 25 * time.Millisecond
	config.MemberlistConfig.SuspicionMult = 1

	config.NodeName = fmt.Sprintf("Node %s", config.MemberlistConfig.BindAddr)

	// Set a short reap interval so that it can run during the test
	config.ReapInterval = 1 * time.Second

	// Set a short reconnect interval so that it can run a lot during tests
	config.ReconnectInterval = 100 * time.Millisecond

	// Set basically zero on the reconnect/tombstone timeouts so that
	// they're removed on the first ReapInterval.
	config.ReconnectTimeout = 1 * time.Microsecond
	config.TombstoneTimeout = 1 * time.Microsecond

	return config
}
Beispiel #3
0
func setupAPITest(t *testing.T) (chan<- struct{}, <-chan int) {
	log.Level = logrus.FatalLevel

	shutdownCh := make(chan struct{})
	// defer close(shutdownCh)

	ui := new(cli.MockUi)
	a := &AgentCommand{
		Ui:         ui,
		ShutdownCh: shutdownCh,
	}

	args := []string{
		"-bind", testutil.GetBindAddr().String(),
		"-http-addr", "127.0.0.1:8090",
		"-node", "test",
		"-server",
	}

	resultCh := make(chan int)
	go func() {
		resultCh <- a.Run(args)
	}()

	time.Sleep(10 * time.Millisecond)

	return shutdownCh, resultCh
}
Beispiel #4
0
func TestEncrypt(t *testing.T) {
	log.Level = logrus.ErrorLevel

	shutdownCh := make(chan struct{})
	defer close(shutdownCh)

	ui := new(cli.MockUi)
	a := &AgentCommand{
		Ui:         ui,
		ShutdownCh: shutdownCh,
	}

	args := []string{
		"-bind", testutil.GetBindAddr().String(),
		"-node", "test1",
		"-server",
		"-tag", "role=test",
		"-encrypt", "kPpdjphiipNSsjd4QHWbkA==",
	}

	go func() {
		a.Run(args)
	}()
	time.Sleep(2 * time.Second)

	if !a.serf.EncryptionEnabled() {
		t.Fatal("Encryption not enabled for serf")
	}
	shutdownCh <- struct{}{}
}
Beispiel #5
0
func Test_getRPCAddr(t *testing.T) {
	shutdownCh := make(chan struct{})
	defer close(shutdownCh)

	ui := new(cli.MockUi)
	a := &AgentCommand{
		Ui:         ui,
		ShutdownCh: shutdownCh,
	}

	a1Addr := testutil.GetBindAddr()

	args := []string{
		"-bind", a1Addr.String() + ":5000",
		"-node", "test1",
		"-server",
		"-tag", "role=test",
	}

	go a.Run(args)
	time.Sleep(2 * time.Second)

	getRPCAddr := a.getRPCAddr()
	exRPCAddr := a1Addr.String() + ":6868"

	if exRPCAddr != getRPCAddr {
		t.Fatalf("Expected address was: %s got %s", exRPCAddr, getRPCAddr)
	}

	shutdownCh <- struct{}{}
}
Beispiel #6
0
func Test_getRPCAddr(t *testing.T) {
	shutdownCh := make(chan struct{})
	defer close(shutdownCh)

	ui := new(cli.MockUi)
	a := &AgentCommand{
		Ui:         ui,
		ShutdownCh: shutdownCh,
	}

	a1Addr := testutil.GetBindAddr()

	args := []string{
		"-bind", a1Addr.String() + ":5000",
		"-node", "test1",
		"-server",
		"-tag", "role=test",
		"-log-level", logLevel,
	}

	go a.Run(args)
	time.Sleep(2 * time.Second)

	getRPCAddr := a.getRPCAddr()
	exRPCAddr := a1Addr.String() + ":6868"

	assert.Equal(t, exRPCAddr, getRPCAddr)

	shutdownCh <- struct{}{}
}
Beispiel #7
0
func TestCommandRun_joinFail(t *testing.T) {
	shutdownCh := make(chan struct{})
	defer close(shutdownCh)

	c := &Command{
		ShutdownCh: shutdownCh,
		Ui:         new(cli.MockUi),
	}

	args := []string{
		"-bind", testutil.GetBindAddr().String(),
		"-join", testutil.GetBindAddr().String(),
	}

	code := c.Run(args)
	if code == 0 {
		t.Fatal("should fail")
	}
}
Beispiel #8
0
func TestCommandRun_advertiseAddr(t *testing.T) {
	doneCh := make(chan struct{})
	shutdownCh := make(chan struct{})
	defer func() {
		close(shutdownCh)
		<-doneCh
	}()

	c := &Command{
		ShutdownCh: shutdownCh,
		Ui:         new(cli.MockUi),
	}

	rpcAddr := getRPCAddr()
	args := []string{
		"-bind", testutil.GetBindAddr().String(),
		"-rpc-addr", rpcAddr,
		"-advertise", "127.0.0.10:12345",
	}

	go func() {
		code := c.Run(args)
		if code != 0 {
			log.Printf("bad: %d", code)
		}

		close(doneCh)
	}()

	testutil.Yield()

	client, err := rpc.NewClient(rpcAddr)
	if err != nil {
		t.Fatalf("err: %s", err)
	}
	defer client.Close()

	members, err := client.Members()
	if err != nil {
		t.Fatalf("err: %s", err)
	}

	if len(members) != 1 {
		t.Fatalf("bad: %#v", members)
	}

	// Check the addr and port is as advertised!
	m := members[0]
	if bytes.Compare(m.Addr, []byte{127, 0, 0, 10}) != 0 {
		t.Fatalf("bad: %#v", m)
	}
	if m.Port != 12345 {
		t.Fatalf("bad: %#v", m)
	}
}
Beispiel #9
0
func testAgent() *Agent {
	config := serf.DefaultConfig()
	config.MemberlistConfig.BindAddr = testutil.GetBindAddr().String()
	config.NodeName = config.MemberlistConfig.BindAddr

	agent := &Agent{
		RPCAddr:    getRPCAddr(),
		SerfConfig: config,
	}

	return agent
}
Beispiel #10
0
func TestAgentConfig(t *testing.T) {
	shutdownCh := make(chan struct{})
	defer close(shutdownCh)

	ui := new(cli.MockUi)
	a := &AgentCommand{
		Ui:         ui,
		ShutdownCh: shutdownCh,
	}

	advAddr := testutil.GetBindAddr().String()
	args := []string{
		"-bind", testutil.GetBindAddr().String(),
		"-advertise", advAddr,
		"-log-level", logLevel,
	}

	resultCh := make(chan int)
	go func() {
		resultCh <- a.Run(args)
	}()

	time.Sleep(2 * time.Second)

	assert.NotEqual(t, a.config.AdvertiseAddr, a.config.BindAddr)
	assert.NotEmpty(t, a.config.AdvertiseAddr)
	assert.Equal(t, advAddr, a.config.AdvertiseAddr)

	// Send a shutdown request
	shutdownCh <- struct{}{}

	select {
	case code := <-resultCh:
		if code != 0 {
			t.Fatalf("bad code: %d", code)
		}
	case <-time.After(100 * time.Millisecond):
		t.Fatalf("timeout")
	}
}
Beispiel #11
0
func testAgent(logOutput io.Writer) *Agent {
	if logOutput == nil {
		logOutput = os.Stderr
	}
	config := serf.DefaultConfig()
	config.MemberlistConfig.ProbeInterval = 100 * time.Millisecond
	config.MemberlistConfig.BindAddr = testutil.GetBindAddr().String()
	config.NodeName = config.MemberlistConfig.BindAddr

	agent, err := Create(config, logOutput)
	if err != nil {
		panic(err)
	}
	return agent
}
func testAgentWithConfig(agentConfig *Config, serfConfig *serf.Config,
	logOutput io.Writer) *Agent {

	if logOutput == nil {
		logOutput = os.Stderr
	}
	serfConfig.MemberlistConfig.ProbeInterval = 100 * time.Millisecond
	serfConfig.MemberlistConfig.BindAddr = testutil.GetBindAddr().String()
	serfConfig.NodeName = serfConfig.MemberlistConfig.BindAddr

	agent, err := Create(agentConfig, serfConfig, logOutput)
	if err != nil {
		panic(err)
	}
	return agent
}
Beispiel #13
0
func testAgent(t *testing.T) *agent.Agent {
	config := serf.DefaultConfig()
	config.MemberlistConfig.BindAddr = testutil.GetBindAddr().String()
	config.NodeName = config.MemberlistConfig.BindAddr

	agent := &agent.Agent{
		RPCAddr:    getRPCAddr(),
		SerfConfig: config,
	}

	if err := agent.Start(); err != nil {
		t.Fatalf("err: %s", err)
	}

	return agent
}
Beispiel #14
0
func TestCommandRun_rpc(t *testing.T) {
	doneCh := make(chan struct{})
	shutdownCh := make(chan struct{})
	defer func() {
		close(shutdownCh)
		<-doneCh
	}()

	c := &Command{
		ShutdownCh: shutdownCh,
		Ui:         new(cli.MockUi),
	}

	rpcAddr := getRPCAddr()
	args := []string{
		"-bind", testutil.GetBindAddr().String(),
		"-rpc-addr", rpcAddr,
	}

	go func() {
		code := c.Run(args)
		if code != 0 {
			log.Printf("bad: %d", code)
		}

		close(doneCh)
	}()

	testutil.Yield()

	client, err := rpc.NewClient(rpcAddr)
	if err != nil {
		t.Fatalf("err: %s", err)
	}
	defer client.Close()

	members, err := client.Members()
	if err != nil {
		t.Fatalf("err: %s", err)
	}

	if len(members) != 1 {
		t.Fatalf("bad: %#v", members)
	}
}
Beispiel #15
0
func testAgent(t *testing.T) *agent.Agent {
	config := serf.DefaultConfig()
	config.MemberlistConfig.BindAddr = testutil.GetBindAddr().String()
	config.MemberlistConfig.ProbeInterval = 50 * time.Millisecond
	config.MemberlistConfig.ProbeTimeout = 25 * time.Millisecond
	config.MemberlistConfig.SuspicionMult = 1
	config.NodeName = config.MemberlistConfig.BindAddr

	agent := &agent.Agent{
		RPCAddr:    getRPCAddr(),
		SerfConfig: config,
	}

	if err := agent.Start(); err != nil {
		t.Fatalf("err: %s", err)
	}

	return agent
}
Beispiel #16
0
func TestAgentCommandRun(t *testing.T) {
	log.Level = logrus.FatalLevel

	shutdownCh := make(chan struct{})
	defer close(shutdownCh)

	ui := new(cli.MockUi)
	a := &AgentCommand{
		Ui:         ui,
		ShutdownCh: shutdownCh,
	}

	args := []string{
		"-bind", testutil.GetBindAddr().String(),
	}

	resultCh := make(chan int)
	go func() {
		resultCh <- a.Run(args)
	}()

	time.Sleep(2 * time.Second)

	// Verify it runs "forever"
	select {
	case <-resultCh:
		t.Fatalf("ended too soon, err: %s", ui.ErrorWriter.String())
	case <-time.After(50 * time.Millisecond):
	}

	// Send a shutdown request
	shutdownCh <- struct{}{}

	select {
	case code := <-resultCh:
		if code != 0 {
			t.Fatalf("bad code: %d", code)
		}
	case <-time.After(50 * time.Millisecond):
		t.Fatalf("timeout")
	}
}
func testAgent(t *testing.T) *agent.Agent {
	config := serf.DefaultConfig()
	config.MemberlistConfig.BindAddr = testutil.GetBindAddr().String()
	config.MemberlistConfig.ProbeInterval = 50 * time.Millisecond
	config.MemberlistConfig.ProbeTimeout = 25 * time.Millisecond
	config.MemberlistConfig.SuspicionMult = 1
	config.NodeName = config.MemberlistConfig.BindAddr
	config.Tags = map[string]string{"role": "test", "tag1": "foo", "tag2": "bar"}

	agent, err := agent.Create(config, nil)
	if err != nil {
		t.Fatalf("err: %s", err)
	}

	if err := agent.Start(); err != nil {
		t.Fatalf("err: %s", err)
	}

	return agent
}
Beispiel #18
0
func TestCommandRun(t *testing.T) {
	shutdownCh := make(chan struct{})
	defer close(shutdownCh)

	ui := new(cli.MockUi)
	c := &Command{
		ShutdownCh: shutdownCh,
		Ui:         ui,
	}

	args := []string{
		"-bind", testutil.GetBindAddr().String(),
		"-rpc-addr", getRPCAddr(),
	}

	resultCh := make(chan int)
	go func() {
		resultCh <- c.Run(args)
	}()

	testutil.Yield()

	// Verify it runs "forever"
	select {
	case <-resultCh:
		t.Fatalf("ended too soon, err: %s", ui.ErrorWriter.String())
	case <-time.After(50 * time.Millisecond):
	}

	// Send a shutdown request
	shutdownCh <- struct{}{}

	select {
	case code := <-resultCh:
		if code != 0 {
			t.Fatalf("bad code: %d", code)
		}
	case <-time.After(50 * time.Millisecond):
		t.Fatalf("timeout")
	}
}
Beispiel #19
0
func TestCommandRun_join(t *testing.T) {
	a1 := testAgent(nil)
	if err := a1.Start(); err != nil {
		t.Fatalf("err: %s", err)
	}
	defer a1.Shutdown()

	doneCh := make(chan struct{})
	shutdownCh := make(chan struct{})
	defer func() {
		close(shutdownCh)
		<-doneCh
	}()

	c := &Command{
		ShutdownCh: shutdownCh,
		Ui:         new(cli.MockUi),
	}

	args := []string{
		"-bind", testutil.GetBindAddr().String(),
		"-join", a1.conf.MemberlistConfig.BindAddr,
		"-replay",
	}

	go func() {
		code := c.Run(args)
		if code != 0 {
			log.Printf("bad: %d", code)
		}

		close(doneCh)
	}()

	testutil.Yield()

	if len(a1.Serf().Members()) != 2 {
		t.Fatalf("bad: %#v", a1.Serf().Members())
	}
}
Beispiel #20
0
func Test_processFilteredNodes(t *testing.T) {
	log.Level = logrus.ErrorLevel

	shutdownCh := make(chan struct{})
	defer close(shutdownCh)

	ui := new(cli.MockUi)
	a := &AgentCommand{
		Ui:         ui,
		ShutdownCh: shutdownCh,
	}

	s := NewStore("etcd", []string{}, nil, "dkron")
	err := s.Client.DeleteTree("dkron")
	if err != nil {
		if err == store.ErrNotReachable {
			t.Fatal("etcd server needed to run tests")
		}
	}

	a1Addr := testutil.GetBindAddr().String()
	a2Addr := testutil.GetBindAddr().String()

	args := []string{
		"-bind", a1Addr,
		"-join", a2Addr,
		"-node", "test1",
		"-server",
		"-tag", "role=test",
	}

	resultCh := make(chan int)
	go func() {
		resultCh <- a.Run(args)
	}()

	time.Sleep(2 * time.Second)
	// Start another agent
	shutdownCh2 := make(chan struct{})
	defer close(shutdownCh2)

	ui2 := new(cli.MockUi)
	a2 := &AgentCommand{
		Ui:         ui2,
		ShutdownCh: shutdownCh2,
	}

	args2 := []string{
		"-bind", a2Addr,
		"-join", a1Addr,
		"-node", "test2",
		"-server",
		"-tag", "role=test",
	}

	resultCh2 := make(chan int)
	go func() {
		resultCh2 <- a2.Run(args2)
	}()

	job := &Job{
		Name: "test_job_1",
		Tags: map[string]string{
			"role": "test:2",
		},
	}

	time.Sleep(2 * time.Second)
	nodes, err := a.processFilteredNodes(job)

	if nodes[0] != "test1" || nodes[1] != "test2" {
		t.Fatal("Not expected returned nodes")
	}

	// Send a shutdown request
	shutdownCh <- struct{}{}
	shutdownCh2 <- struct{}{}
}
Beispiel #21
0
func TestAgentCommandElectLeader(t *testing.T) {
	log.Level = logrus.ErrorLevel

	shutdownCh := make(chan struct{})
	defer close(shutdownCh)

	ui := new(cli.MockUi)
	a1 := &AgentCommand{
		Ui:         ui,
		ShutdownCh: shutdownCh,
	}

	s := NewStore("etcd", []string{}, nil, "dkron")
	err := s.Client.DeleteTree("dkron")
	if err != nil {
		if err == store.ErrNotReachable {
			t.Fatal("etcd server needed to run tests")
		}
	}

	a1Addr := testutil.GetBindAddr().String()
	a2Addr := testutil.GetBindAddr().String()

	args := []string{
		"-bind", a1Addr,
		"-join", a2Addr,
		"-node", "test1",
		"-server",
	}

	resultCh := make(chan int)
	go func() {
		resultCh <- a1.Run(args)
	}()

	// Wait for the first agent to start and set itself as leader
	time.Sleep(2 * time.Second)
	test1Key := a1.config.Tags["key"]
	t.Logf("test1 key %s", test1Key)

	// Start another agent
	shutdownCh2 := make(chan struct{})
	defer close(shutdownCh2)

	ui2 := new(cli.MockUi)
	a2 := &AgentCommand{
		Ui:         ui2,
		ShutdownCh: shutdownCh2,
	}
	defer func() { shutdownCh2 <- struct{}{} }()

	args2 := []string{
		"-bind", a2Addr,
		"-join", a1Addr,
		"-node", "test2",
		"-server",
	}

	resultCh2 := make(chan int)
	go func() {
		resultCh2 <- a2.Run(args2)
	}()

	time.Sleep(2 * time.Second)
	test2Key := a2.config.Tags["key"]
	t.Logf("test2 key %s", test2Key)

	// Send a shutdown request
	shutdownCh <- struct{}{}

	time.Sleep(2 * time.Second)

	// Listen for leader key changes or timeout
	stopCh := make(chan struct{})
	receiver, err := s.Client.Watch("/dkron/leader", stopCh)
	if err != nil {
		t.Fatal(err)
	}

	// Wait for the new leader election
	for {
		select {
		case res := <-receiver:
			if res != nil {
				if bytes.Equal(res.Value, []byte(test2Key)) {
					t.Logf("Leader changed: %s", res.Value)
					stopCh <- struct{}{}
					return
				}
				if bytes.Equal(res.Value, []byte(test1Key)) {
					t.Logf("Leader set to agent1: %s", res.Value)
				}
			}
		case <-time.After(10 * time.Second):
			t.Fatal("No leader swap occurred")
			stopCh <- struct{}{}
			return
		}
	}
}
Beispiel #22
0
func TestRPCExecutionDone(t *testing.T) {
	store := NewStore("etcd", []string{"127.0.0.1:4001"}, nil, "dkron")

	// Cleanup everything
	err := store.Client.DeleteTree("dkron")
	if err != nil {
		t.Logf("error cleaning up: %s", err)
	}

	shutdownCh := make(chan struct{})
	defer close(shutdownCh)

	ui := new(cli.MockUi)
	a := &AgentCommand{
		Ui:         ui,
		ShutdownCh: shutdownCh,
	}

	aAddr := testutil.GetBindAddr().String()

	args := []string{
		"-bind", aAddr,
		"-node", "test1",
		"-server",
		"-keyspace", "dkron",
	}

	resultCh := make(chan int)
	go func() {
		resultCh <- a.Run(args)
	}()
	time.Sleep(2 * time.Second)

	testJob := &Job{
		Name:     "test",
		Schedule: "@every 2s",
		Disabled: true,
	}

	if err := store.SetJob(testJob); err != nil {
		t.Fatalf("error creating job: %s", err)
	}

	testExecution := &Execution{
		JobName:    "test",
		Group:      time.Now().UnixNano(),
		StartedAt:  time.Now(),
		NodeName:   "testNode",
		FinishedAt: time.Now(),
		Success:    true,
		Output:     []byte("type"),
	}

	rc := &RPCClient{
		ServerAddr: a.getRPCAddr(),
	}

	rc.callExecutionDone(testExecution)
	execs, _ := store.GetExecutions("test")

	if len(execs) == 0 {
		t.Fatal("executions result is empty")
	}

	if string(execs[0].Output) != string(testExecution.Output) {
		t.Fatalf("error on retrieved excution expected: %s got: %s", testExecution.Output, execs[0].Output)
	}

	// Test store execution on a deleted job
	store.DeleteJob(testJob.Name)

	testExecution.FinishedAt = time.Now()
	rc.callExecutionDone(testExecution)
}
Beispiel #23
0
func TestCommandRun_mDNS(t *testing.T) {
	// mDNS does not work in travis
	if os.Getenv("TRAVIS") != "" {
		t.SkipNow()
	}

	// Start an agent
	doneCh := make(chan struct{})
	shutdownCh := make(chan struct{})
	defer func() {
		close(shutdownCh)
		<-doneCh
	}()

	c := &Command{
		ShutdownCh: shutdownCh,
		Ui:         new(cli.MockUi),
	}

	args := []string{
		"-node", "foo",
		"-bind", testutil.GetBindAddr().String(),
		"-discover", "test",
		"-rpc-addr", getRPCAddr(),
	}

	go func() {
		code := c.Run(args)
		if code != 0 {
			log.Printf("bad: %d", code)
		}
		close(doneCh)
	}()

	// Start a second agent
	doneCh2 := make(chan struct{})
	shutdownCh2 := make(chan struct{})
	defer func() {
		close(shutdownCh2)
		<-doneCh2
	}()

	c2 := &Command{
		ShutdownCh: shutdownCh2,
		Ui:         new(cli.MockUi),
	}

	addr2 := getRPCAddr()
	args2 := []string{
		"-node", "bar",
		"-bind", testutil.GetBindAddr().String(),
		"-discover", "test",
		"-rpc-addr", addr2,
	}

	go func() {
		code := c2.Run(args2)
		if code != 0 {
			log.Printf("bad: %d", code)
		}
		close(doneCh2)
	}()

	time.Sleep(150 * time.Millisecond)

	client, err := client.NewRPCClient(addr2)
	if err != nil {
		t.Fatalf("err: %s", err)
	}
	defer client.Close()

	members, err := client.Members()
	if err != nil {
		t.Fatalf("err: %s", err)
	}

	if len(members) != 2 {
		t.Fatalf("bad: %#v", members)
	}
}
Beispiel #24
0
func TestAgentCommand_runForElection(t *testing.T) {
	a1Name := "test1"
	a2Name := "test2"
	a1Addr := testutil.GetBindAddr().String()
	a2Addr := testutil.GetBindAddr().String()
	shutdownCh := make(chan struct{})
	defer close(shutdownCh)

	ui := new(cli.MockUi)
	a1 := &AgentCommand{
		Ui:         ui,
		ShutdownCh: shutdownCh,
	}

	client, err := libkv.NewStore("etcd", []string{etcdAddr}, &store.Config{})
	if err != nil {
		panic(err)
	}
	err = client.DeleteTree("dkron")
	if err != nil {
		if err != store.ErrKeyNotFound {
			panic(err)
		}
	}

	args := []string{
		"-bind", a1Addr,
		"-join", a2Addr,
		"-node", a1Name,
		"-server",
		"-log-level", logLevel,
	}

	resultCh := make(chan int)
	go func() {
		resultCh <- a1.Run(args)
	}()

	// Wait for the first agent to start and set itself as leader
	time.Sleep(2 * time.Second)

	// Start another agent
	shutdownCh2 := make(chan struct{})
	defer close(shutdownCh2)

	ui2 := new(cli.MockUi)
	a2 := &AgentCommand{
		Ui:         ui2,
		ShutdownCh: shutdownCh2,
	}
	defer func() { shutdownCh2 <- struct{}{} }()

	args2 := []string{
		"-bind", a2Addr,
		"-join", a1Addr + ":8946",
		"-node", a2Name,
		"-server",
		"-log-level", logLevel,
	}

	resultCh2 := make(chan int)
	go func() {
		resultCh2 <- a2.Run(args2)
	}()

	kv, _ := client.Get("dkron/leader")
	leader := string(kv.Value)
	log.Printf("%s is the current leader", leader)
	if leader != a1Name {
		t.Errorf("Expected %s to be the leader, got %s", a1Name, leader)
	}

	// Send a shutdown request
	shutdownCh <- struct{}{}

	// Wait until test2 steps as leader
	time.Sleep(30 * time.Second)

	kv, _ = client.Get("dkron/leader")
	leader = string(kv.Value)
	log.Printf("%s is the current leader", leader)
	if leader != a2Name {
		t.Errorf("Expected %s to be the leader, got %s", a2Name, leader)
	}
}
Beispiel #25
0
func Test_processFilteredNodes(t *testing.T) {
	shutdownCh := make(chan struct{})
	defer close(shutdownCh)

	ui := new(cli.MockUi)
	a := &AgentCommand{
		Ui:         ui,
		ShutdownCh: shutdownCh,
	}

	client, err := libkv.NewStore("etcd", []string{etcdAddr}, &store.Config{})
	err = client.DeleteTree("dkron")
	if err != nil {
		if err == store.ErrNotReachable {
			t.Fatal("etcd server needed to run tests")
		}
	}

	a1Addr := testutil.GetBindAddr().String()
	a2Addr := testutil.GetBindAddr().String()

	args := []string{
		"-bind", a1Addr,
		"-join", a2Addr,
		"-node", "test1",
		"-server",
		"-tag", "role=test",
		"-log-level", logLevel,
	}

	resultCh := make(chan int)
	go func() {
		resultCh <- a.Run(args)
	}()

	time.Sleep(2 * time.Second)
	// Start another agent
	shutdownCh2 := make(chan struct{})
	defer close(shutdownCh2)

	ui2 := new(cli.MockUi)
	a2 := &AgentCommand{
		Ui:         ui2,
		ShutdownCh: shutdownCh2,
	}

	args2 := []string{
		"-bind", a2Addr,
		"-join", a1Addr,
		"-node", "test2",
		"-server",
		"-tag", "role=test",
		"-log-level", logLevel,
	}

	resultCh2 := make(chan int)
	go func() {
		resultCh2 <- a2.Run(args2)
	}()

	job := &Job{
		Name: "test_job_1",
		Tags: map[string]string{
			"foo":  "bar:1",
			"role": "test:2",
		},
	}

	time.Sleep(2 * time.Second)
	nodes, tags, err := a.processFilteredNodes(job)

	assert.Contains(t, nodes, "test1")
	assert.Contains(t, nodes, "test2")
	assert.Equal(t, tags["role"], "test")
	assert.Equal(t, job.Tags["role"], "test:2")
	assert.Equal(t, job.Tags["foo"], "bar:1")

	// Send a shutdown request
	shutdownCh <- struct{}{}
	shutdownCh2 <- struct{}{}
}