mirror of https://github.com/docker/buildx.git
imagetools: fix merging JSON descriptor with old one
Signed-off-by: Tonis Tiigi <tonistiigi@gmail.com>
This commit is contained in:
parent
ab09846df7
commit
328441cdc6
|
@ -118,7 +118,15 @@ func runCreate(dockerCli command.Cli, in createOptions, args []string) error {
|
|||
return err
|
||||
}
|
||||
srcs[i].Ref = nil
|
||||
srcs[i].Desc = desc
|
||||
if srcs[i].Desc.Digest == "" {
|
||||
srcs[i].Desc = desc
|
||||
} else {
|
||||
var err error
|
||||
srcs[i].Desc, err = mergeDesc(desc, srcs[i].Desc)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
return nil
|
||||
})
|
||||
}(i)
|
||||
|
@ -238,3 +246,19 @@ func createCmd(dockerCli command.Cli) *cobra.Command {
|
|||
|
||||
return cmd
|
||||
}
|
||||
|
||||
func mergeDesc(d1, d2 ocispec.Descriptor) (ocispec.Descriptor, error) {
|
||||
if d2.Size != 0 && d1.Size != d2.Size {
|
||||
return ocispec.Descriptor{}, errors.Errorf("invalid size mismatch for %s, %d != %d", d1.Digest, d2.Size, d1.Size)
|
||||
}
|
||||
if d2.MediaType != "" {
|
||||
d1.MediaType = d2.MediaType
|
||||
}
|
||||
if len(d2.Annotations) != 0 {
|
||||
d1.Annotations = d2.Annotations // no merge so support removes
|
||||
}
|
||||
if d2.Platform != nil {
|
||||
d1.Platform = d2.Platform // missing items filled in later from image config
|
||||
}
|
||||
return d1, nil
|
||||
}
|
||||
|
|
|
@ -50,6 +50,19 @@ Use the `--dry-run` flag to not push the image, just show it.
|
|||
Reads source from files. A source can be a manifest digest, manifest reference,
|
||||
or a JSON of OCI descriptor object.
|
||||
|
||||
In order to define annotations or additional platform properties like `os.version` and
|
||||
`os.features` you need to add them in the OCI descriptor object encoded in JSON.
|
||||
|
||||
```
|
||||
docker buildx imagetools inspect --raw alpine | jq '.manifests[0] | .platform."os.version"="10.1"' > descr.json
|
||||
docker buildx imagetools create -f descr.json myuser/image
|
||||
```
|
||||
|
||||
The descriptor in the file is merged with existing descriptor in the registry if it exists.
|
||||
|
||||
The supported fields for the descriptor are defined in [OCI spec](https://github.com/opencontainers/image-spec/blob/master/descriptor.md#properties) .
|
||||
|
||||
|
||||
### <a name="tag"></a> Set reference for new image (-t, --tag)
|
||||
|
||||
```
|
||||
|
|
|
@ -47,13 +47,16 @@ func (r *Resolver) Combine(ctx context.Context, in string, descs []ocispec.Descr
|
|||
|
||||
switch mt {
|
||||
case images.MediaTypeDockerSchema2Manifest, ocispec.MediaTypeImageManifest:
|
||||
p := descs[i].Platform
|
||||
if descs[i].Platform == nil {
|
||||
p, err := r.loadPlatform(ctx, in, dt)
|
||||
if err != nil {
|
||||
p = &ocispec.Platform{}
|
||||
}
|
||||
if p.OS == "" || p.Architecture == "" {
|
||||
if err := r.loadPlatform(ctx, p, in, dt); err != nil {
|
||||
return err
|
||||
}
|
||||
descs[i].Platform = p
|
||||
}
|
||||
descs[i].Platform = p
|
||||
case images.MediaTypeDockerSchema1Manifest:
|
||||
return errors.Errorf("schema1 manifests are not allowed in manifest lists")
|
||||
}
|
||||
|
@ -166,24 +169,35 @@ func (r *Resolver) Push(ctx context.Context, ref reference.Named, desc ocispec.D
|
|||
return err
|
||||
}
|
||||
|
||||
func (r *Resolver) loadPlatform(ctx context.Context, in string, dt []byte) (*ocispec.Platform, error) {
|
||||
func (r *Resolver) loadPlatform(ctx context.Context, p2 *ocispec.Platform, in string, dt []byte) error {
|
||||
var manifest ocispec.Manifest
|
||||
if err := json.Unmarshal(dt, &manifest); err != nil {
|
||||
return nil, errors.WithStack(err)
|
||||
return errors.WithStack(err)
|
||||
}
|
||||
|
||||
dt, err := r.GetDescriptor(ctx, in, manifest.Config)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
return err
|
||||
}
|
||||
|
||||
var p ocispec.Platform
|
||||
if err := json.Unmarshal(dt, &p); err != nil {
|
||||
return nil, errors.WithStack(err)
|
||||
return errors.WithStack(err)
|
||||
}
|
||||
|
||||
p = platforms.Normalize(p)
|
||||
return &p, nil
|
||||
|
||||
if p2.Architecture == "" {
|
||||
p2.Architecture = p.Architecture
|
||||
if p2.Variant == "" {
|
||||
p2.Variant = p.Variant
|
||||
}
|
||||
}
|
||||
if p2.OS == "" {
|
||||
p2.OS = p.OS
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func detectMediaType(dt []byte) (string, error) {
|
||||
|
|
Loading…
Reference in New Issue