Browse Source

Merge pull request #10663 from brahmaroutu/events_filterbyname_10645

filter events by container name
moxiegirl 10 years ago
parent
commit
dd6f76a76c

+ 6 - 0
docs/sources/reference/commandline/cli.md

@@ -992,6 +992,12 @@ You'll need two shells for this example.
     $ sudo docker events --filter 'container=7805c1d35632' --filter 'event=stop'
     2014-09-03T15:49:29.999999999Z07:00 7805c1d35632: (from redis:2.8) stop
 
+    $ sudo docker events --filter 'container=container_1' --filter 'container=container_2'
+    2014-09-03T15:49:29.999999999Z07:00 4386fb97867d: (from ubuntu-1:14.04) die
+    2014-05-10T17:42:14.999999999Z07:00 4386fb97867d: (from ubuntu-1:14.04) stop
+    2014-05-10T17:42:14.999999999Z07:00 7805c1d35632: (from redis:2.8) die
+    2014-09-03T15:49:29.999999999Z07:00 7805c1d35632: (from redis:2.8) stop
+
 ## exec
 
     Usage: docker exec [OPTIONS] CONTAINER COMMAND [ARG...]

+ 26 - 1
events/events.go

@@ -1,7 +1,9 @@
 package events
 
 import (
+	"bytes"
 	"encoding/json"
+	"io"
 	"strings"
 	"sync"
 	"time"
@@ -123,7 +125,13 @@ func writeEvent(job *engine.Job, event *utils.JSONMessage, eventFilters filters.
 		return true
 	}
 
-	if isFiltered(event.Status, eventFilters["event"]) || isFiltered(event.From, eventFilters["image"]) || isFiltered(event.ID, eventFilters["container"]) {
+	//incoming container filter can be name,id or partial id, convert and replace as a full container id
+	for i, cn := range eventFilters["container"] {
+		eventFilters["container"][i] = GetContainerId(job.Eng, cn)
+	}
+
+	if isFiltered(event.Status, eventFilters["event"]) || isFiltered(event.From, eventFilters["image"]) ||
+		isFiltered(event.ID, eventFilters["container"]) {
 		return nil
 	}
 
@@ -203,3 +211,20 @@ func (e *Events) unsubscribe(l listener) bool {
 	e.mu.Unlock()
 	return false
 }
+
+func GetContainerId(eng *engine.Engine, name string) string {
+	var buf bytes.Buffer
+	job := eng.Job("container_inspect", name)
+
+	var outStream io.Writer
+
+	outStream = &buf
+	job.Stdout.Set(outStream)
+
+	if err := job.Run(); err != nil {
+		return ""
+	}
+	var out struct{ ID string }
+	json.NewDecoder(&buf).Decode(&out)
+	return out.ID
+}

+ 94 - 0
integration-cli/docker_cli_events_test.go

@@ -258,6 +258,7 @@ func TestEventsFilterImageName(t *testing.T) {
 		t.Fatal(out, err)
 	}
 	container1 := stripTrailingCharacters(out)
+
 	out, _, err = runCommandWithOutput(exec.Command(dockerBinary, "run", "--name", "container_2", "-d", "busybox", "true"))
 	if err != nil {
 		t.Fatal(out, err)
@@ -290,5 +291,98 @@ func TestEventsFilterImageName(t *testing.T) {
 	}
 
 	logDone("events - filters using image")
+}
+
+func TestEventsFilterContainerID(t *testing.T) {
+	since := time.Now().Unix()
+	defer deleteAllContainers()
+
+	out, _, err := runCommandWithOutput(exec.Command(dockerBinary, "run", "-d", "busybox", "true"))
+	if err != nil {
+		t.Fatal(out, err)
+	}
+	container1 := stripTrailingCharacters(out)
+
+	out, _, err = runCommandWithOutput(exec.Command(dockerBinary, "run", "-d", "busybox", "true"))
+	if err != nil {
+		t.Fatal(out, err)
+	}
+	container2 := stripTrailingCharacters(out)
+
+	for _, s := range []string{container1, container2, container1[:12], container2[:12]} {
+		eventsCmd := exec.Command(dockerBinary, "events", fmt.Sprintf("--since=%d", since), fmt.Sprintf("--until=%d", time.Now().Unix()), "--filter", fmt.Sprintf("container=%s", s))
+		out, _, err := runCommandWithOutput(eventsCmd)
+		if err != nil {
+			t.Fatalf("Failed to get events, error: %s(%s)", err, out)
+		}
+		events := strings.Split(out, "\n")
+		events = events[:len(events)-1]
+		if len(events) == 0 || len(events) > 3 {
+			t.Fatalf("Expected 3 events, got %d: %v", len(events), events)
+		}
+		createEvent := strings.Fields(events[0])
+		if createEvent[len(createEvent)-1] != "create" {
+			t.Fatalf("first event should be create, not %#v", createEvent)
+		}
+		if len(events) > 1 {
+			startEvent := strings.Fields(events[1])
+			if startEvent[len(startEvent)-1] != "start" {
+				t.Fatalf("second event should be start, not %#v", startEvent)
+			}
+		}
+		if len(events) == 3 {
+			dieEvent := strings.Fields(events[len(events)-1])
+			if dieEvent[len(dieEvent)-1] != "die" {
+				t.Fatalf("event should be die, not %#v", dieEvent)
+			}
+		}
+	}
+
+	logDone("events - filters using container id")
+}
+
+func TestEventsFilterContainerName(t *testing.T) {
+	since := time.Now().Unix()
+	defer deleteAllContainers()
+
+	_, _, err := runCommandWithOutput(exec.Command(dockerBinary, "run", "--name", "container_1", "busybox", "true"))
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	_, _, err = runCommandWithOutput(exec.Command(dockerBinary, "run", "--name", "container_2", "busybox", "true"))
+	if err != nil {
+		t.Fatal(err)
+	}
+
+	for _, s := range []string{"container_1", "container_2"} {
+		eventsCmd := exec.Command(dockerBinary, "events", fmt.Sprintf("--since=%d", since), fmt.Sprintf("--until=%d", time.Now().Unix()), "--filter", fmt.Sprintf("container=%s", s))
+		out, _, err := runCommandWithOutput(eventsCmd)
+		if err != nil {
+			t.Fatalf("Failed to get events, error : %s(%s)", err, out)
+		}
+		events := strings.Split(out, "\n")
+		events = events[:len(events)-1]
+		if len(events) == 0 || len(events) > 3 {
+			t.Fatalf("Expected 3 events, got %d: %v", len(events), events)
+		}
+		createEvent := strings.Fields(events[0])
+		if createEvent[len(createEvent)-1] != "create" {
+			t.Fatalf("first event should be create, not %#v", createEvent)
+		}
+		if len(events) > 1 {
+			startEvent := strings.Fields(events[1])
+			if startEvent[len(startEvent)-1] != "start" {
+				t.Fatalf("second event should be start, not %#v", startEvent)
+			}
+		}
+		if len(events) == 3 {
+			dieEvent := strings.Fields(events[len(events)-1])
+			if dieEvent[len(dieEvent)-1] != "die" {
+				t.Fatalf("event should be die, not %#v", dieEvent)
+			}
+		}
+	}
 
+	logDone("events - filters using container name")
 }