docker-multi-arch-builder/image.go

87 lines
2.3 KiB
Go

package main
import (
"fmt"
log "github.com/sirupsen/logrus"
)
type Image struct {
name string
tag string
}
func (image Image) String() string {
imageName := image.name
if image.tag != "" {
imageName = fmt.Sprintf("%s:%s", imageName, image.tag)
}
return imageName
}
type ManifestImage struct {
Image
layers Layers
buildDir string
}
func NewManifest(imageName string, imageTag string, buildDir string, platforms []string) ManifestImage {
return ManifestImage{
Image: Image{
imageName,
imageTag,
},
layers: NewLayers(imageName, platforms),
buildDir: buildDir,
}
}
// CreateLayers build and push each layer image
func (manifest *ManifestImage) CreateLayers(registry Registry, buildOpt string) {
for _, layer := range manifest.layers {
layer.CreateLayer(registry, manifest.buildDir, buildOpt)
}
}
// CreateManifest produce manifest list of layers
func (manifest *ManifestImage) CreateManifest(registry Registry) {
const insecureRegistryOpt = "--insecure"
// $(OCI_CLI) manifest create $(OCI_OPT) $(REGISTRY_IP):5000/$(1) --amend docker.registry:5000/registry-ui:linux-armv6
var amend []string
for _, layer := range manifest.layers {
amend = append(amend, "--amend")
amend = append(amend, fmt.Sprintf("%s/%s", registry.String(), layer.Image.String()))
}
if stdout, err := runOciCli("docker", "manifest create", insecureRegistryOpt, registry, manifest.Image, amend...); err != nil {
log.Fatal(err)
} else {
log.Debug(stdout)
}
// $(OCI_CLI) manifest annotate --os linux --arch arm --variant v6 $(REGISTRY_IP):5000/$(1) $(REGISTRY_IP):5000/$(1):linux-armv6
for _, layer := range manifest.layers {
manifest.annotateManifest(registry, layer)
}
// $(OCI_CLI) manifest push $(OCI_OPT) $(REGISTRY_IP):5000/$(1)
if stdout, err := runOciCli("docker", "manifest push", insecureRegistryOpt, registry, manifest.Image); err != nil {
log.Fatal(err)
} else {
log.Debug(stdout)
}
}
func (manifest *ManifestImage) annotateManifest(registry Registry, layer Layer) {
stdout, err := runOciCli("docker", "manifest annotate",
fmt.Sprintf("--os %s --arch %s --variant %s", layer.os, layer.arch, layer.variant),
registry, manifest.Image,
fmt.Sprintf("%s/%s", registry.String(), layer.Image.String()),
)
if err != nil {
log.Warn("layer %s not annotated", layer.String())
} else {
log.Debug(stdout)
}
}