Use tarball.LayerFromOpener

tarball.LayerFromReader slurps the whole src in memory. The payoff is
that we might read the file multiple time as internally it's called
multiple times.
This commit is contained in:
Ettore Di Giacinto 2021-11-22 11:27:46 +01:00
parent 80412e2e5d
commit 44e66cc729
3 changed files with 18 additions and 36 deletions

View File

@ -28,7 +28,6 @@ import (
fileHelper "github.com/mudler/luet/pkg/helpers/file"
"github.com/pkg/errors"
containerdCompression "github.com/containerd/containerd/archive/compression"
"github.com/mudler/luet/cmd/util"
"github.com/mudler/luet/pkg/helpers/docker"
@ -36,16 +35,6 @@ import (
)
func pack(ctx *luettypes.Context, p, dst, imageName, arch, OS string) error {
archiveFile, err := os.Open(p)
if err != nil {
return errors.Wrap(err, "Cannot open "+p)
}
defer archiveFile.Close()
decompressed, err := containerdCompression.DecompressStream(archiveFile)
if err != nil {
return errors.Wrap(err, "Cannot open "+p)
}
tempimage, err := ctx.Config.GetSystem().TempFile("tempimage")
if err != nil {
@ -53,7 +42,7 @@ func pack(ctx *luettypes.Context, p, dst, imageName, arch, OS string) error {
}
defer os.RemoveAll(tempimage.Name()) // clean up
if err := image.CreateTarReader(decompressed, tempimage.Name(), imageName, arch, OS); err != nil {
if err := image.CreateTar(p, tempimage.Name(), imageName, arch, OS); err != nil {
return errors.Wrap(err, "could not create image from tar")
}

View File

@ -19,6 +19,7 @@ import (
"io"
"os"
containerdCompression "github.com/containerd/containerd/archive/compression"
"github.com/google/go-containerregistry/pkg/name"
v1 "github.com/google/go-containerregistry/pkg/v1"
"github.com/google/go-containerregistry/pkg/v1/empty"
@ -27,13 +28,13 @@ import (
"github.com/pkg/errors"
)
func imageFromTar(imagename, architecture, OS string, r io.Reader) (name.Reference, v1.Image, error) {
func imageFromTar(imagename, architecture, OS string, opener func() (io.ReadCloser, error)) (name.Reference, v1.Image, error) {
newRef, err := name.ParseReference(imagename)
if err != nil {
return nil, nil, err
}
layer, err := tarball.LayerFromReader(r)
layer, err := tarball.LayerFromOpener(opener)
if err != nil {
return nil, nil, err
}
@ -67,28 +68,30 @@ func imageFromTar(imagename, architecture, OS string, r io.Reader) (name.Referen
// CreateTar a imagetarball from a standard tarball
func CreateTar(srctar, dstimageTar, imagename, architecture, OS string) error {
f, err := os.Open(srctar)
if err != nil {
return errors.Wrap(err, "Cannot open "+srctar)
}
defer f.Close()
return CreateTarReader(f, dstimageTar, imagename, architecture, OS)
}
// CreateTarReader a imagetarball from a standard tarball
func CreateTarReader(r io.Reader, dstimageTar, imagename, architecture, OS string) error {
dstFile, err := os.Create(dstimageTar)
if err != nil {
return errors.Wrap(err, "Cannot create "+dstimageTar)
}
defer dstFile.Close()
newRef, img, err := imageFromTar(imagename, architecture, OS, r)
newRef, img, err := imageFromTar(imagename, architecture, OS, func() (io.ReadCloser, error) {
f, err := os.Open(srctar)
if err != nil {
return nil, errors.Wrap(err, "Cannot open "+srctar)
}
decompressed, err := containerdCompression.DecompressStream(f)
if err != nil {
return nil, errors.Wrap(err, "Cannot open "+srctar)
}
return decompressed, nil
})
if err != nil {
return err
}
// NOTE: We might also stream that back to the daemon with daemon.Write(tag, img)
return tarball.Write(newRef, img, dstFile)
}

View File

@ -211,16 +211,6 @@ type ImageBuilder interface {
// GenerateFinalImage takes an artifact and builds a Docker image with its content
func (a *PackageArtifact) GenerateFinalImage(ctx *types.Context, imageName string, b ImageBuilder, keepPerms bool) error {
archiveFile, err := os.Open(a.Path)
if err != nil {
return errors.Wrap(err, "Cannot open "+a.Path)
}
defer archiveFile.Close()
decompressed, err := containerdCompression.DecompressStream(archiveFile)
if err != nil {
return errors.Wrap(err, "Cannot open "+a.Path)
}
tempimage, err := ctx.Config.GetSystem().TempFile("tempimage")
if err != nil {
@ -228,7 +218,7 @@ func (a *PackageArtifact) GenerateFinalImage(ctx *types.Context, imageName strin
}
defer os.RemoveAll(tempimage.Name()) // clean up
if err := image.CreateTarReader(decompressed, tempimage.Name(), imageName, runtime.GOARCH, runtime.GOOS); err != nil {
if err := image.CreateTar(a.Path, tempimage.Name(), imageName, runtime.GOARCH, runtime.GOOS); err != nil {
return errors.Wrap(err, "could not create image from tar")
}