Skip to content

Commit

Permalink
implement publish
Browse files Browse the repository at this point in the history
Signed-off-by: Nicolas De Loof <[email protected]>
  • Loading branch information
ndeloof committed Sep 17, 2023
1 parent a697a06 commit 07aa128
Showing 1 changed file with 117 additions and 3 deletions.
120 changes: 117 additions & 3 deletions pkg/compose/publish.go
Original file line number Diff line number Diff line change
Expand Up @@ -18,24 +18,138 @@ package compose

import (
"context"
"encoding/json"
"os"

"github.com/compose-spec/compose-go/types"
"github.com/distribution/reference"
"github.com/docker/buildx/util/imagetools"
"github.com/docker/compose/v2/pkg/api"
"github.com/docker/compose/v2/pkg/progress"
"github.com/opencontainers/go-digest"
"github.com/opencontainers/image-spec/specs-go"
v1 "github.com/opencontainers/image-spec/specs-go/v1"
)

func (s *composeService) Publish(ctx context.Context, project *types.Project, repository string, options api.PublishOptions) error {
return progress.RunWithTitle(ctx, func(ctx context.Context) error {
return s.publish(ctx, project, repository, options)
}, s.stdinfo(), "Publishing")
}

func (s *composeService) publish(ctx context.Context, project *types.Project, repository string, options api.PublishOptions) error {
err := s.Push(ctx, project, api.PushOptions{})
if err != nil {
return err
}

_, err = reference.ParseDockerRef(repository)
w := progress.ContextWriter(ctx)

named, err := reference.ParseDockerRef(repository)
if err != nil {
return err
}

resolver := imagetools.New(imagetools.Opt{
Auth: s.configFile(),
})

var layers []v1.Descriptor
for _, file := range project.ComposeFiles {
f, err := os.ReadFile(file)
if err != nil {
return err
}

w.Event(progress.Event{
ID: file,
Text: "publishing",
Status: progress.Working,
})
layer := v1.Descriptor{
MediaType: v1.MediaTypeImageLayer,
Digest: digest.FromString(string(f)),
Size: int64(len(f)),
Annotations: map[string]string{
"com.docker.compose": api.ComposeVersion,
},
ArtifactType: "application/vnd.docker.compose.file+yaml",
}
layers = append(layers, layer)
err = resolver.Push(ctx, named, layer, f)
if err != nil {
w.Event(progress.Event{
ID: file,
Text: "publishing",
Status: progress.Error,
})

return err
}

w.Event(progress.Event{
ID: file,
Text: "published",
Status: progress.Done,
})
}

emptyConfig, err := json.Marshal(v1.ImageConfig{})
if err != nil {
return err
}
configDescriptor := v1.Descriptor{
MediaType: v1.MediaTypeImageConfig,
Digest: digest.FromBytes(emptyConfig),
Size: int64(len(emptyConfig)),
Annotations: map[string]string{
"com.docker.compose.version": api.ComposeVersion,
},
ArtifactType: "application/vnd.docker.compose",
}
err = resolver.Push(ctx, named, configDescriptor, emptyConfig)
if err != nil {
return err
}

imageManifest, err := json.Marshal(v1.Manifest{
Versioned: specs.Versioned{SchemaVersion: 2},
MediaType: v1.MediaTypeImageManifest,
ArtifactType: "application/vnd.docker.compose.project",
Config: configDescriptor,
Layers: layers,
})
if err != nil {
return err
}

// TODO publish project.ComposeFiles
w.Event(progress.Event{
ID: repository,
Text: "publishing",
Status: progress.Working,
})

return api.ErrNotImplemented
err = resolver.Push(ctx, named, v1.Descriptor{
MediaType: v1.MediaTypeImageManifest,
Digest: digest.FromString(string(imageManifest)),
Size: int64(len(imageManifest)),
Annotations: map[string]string{
"com.docker.compose.version": api.ComposeVersion,
},
ArtifactType: "application/vnd.docker.compose",
}, imageManifest)
if err != nil {
w.Event(progress.Event{
ID: repository,
Text: "publishing",
Status: progress.Error,
})
return err
}
w.Event(progress.Event{
ID: repository,
Text: "published",
Status: progress.Done,
})
return nil
}

0 comments on commit 07aa128

Please sign in to comment.