feat: support import image for specific platform

Signed-off-by: jonyhy <yun.hao@daocloud.io>
This commit is contained in:
jonyhy 2021-09-29 14:00:17 +08:00
parent d132691f10
commit da16d492cd
2 changed files with 41 additions and 13 deletions

View File

@ -26,6 +26,7 @@ import (
"github.com/containerd/containerd/cmd/ctr/commands"
"github.com/containerd/containerd/images/archive"
"github.com/containerd/containerd/log"
"github.com/containerd/containerd/platforms"
"github.com/urfave/cli"
)
@ -72,6 +73,10 @@ If foobar.tar contains an OCI ref named "latest" and anonymous ref "sha256:deadb
Name: "all-platforms",
Usage: "imports content for all platforms, false by default",
},
cli.BoolFlag{
Name: "platform",
Usage: "imports content for specific platform",
},
cli.BoolFlag{
Name: "no-unpack",
Usage: "skip unpacking the images, false by default",
@ -84,8 +89,9 @@ If foobar.tar contains an OCI ref named "latest" and anonymous ref "sha256:deadb
Action: func(context *cli.Context) error {
var (
in = context.Args().First()
opts []containerd.ImportOpt
in = context.Args().First()
opts []containerd.ImportOpt
platformMacher platforms.MatchComparer
)
prefix := context.String("base-name")
@ -115,6 +121,15 @@ If foobar.tar contains an OCI ref named "latest" and anonymous ref "sha256:deadb
opts = append(opts, containerd.WithImportCompression())
}
if platform := context.String("platform"); platform != "" {
platSpec, err := platforms.Parse(platform)
if err != nil {
return err
}
platformMacher = platforms.Only(platSpec)
opts = append(opts, containerd.WithImportPlatform(platformMacher))
}
opts = append(opts, containerd.WithAllPlatforms(context.Bool("all-platforms")))
client, ctx, cancel, err := commands.NewClient(context)
@ -145,8 +160,10 @@ If foobar.tar contains an OCI ref named "latest" and anonymous ref "sha256:deadb
log.G(ctx).Debugf("unpacking %d images", len(imgs))
for _, img := range imgs {
// TODO: Allow configuration of the platform
image := containerd.NewImage(client, img)
if platformMacher == nil { // if platform not specified use default.
platformMacher = platforms.Default()
}
image := containerd.NewImageWithPlatform(client, img, platformMacher)
// TODO: Show unpack status
fmt.Printf("unpacking %s (%s)...", img.Name, img.Target.Digest)

View File

@ -31,12 +31,13 @@ import (
)
type importOpts struct {
indexName string
imageRefT func(string) string
dgstRefT func(digest.Digest) string
skipDgstRef func(string) bool
allPlatforms bool
compress bool
indexName string
imageRefT func(string) string
dgstRefT func(digest.Digest) string
skipDgstRef func(string) bool
allPlatforms bool
platformMatcher platforms.MatchComparer
compress bool
}
// ImportOpt allows the caller to specify import specific options
@ -87,6 +88,14 @@ func WithAllPlatforms(allPlatforms bool) ImportOpt {
}
}
// WithImportPlatform is used to import content for specific platform.
func WithImportPlatform(platformMacher platforms.MatchComparer) ImportOpt {
return func(c *importOpts) error {
c.platformMatcher = platformMacher
return nil
}
}
// WithImportCompression compresses uncompressed layers on import.
// This is used for import formats which do not include the manifest.
func WithImportCompression() ImportOpt {
@ -135,9 +144,11 @@ func (c *Client) Import(ctx context.Context, reader io.Reader, opts ...ImportOpt
Target: index,
})
}
var platformMatcher = platforms.All
if !iopts.allPlatforms {
platformMatcher = c.platform
var platformMatcher = c.platform
if iopts.allPlatforms {
platformMatcher = platforms.All
} else if iopts.platformMatcher != nil {
platformMatcher = iopts.platformMatcher
}
var handler images.HandlerFunc = func(ctx context.Context, desc ocispec.Descriptor) ([]ocispec.Descriptor, error) {