events: add protos
Signed-off-by: Evan Hazlett <ejhazlett@gmail.com> events: update events package to include emitter and use envelope proto Signed-off-by: Evan Hazlett <ejhazlett@gmail.com> events: add events service Signed-off-by: Evan Hazlett <ejhazlett@gmail.com> events: enable events service and update ctr events to use events service Signed-off-by: Evan Hazlett <ejhazlett@gmail.com> event listeners Signed-off-by: Evan Hazlett <ejhazlett@gmail.com> events: helper func for emitting in services Signed-off-by: Evan Hazlett <ejhazlett@gmail.com> events: improved cli for containers and tasks Signed-off-by: Evan Hazlett <ejhazlett@gmail.com> create event envelope with poster Signed-off-by: Evan Hazlett <ejhazlett@gmail.com> events: introspect event data to use for type url Signed-off-by: Evan Hazlett <ejhazlett@gmail.com> events: use pb encoding; add event types Signed-off-by: Evan Hazlett <ejhazlett@gmail.com> events: instrument content and snapshot services with events Signed-off-by: Evan Hazlett <ejhazlett@gmail.com> events: instrument image service with events Signed-off-by: Evan Hazlett <ejhazlett@gmail.com> events: instrument namespace service with events Signed-off-by: Evan Hazlett <ejhazlett@gmail.com> events: add namespace support Signed-off-by: Evan Hazlett <ejhazlett@gmail.com> events: only send events from namespace requested from client Signed-off-by: Evan Hazlett <ejhazlett@gmail.com> events: switch to go-events for broadcasting Signed-off-by: Evan Hazlett <ejhazlett@gmail.com>
This commit is contained in:
174
cmd/ctr/events.go
Normal file
174
cmd/ctr/events.go
Normal file
@@ -0,0 +1,174 @@
|
||||
package main
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"os"
|
||||
"strings"
|
||||
"text/tabwriter"
|
||||
|
||||
eventsapi "github.com/containerd/containerd/api/services/events"
|
||||
"github.com/containerd/containerd/api/types/event"
|
||||
"github.com/gogo/protobuf/proto"
|
||||
"github.com/urfave/cli"
|
||||
)
|
||||
|
||||
var eventsCommand = cli.Command{
|
||||
Name: "events",
|
||||
Usage: "display containerd events",
|
||||
Action: func(context *cli.Context) error {
|
||||
eventsClient, err := getEventsService(context)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
ctx, cancel := appContext(context)
|
||||
defer cancel()
|
||||
|
||||
events, err := eventsClient.EventStream(ctx, &eventsapi.EventStreamRequest{})
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
w := tabwriter.NewWriter(os.Stdout, 10, 1, 3, ' ', 0)
|
||||
for {
|
||||
e, err := events.Recv()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
out, err := getEventOutput(e)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
if _, err := fmt.Fprintf(w,
|
||||
"%s\t%s",
|
||||
e.Timestamp,
|
||||
e.Topic,
|
||||
); err != nil {
|
||||
return err
|
||||
}
|
||||
if _, err := fmt.Fprintf(w, "\t%s\n", out); err != nil {
|
||||
return err
|
||||
}
|
||||
if err := w.Flush(); err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
},
|
||||
}
|
||||
|
||||
func getEventOutput(evt *event.Envelope) (string, error) {
|
||||
|
||||
out := ""
|
||||
switch evt.Event.TypeUrl {
|
||||
case "types.containerd.io/containerd.v1.types.event.ContainerCreate":
|
||||
e := &event.ContainerCreate{}
|
||||
if err := proto.Unmarshal(evt.Event.Value, e); err != nil {
|
||||
return out, err
|
||||
}
|
||||
out = fmt.Sprintf("id=%s image=%s runtime=%s", e.ContainerID, e.Image, e.Runtime)
|
||||
case "types.containerd.io/containerd.v1.types.event.TaskCreate":
|
||||
e := &event.TaskCreate{}
|
||||
if err := proto.Unmarshal(evt.Event.Value, e); err != nil {
|
||||
return out, err
|
||||
}
|
||||
out = "id=" + e.ContainerID
|
||||
case "types.containerd.io/containerd.v1.types.event.TaskStart":
|
||||
e := &event.TaskStart{}
|
||||
if err := proto.Unmarshal(evt.Event.Value, e); err != nil {
|
||||
return out, err
|
||||
}
|
||||
out = fmt.Sprintf("id=%s", e.ContainerID)
|
||||
case "types.containerd.io/containerd.v1.types.event.TaskDelete":
|
||||
e := &event.TaskDelete{}
|
||||
if err := proto.Unmarshal(evt.Event.Value, e); err != nil {
|
||||
return out, err
|
||||
}
|
||||
out = fmt.Sprintf("id=%s", e.ContainerID)
|
||||
case "types.containerd.io/containerd.v1.types.event.ContainerUpdate":
|
||||
e := &event.ContainerUpdate{}
|
||||
if err := proto.Unmarshal(evt.Event.Value, e); err != nil {
|
||||
return out, err
|
||||
}
|
||||
out = fmt.Sprintf("id=%s", e.ContainerID)
|
||||
case "types.containerd.io/containerd.v1.types.event.ContainerDelete":
|
||||
e := &event.ContainerDelete{}
|
||||
if err := proto.Unmarshal(evt.Event.Value, e); err != nil {
|
||||
return out, err
|
||||
}
|
||||
out = fmt.Sprintf("id=%s", e.ContainerID)
|
||||
case "types.containerd.io/containerd.v1.types.event.SnapshotPrepare":
|
||||
e := &event.SnapshotPrepare{}
|
||||
if err := proto.Unmarshal(evt.Event.Value, e); err != nil {
|
||||
return out, err
|
||||
}
|
||||
out = fmt.Sprintf("key=%s parent=%s", e.Key, e.Parent)
|
||||
case "types.containerd.io/containerd.v1.types.event.SnapshotCommit":
|
||||
e := &event.SnapshotCommit{}
|
||||
if err := proto.Unmarshal(evt.Event.Value, e); err != nil {
|
||||
return out, err
|
||||
}
|
||||
out = fmt.Sprintf("key=%s name=%s", e.Key, e.Name)
|
||||
case "types.containerd.io/containerd.v1.types.event.SnapshotRemove":
|
||||
e := &event.SnapshotRemove{}
|
||||
if err := proto.Unmarshal(evt.Event.Value, e); err != nil {
|
||||
return out, err
|
||||
}
|
||||
out = fmt.Sprintf("key=%s", e.Key)
|
||||
case "types.containerd.io/containerd.v1.types.event.ImagePut":
|
||||
e := &event.ImagePut{}
|
||||
if err := proto.Unmarshal(evt.Event.Value, e); err != nil {
|
||||
return out, err
|
||||
}
|
||||
out = fmt.Sprintf("name=%s labels=%s", e.Name, e.Labels)
|
||||
case "types.containerd.io/containerd.v1.types.event.ImageDelete":
|
||||
e := &event.ImageDelete{}
|
||||
if err := proto.Unmarshal(evt.Event.Value, e); err != nil {
|
||||
return out, err
|
||||
}
|
||||
out = fmt.Sprintf("name=%s", e.Name)
|
||||
case "types.containerd.io/containerd.v1.types.event.NamespaceCreate":
|
||||
e := &event.NamespaceCreate{}
|
||||
if err := proto.Unmarshal(evt.Event.Value, e); err != nil {
|
||||
return out, err
|
||||
}
|
||||
out = fmt.Sprintf("name=%s labels=%s", e.Name, e.Labels)
|
||||
case "types.containerd.io/containerd.v1.types.event.NamespaceUpdate":
|
||||
e := &event.NamespaceUpdate{}
|
||||
if err := proto.Unmarshal(evt.Event.Value, e); err != nil {
|
||||
return out, err
|
||||
}
|
||||
out = fmt.Sprintf("name=%s labels=%s", e.Name, e.Labels)
|
||||
case "types.containerd.io/containerd.v1.types.event.NamespaceDelete":
|
||||
e := &event.NamespaceDelete{}
|
||||
if err := proto.Unmarshal(evt.Event.Value, e); err != nil {
|
||||
return out, err
|
||||
}
|
||||
out = fmt.Sprintf("name=%s", e.Name)
|
||||
case "types.containerd.io/containerd.v1.types.event.RuntimeCreate":
|
||||
e := &event.RuntimeCreate{}
|
||||
if err := proto.Unmarshal(evt.Event.Value, e); err != nil {
|
||||
return out, err
|
||||
}
|
||||
mounts := []string{}
|
||||
for _, m := range e.RootFS {
|
||||
mounts = append(mounts, fmt.Sprintf("type=%s:src=%s", m.Type, m.Source))
|
||||
}
|
||||
out = fmt.Sprintf("id=%s bundle=%s rootfs=%s checkpoint=%s", e.ID, e.Bundle, strings.Join(mounts, ","), e.Checkpoint)
|
||||
case "types.containerd.io/containerd.v1.types.event.RuntimeEvent":
|
||||
e := &event.RuntimeEvent{}
|
||||
if err := proto.Unmarshal(evt.Event.Value, e); err != nil {
|
||||
return out, err
|
||||
}
|
||||
out = fmt.Sprintf("id=%s type=%s pid=%d status=%d exited=%s", e.ID, e.Type, e.Pid, e.ExitStatus, e.ExitedAt)
|
||||
case "types.containerd.io/containerd.v1.types.event.RuntimeDelete":
|
||||
e := &event.RuntimeDelete{}
|
||||
if err := proto.Unmarshal(evt.Event.Value, e); err != nil {
|
||||
return out, err
|
||||
}
|
||||
out = fmt.Sprintf("id=%s runtime=%s status=%d exited=%s", e.ID, e.Runtime, e.ExitStatus, e.ExitedAt)
|
||||
default:
|
||||
out = evt.Event.TypeUrl
|
||||
}
|
||||
|
||||
return out, nil
|
||||
}
|
||||
@@ -57,6 +57,7 @@ containerd CLI
|
||||
runCommand,
|
||||
deleteCommand,
|
||||
namespacesCommand,
|
||||
eventsCommand,
|
||||
listCommand,
|
||||
infoCommand,
|
||||
killCommand,
|
||||
|
||||
@@ -15,6 +15,7 @@ import (
|
||||
containersapi "github.com/containerd/containerd/api/services/containers"
|
||||
contentapi "github.com/containerd/containerd/api/services/content"
|
||||
diffapi "github.com/containerd/containerd/api/services/diff"
|
||||
"github.com/containerd/containerd/api/services/events"
|
||||
"github.com/containerd/containerd/api/services/execution"
|
||||
imagesapi "github.com/containerd/containerd/api/services/images"
|
||||
namespacesapi "github.com/containerd/containerd/api/services/namespaces"
|
||||
@@ -89,6 +90,15 @@ func getTasksService(context *cli.Context) (execution.TasksClient, error) {
|
||||
return execution.NewTasksClient(conn), nil
|
||||
}
|
||||
|
||||
func getEventsService(context *cli.Context) (events.EventsClient, error) {
|
||||
conn, err := getGRPCConnection(context)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return events.NewEventsClient(conn), nil
|
||||
}
|
||||
|
||||
func getContentStore(context *cli.Context) (content.Store, error) {
|
||||
conn, err := getGRPCConnection(context)
|
||||
if err != nil {
|
||||
|
||||
Reference in New Issue
Block a user