diff --git a/libcontainer/specconv/spec_linux.go b/libcontainer/specconv/spec_linux.go index af569726f05..4c6f7b7ad69 100644 --- a/libcontainer/specconv/spec_linux.go +++ b/libcontainer/specconv/spec_linux.go @@ -165,14 +165,16 @@ func CreateLibcontainerConfig(opts *CreateOpts) (*configs.Config, error) { if !filepath.IsAbs(rootfsPath) { rootfsPath = filepath.Join(cwd, rootfsPath) } + labels := []string{} + for k, v := range spec.Annotations { + labels = append(labels, fmt.Sprintf("%s=%s", k, v)) + } config := &configs.Config{ Rootfs: rootfsPath, NoPivotRoot: opts.NoPivotRoot, Readonlyfs: spec.Root.Readonly, Hostname: spec.Hostname, - Labels: []string{ - "bundle=" + cwd, - }, + Labels: append(labels, fmt.Sprintf("bundle=%s", cwd)), } exists := false diff --git a/libcontainer/utils/utils.go b/libcontainer/utils/utils.go index 9e748a6d6f0..3466bfcea68 100644 --- a/libcontainer/utils/utils.go +++ b/libcontainer/utils/utils.go @@ -100,3 +100,22 @@ func SearchLabels(labels []string, query string) string { } return "" } + +// Annotations returns the bundle path and user defined annotations from the +// libcontianer state. We need to remove the bundle because that is a label +// added by libcontainer. +func Annotations(labels []string) (bundle string, userAnnotations map[string]string) { + userAnnotations = make(map[string]string) + for _, l := range labels { + parts := strings.SplitN(l, "=", 2) + if len(parts) < 2 { + continue + } + if parts[0] == "bundle" { + bundle = parts[1] + } else { + userAnnotations[parts[0]] = parts[1] + } + } + return +} diff --git a/list.go b/list.go index 627310d6b3a..7214b451194 100644 --- a/list.go +++ b/list.go @@ -31,6 +31,8 @@ type containerState struct { Bundle string `json:"bundle"` // Created is the unix timestamp for the creation time of the container in UTC Created time.Time `json:"created"` + // Annotations is the user defined annotations added to the config. + Annotations map[string]string `json:"annotations,omitempty"` } var listCommand = cli.Command{ @@ -116,12 +118,15 @@ func getContainers(context *cli.Context) ([]containerState, error) { if err != nil { return nil, err } + bundle, annotations := utils.Annotations(state.Config.Labels) s = append(s, containerState{ ID: state.BaseState.ID, InitProcessPid: state.BaseState.InitProcessPid, Status: containerStatus.String(), - Bundle: utils.SearchLabels(state.Config.Labels, "bundle"), - Created: state.BaseState.Created}) + Bundle: bundle, + Created: state.BaseState.Created, + Annotations: annotations, + }) } } return s, nil diff --git a/state.go b/state.go index c5ee921aace..676384e26fc 100644 --- a/state.go +++ b/state.go @@ -30,6 +30,8 @@ type cState struct { Status string `json:"status"` // Created is the unix timestamp for the creation time of the container in UTC Created time.Time `json:"created"` + // Annotations is the user defined annotations added to the config. + Annotations map[string]string `json:"annotations,omitempty"` } var stateCommand = cli.Command{ @@ -53,14 +55,17 @@ instance of a container.`, if err != nil { return err } + bundle, annotations := utils.Annotations(state.Config.Labels) cs := cState{ Version: state.BaseState.Config.Version, ID: state.BaseState.ID, InitProcessPid: state.BaseState.InitProcessPid, Status: containerStatus.String(), - Bundle: utils.SearchLabels(state.Config.Labels, "bundle"), + Bundle: bundle, Rootfs: state.BaseState.Config.Rootfs, - Created: state.BaseState.Created} + Created: state.BaseState.Created, + Annotations: annotations, + } data, err := json.MarshalIndent(cs, "", " ") if err != nil { return err