diff --git a/exporter/containerimage/export.go b/exporter/containerimage/export.go index bfe3f2bcfad6..3e5ab03a84cd 100644 --- a/exporter/containerimage/export.go +++ b/exporter/containerimage/export.go @@ -234,7 +234,14 @@ func (e *imageExporterInstance) Export(ctx context.Context, src *exporter.Source if err != nil { return nil, nil, err } - desc := descriptors[0] + var desc *ocispecs.Descriptor + if len(descriptors) != 1 { + desc = descriptors["index"][0] + } else { + for _, v := range descriptors { + desc = v[0] + } + } defer func() { if err == nil { descref = NewDescriptorReference(*desc, done) @@ -360,7 +367,7 @@ func (e *imageExporterInstance) Export(ctx context.Context, src *exporter.Source } resp[exptypes.ExporterImageDescriptorKey] = base64.StdEncoding.EncodeToString(dtdesc) - dtdesclist, err := json.Marshal(map[string]any{"list": descriptors}) + dtdesclist, err := json.Marshal(descriptors) if err != nil { return nil, nil, err } diff --git a/exporter/containerimage/writer.go b/exporter/containerimage/writer.go index a23cefa7e9ac..34dbc03aac01 100644 --- a/exporter/containerimage/writer.go +++ b/exporter/containerimage/writer.go @@ -61,7 +61,11 @@ type ImageWriter struct { opt WriterOpt } -func (ic *ImageWriter) Commit(ctx context.Context, inp *exporter.Source, sessionID string, inlineCache exptypes.InlineCache, opts *ImageCommitOpts) ([]*ocispecs.Descriptor, error) { +func platformStringify(p *ocispecs.Platform) string { + return fmt.Sprintf("%s/%s", p.OS, p.Architecture) +} + +func (ic *ImageWriter) Commit(ctx context.Context, inp *exporter.Source, sessionID string, inlineCache exptypes.InlineCache, opts *ImageCommitOpts) (map[string][]*ocispecs.Descriptor, error) { if _, ok := inp.Metadata[exptypes.ExporterPlatformsKey]; len(inp.Refs) > 0 && !ok { return nil, errors.Errorf("unable to export multiple refs, missing platforms mapping") } @@ -180,9 +184,11 @@ func (ic *ImageWriter) Commit(ctx context.Context, inp *exporter.Source, session } mfstDesc.Annotations[exptypes.ExporterConfigDigestKey] = configDesc.Digest.String() - return []*ocispecs.Descriptor{ - mfstDesc, - configDesc, + return map[string][]*ocispecs.Descriptor{ + platformStringify(mfstDesc.Platform): { + mfstDesc, + configDesc, + }, }, nil } @@ -228,7 +234,7 @@ func (ic *ImageWriter) Commit(ctx context.Context, inp *exporter.Source, session labels := map[string]string{} - var descriptors []*ocispecs.Descriptor + var descriptors = make(map[string][]*ocispecs.Descriptor) var attestationManifests []ocispecs.Descriptor for i, p := range ps.Platforms { @@ -272,7 +278,7 @@ func (ic *ImageWriter) Commit(ctx context.Context, inp *exporter.Source, session dp := p.Platform mfstDesc.Platform = &dp idx.Manifests = append(idx.Manifests, *mfstDesc) - descriptors = append(descriptors, mfstDesc, configDesc) + descriptors[platformStringify(&dp)] = append(descriptors[platformStringify(&dp)], mfstDesc, configDesc) labels[fmt.Sprintf("containerd.io/gc.ref.content.%d", i)] = mfstDesc.Digest.String() @@ -328,7 +334,7 @@ func (ic *ImageWriter) Commit(ctx context.Context, inp *exporter.Source, session for i, mfst := range attestationManifests { idx.Manifests = append(idx.Manifests, mfst) - descriptors = append(descriptors, &mfst) + descriptors[platformStringify(mfst.Platform)] = append(descriptors[platformStringify(mfst.Platform)], &mfst) labels[fmt.Sprintf("containerd.io/gc.ref.content.%d", len(ps.Platforms)+i)] = mfst.Digest.String() } @@ -350,7 +356,7 @@ func (ic *ImageWriter) Commit(ctx context.Context, inp *exporter.Source, session return nil, idxDone(errors.Wrapf(err, "error writing manifest list blob %s", idxDigest)) } idxDone(nil) - descriptors = append([]*ocispecs.Descriptor{&idxDesc}, descriptors...) + descriptors["index"] = []*ocispecs.Descriptor{&idxDesc} return descriptors, nil } diff --git a/exporter/oci/export.go b/exporter/oci/export.go index db60c09d44ac..11c4b06e5383 100644 --- a/exporter/oci/export.go +++ b/exporter/oci/export.go @@ -163,7 +163,14 @@ func (e *imageExporterInstance) Export(ctx context.Context, src *exporter.Source if err != nil { return nil, nil, err } - desc := descriptors[0] + var desc *ocispecs.Descriptor + if len(descriptors) != 1 { + desc = descriptors["index"][0] + } else { + for _, v := range descriptors { + desc = v[0] + } + } defer func() { if err == nil { descref = containerimage.NewDescriptorReference(*desc, done) @@ -195,7 +202,7 @@ func (e *imageExporterInstance) Export(ctx context.Context, src *exporter.Source } resp[exptypes.ExporterImageDescriptorKey] = base64.StdEncoding.EncodeToString(dtdesc) - dtdesclist, err := json.Marshal(map[string]any{"list": descriptors}) + dtdesclist, err := json.Marshal(descriptors) if err != nil { return nil, nil, err }