X Tutup
Skip to content

Commit f40df3d

Browse files
committed
Enable image config labels in ctr and CRI container creation
Signed-off-by: Phil Estes <estesp@amazon.com>
1 parent d081457 commit f40df3d

File tree

8 files changed

+78
-10
lines changed

8 files changed

+78
-10
lines changed

cmd/ctr/commands/run/run.go

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -249,3 +249,16 @@ func fullID(ctx context.Context, c containerd.Container) string {
249249
}
250250
return fmt.Sprintf("%s-%s", ns, id)
251251
}
252+
253+
// buildLabel builds the labels from command line labels and the image labels
254+
func buildLabels(cmdLabels, imageLabels map[string]string) map[string]string {
255+
labels := make(map[string]string)
256+
for k, v := range imageLabels {
257+
labels[k] = v
258+
}
259+
// labels from the command line will override image and the initial image config labels
260+
for k, v := range cmdLabels {
261+
labels[k] = v
262+
}
263+
return labels
264+
}

cmd/ctr/commands/run/run_unix.go

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -103,8 +103,8 @@ func NewContainer(ctx gocontext.Context, client *containerd.Client, context *cli
103103
spec containerd.NewContainerOpts
104104
)
105105

106-
cOpts = append(cOpts, containerd.WithContainerLabels(commands.LabelArgs(context.StringSlice("label"))))
107106
if config {
107+
cOpts = append(cOpts, containerd.WithContainerLabels(commands.LabelArgs(context.StringSlice("labels"))))
108108
opts = append(opts, oci.WithSpecFromFile(context.String("config")))
109109
} else {
110110
var (
@@ -125,6 +125,7 @@ func NewContainer(ctx gocontext.Context, client *containerd.Client, context *cli
125125
return nil, err
126126
}
127127
opts = append(opts, oci.WithRootFSPath(rootfs))
128+
cOpts = append(cOpts, containerd.WithContainerLabels(commands.LabelArgs(context.StringSlice("labels"))))
128129
} else {
129130
snapshotter := context.String("snapshotter")
130131
var image containerd.Image
@@ -151,9 +152,12 @@ func NewContainer(ctx gocontext.Context, client *containerd.Client, context *cli
151152
return nil, err
152153
}
153154
}
155+
labels := buildLabels(commands.LabelArgs(context.StringSlice("label")), image.Labels())
154156
opts = append(opts, oci.WithImageConfig(image))
155157
cOpts = append(cOpts,
156158
containerd.WithImage(image),
159+
containerd.WithImageConfigLabels(image),
160+
containerd.WithAdditionalContainerLabels(labels),
157161
containerd.WithSnapshotter(snapshotter))
158162
if uidmap, gidmap := context.String("uidmap"), context.String("gidmap"); uidmap != "" && gidmap != "" {
159163
uidMap, err := parseIDMapping(uidmap)

cmd/ctr/commands/run/run_windows.go

Lines changed: 8 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -51,6 +51,7 @@ func NewContainer(ctx gocontext.Context, client *containerd.Client, context *cli
5151
if config {
5252
id = context.Args().First()
5353
opts = append(opts, oci.WithSpecFromFile(context.String("config")))
54+
cOpts = append(cOpts, containerd.WithContainerLabels(commands.LabelArgs(context.StringSlice("label"))))
5455
} else {
5556
var (
5657
ref = context.Args().First()
@@ -88,9 +89,13 @@ func NewContainer(ctx gocontext.Context, client *containerd.Client, context *cli
8889
}
8990
}
9091
opts = append(opts, oci.WithImageConfig(image))
91-
cOpts = append(cOpts, containerd.WithImage(image))
92-
cOpts = append(cOpts, containerd.WithSnapshotter(snapshotter))
93-
cOpts = append(cOpts, containerd.WithNewSnapshot(id, image))
92+
labels := buildLabels(commands.LabelArgs(context.StringSlice("label")), image.Labels())
93+
cOpts = append(cOpts,
94+
containerd.WithImage(image),
95+
containerd.WithImageConfigLabels(image),
96+
containerd.WithSnapshotter(snapshotter),
97+
containerd.WithNewSnapshot(id, image),
98+
containerd.WithAdditionalContainerLabels(labels))
9499

95100
if len(args) > 0 {
96101
opts = append(opts, oci.WithProcessArgs(args...))
@@ -124,7 +129,6 @@ func NewContainer(ctx gocontext.Context, client *containerd.Client, context *cli
124129
}
125130
}
126131

127-
cOpts = append(cOpts, containerd.WithContainerLabels(commands.LabelArgs(context.StringSlice("label"))))
128132
runtime := context.String("runtime")
129133
var runtimeOpts interface{}
130134
if runtime == "io.containerd.runhcs.v1" {

container_opts.go

Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,14 +18,19 @@ package containerd
1818

1919
import (
2020
"context"
21+
"encoding/json"
22+
"fmt"
2123

2224
"github.com/containerd/containerd/containers"
25+
"github.com/containerd/containerd/content"
2326
"github.com/containerd/containerd/errdefs"
27+
"github.com/containerd/containerd/images"
2428
"github.com/containerd/containerd/oci"
2529
"github.com/containerd/containerd/snapshots"
2630
"github.com/containerd/typeurl"
2731
"github.com/gogo/protobuf/types"
2832
"github.com/opencontainers/image-spec/identity"
33+
v1 "github.com/opencontainers/image-spec/specs-go/v1"
2934
"github.com/pkg/errors"
3035
)
3136

@@ -95,6 +100,39 @@ func WithContainerLabels(labels map[string]string) NewContainerOpts {
95100
}
96101
}
97102

103+
// WithImageConfigLabels sets the image config labels on the container.
104+
// The existing labels are cleared as this is expected to be the first
105+
// operation in setting up a container's labels. Use WithAdditionalContainerLabels
106+
// to add/overwrite the existing image config labels.
107+
func WithImageConfigLabels(image Image) NewContainerOpts {
108+
return func(ctx context.Context, _ *Client, c *containers.Container) error {
109+
ic, err := image.Config(ctx)
110+
if err != nil {
111+
return err
112+
}
113+
var (
114+
ociimage v1.Image
115+
config v1.ImageConfig
116+
)
117+
switch ic.MediaType {
118+
case v1.MediaTypeImageConfig, images.MediaTypeDockerSchema2Config:
119+
p, err := content.ReadBlob(ctx, image.ContentStore(), ic)
120+
if err != nil {
121+
return err
122+
}
123+
124+
if err := json.Unmarshal(p, &ociimage); err != nil {
125+
return err
126+
}
127+
config = ociimage.Config
128+
default:
129+
return fmt.Errorf("unknown image config media type %s", ic.MediaType)
130+
}
131+
c.Labels = config.Labels
132+
return nil
133+
}
134+
}
135+
98136
// WithAdditionalContainerLabels adds the provided labels to the container
99137
// The existing labels are preserved as long as they do not conflict with the added labels.
100138
func WithAdditionalContainerLabels(labels map[string]string) NewContainerOpts {

pkg/cri/server/container_create.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -230,7 +230,7 @@ func (c *criService) CreateContainer(ctx context.Context, r *runtime.CreateConta
230230
return nil, errors.Wrap(err, "failed to get container spec opts")
231231
}
232232

233-
containerLabels := buildLabels(config.Labels, containerKindContainer)
233+
containerLabels := buildLabels(config.Labels, image.ImageSpec.Config.Labels, containerKindContainer)
234234

235235
runtimeOptions, err := getRuntimeOptions(sandboxInfo)
236236
if err != nil {

pkg/cri/server/helpers.go

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -283,8 +283,12 @@ func filterLabel(k, v string) string {
283283
}
284284

285285
// buildLabel builds the labels from config to be passed to containerd
286-
func buildLabels(configLabels map[string]string, containerType string) map[string]string {
286+
func buildLabels(configLabels, imageConfigLabels map[string]string, containerType string) map[string]string {
287287
labels := make(map[string]string)
288+
for k, v := range imageConfigLabels {
289+
labels[k] = v
290+
}
291+
// labels from the CRI request (config) will override labels in the image config
288292
for k, v := range configLabels {
289293
labels[k] = v
290294
}

pkg/cri/server/helpers_test.go

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -118,14 +118,19 @@ func TestGetRepoDigestAndTag(t *testing.T) {
118118
}
119119

120120
func TestBuildLabels(t *testing.T) {
121+
imageConfigLabels := map[string]string{
122+
"a": "z",
123+
"d": "y",
124+
}
121125
configLabels := map[string]string{
122126
"a": "b",
123127
"c": "d",
124128
}
125-
newLabels := buildLabels(configLabels, containerKindSandbox)
126-
assert.Len(t, newLabels, 3)
129+
newLabels := buildLabels(configLabels, imageConfigLabels, containerKindSandbox)
130+
assert.Len(t, newLabels, 4)
127131
assert.Equal(t, "b", newLabels["a"])
128132
assert.Equal(t, "d", newLabels["c"])
133+
assert.Equal(t, "y", newLabels["d"])
129134
assert.Equal(t, containerKindSandbox, newLabels[containerKindLabel])
130135

131136
newLabels["a"] = "e"

pkg/cri/server/sandbox_run.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -198,7 +198,7 @@ func (c *criService) RunPodSandbox(ctx context.Context, r *runtime.RunPodSandbox
198198
return nil, errors.Wrap(err, "failed to generate sanbdox container spec options")
199199
}
200200

201-
sandboxLabels := buildLabels(config.Labels, containerKindSandbox)
201+
sandboxLabels := buildLabels(config.Labels, image.ImageSpec.Config.Labels, containerKindSandbox)
202202

203203
runtimeOpts, err := generateRuntimeOptions(ociRuntime, c.config)
204204
if err != nil {

0 commit comments

Comments
 (0)
X Tutup