Skip to content
This repository has been archived by the owner on Mar 13, 2021. It is now read-only.

Commit

Permalink
riff image load
Browse files Browse the repository at this point in the history
Fixes #806
  • Loading branch information
glyn committed Sep 24, 2018
1 parent 37511cb commit 3d8bc6a
Show file tree
Hide file tree
Showing 12 changed files with 493 additions and 14 deletions.
1 change: 1 addition & 0 deletions Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ gen-mocks:
mockery -output pkg/core/vendor_mocks -outpkg vendor_mocks -dir vendor/k8s.io/client-go/kubernetes/typed/core/v1 -name NamespaceInterface
mockery -output pkg/core/vendor_mocks -outpkg vendor_mocks -dir vendor/k8s.io/client-go/kubernetes/typed/core/v1 -name ServiceAccountInterface
mockery -output pkg/core/vendor_mocks -outpkg vendor_mocks -dir vendor/k8s.io/client-go/kubernetes/typed/core/v1 -name SecretInterface
mockery -output pkg/docker/mocks -outpkg mocks -dir pkg/docker -name Docker

install: build
cp $(OUTPUT) $(GOBIN)
Expand Down
43 changes: 42 additions & 1 deletion cmd/commands/image.go
Original file line number Diff line number Diff line change
Expand Up @@ -119,14 +119,55 @@ func ImageRelocate(c *core.Client) *cobra.Command {
return command
}

func ImageLoad(c *core.ImageClient) *cobra.Command {
options := core.LoadAndTagImagesOptions{}

command := &cobra.Command{
Use: "load",
Short: "Load and tag docker images",
Long: "Load the set of images identified by the provided image manifest into a docker daemon.\n\n" +
"NOTE: This command requires the `docker` command line tool, as well as a (local) docker daemon.\n\n"+
"SEE ALSO: To load, tag, and push images, use `riff image push`.",
Example: ` riff image load --images=riff-distro-xx/image-manifest.yaml`,
PreRunE: func(cmd *cobra.Command, args []string) error {
// FIXME: these flags should not apply to this command: https://github.com/projectriff/riff/issues/743
if cmd.Flags().Changed("kubeconfig") {
return errors.New("the 'kubeconfig' flag is not supported by the 'image load' command")
}
m, _ := cmd.Flags().GetString("master")
if len(m) > 0 {
return errors.New("the 'master' flag is not supported by the 'image load' command")
}

return nil
},
RunE: func(cmd *cobra.Command, args []string) error {
err := (*c).LoadAndTagImages(options)
if err != nil {
return err
}

PrintSuccessfulCompletion(cmd)
return nil
},
}
command.Flags().StringVarP(&options.Images, "images", "i", "", "path of an image manifest of image names to be loaded")
command.MarkFlagRequired("images")
command.MarkFlagFilename("images", "yml", "yaml")

return command
}


func ImagePush(c *core.ImageClient) *cobra.Command {
options := core.PushImagesOptions{}

command := &cobra.Command{
Use: "push",
Short: "Push (relocated) docker image names to an image registry",
Long: "Push the set of images identified by the provided image manifest into a remote registry, for later consumption by `riff system install`.\n\n" +
"NOTE: This command requires the `docker` command line tool, as well as a (local) docker daemon and will load and tag the images using that daemon.",
"NOTE: This command requires the `docker` command line tool, as well as a (local) docker daemon and will load and tag the images using that daemon.\n\n"+
"SEE ALSO: To load and tag images, but not push them, use `riff image load`.",
Example: ` riff image push --images=riff-distro-xx/image-manifest.yaml`,
RunE: func(cmd *cobra.Command, args []string) error {
err := (*c).PushImages(options)
Expand Down
1 change: 1 addition & 0 deletions cmd/commands/wiring.go
Original file line number Diff line number Diff line change
Expand Up @@ -135,6 +135,7 @@ See https://projectriff.io and https://github.com/knative/docs`,
image := Image()
image.AddCommand(
ImageRelocate(&client),
ImageLoad(&imageClient),
ImagePush(&imageClient),
)

Expand Down
1 change: 1 addition & 0 deletions docs/riff_image.md
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ Interact with docker images
### SEE ALSO

* [riff](riff.md) - Commands for creating and managing function resources
* [riff image load](riff_image_load.md) - Load and tag docker images
* [riff image push](riff_image_push.md) - Push (relocated) docker image names to an image registry
* [riff image relocate](riff_image_relocate.md) - Relocate docker image names to another registry

33 changes: 33 additions & 0 deletions docs/riff_image_load.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
## riff image load

Load and tag docker images

### Synopsis

Load the set of images identified by the provided image manifest into a docker daemon.

NOTE: This command requires the `docker` command line tool, as well as a (local) docker daemon.

SEE ALSO: To load, tag, and push images, use the image push command.

```
riff image load [flags]
```

### Examples

```
riff image load --images=riff-distro-xx/image-manifest.yaml
```

### Options

```
-h, --help help for load
-i, --images string path of an image manifest of image names to be loaded
```

### SEE ALSO

* [riff image](riff_image.md) - Interact with docker images

2 changes: 2 additions & 0 deletions docs/riff_image_push.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,8 @@ Push the set of images identified by the provided image manifest into a remote r

NOTE: This command requires the `docker` command line tool, as well as a (local) docker daemon and will load and tag the images using that daemon.

SEE ALSO: To load and tag images but not push them, use the image load command.

```
riff image push [flags]
```
Expand Down
4 changes: 4 additions & 0 deletions pkg/core/fixtures/image_client/complete.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
Images:
a/b: "1"
c/d: "2"
manifestVersion: "0.1"
4 changes: 4 additions & 0 deletions pkg/core/fixtures/image_client/incomplete.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
manifestVersion: 0.1
images:
"a/b": "1"
"c/d":
41 changes: 33 additions & 8 deletions pkg/core/image_client.go
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@ import (
)

type ImageClient interface {
LoadAndTagImages(options LoadAndTagImagesOptions) error
PushImages(options PushImagesOptions) error
PullImages(options PullImagesOptions) error
}
Expand All @@ -34,6 +35,10 @@ type PushImagesOptions struct {
Images string
}

type LoadAndTagImagesOptions struct {
Images string
}

type PullImagesOptions struct {
Images string
Output string
Expand All @@ -44,22 +49,42 @@ type imageClient struct {
docker docker.Docker
}

// TODO: provide unit test
func (c *imageClient) LoadAndTagImages(options LoadAndTagImagesOptions) error {
_, err := c.loadAndTagImages(options.Images)
return err
}

func (c *imageClient) PushImages(options PushImagesOptions) error {
imManifest, err := NewImageManifest(options.Images)
imManifest, err := c.loadAndTagImages(options.Images)
if err != nil {
return err
}
distroLocation := filepath.Dir(options.Images)
for name, digest := range imManifest.Images {
filename := filepath.Join(distroLocation, "images", string(digest))
if err := c.docker.PushImage(string(name), string(digest), filename); err != nil {
for name, _ := range imManifest.Images {
if err := c.docker.PushImage(string(name)); err != nil {
return err
}
}
return nil
}

func (c *imageClient) loadAndTagImages(imageManifest string) (*ImageManifest, error) {
imManifest, err := NewImageManifest(imageManifest)
if err != nil {
return nil, err
}
distroLocation := filepath.Dir(imageManifest)
for name, digest := range imManifest.Images {
if digest == "" {
return nil, fmt.Errorf("image manifest %s does not specify a digest for image %s", imageManifest, name)
}
filename := filepath.Join(distroLocation, "images", string(digest))
if err := c.docker.LoadAndTagImage(string(name), string(digest), filename); err != nil {
return nil, err
}
}
return imManifest, nil
}

func (c *imageClient) PullImages(options PullImagesOptions) error {
originalManifest, err := NewImageManifest(options.Images)
if err != nil {
Expand All @@ -74,7 +99,7 @@ func (c *imageClient) PullImages(options PullImagesOptions) error {
newManifestPath = filepath.Join(options.Output, "image-manifest.yaml")
imagesDir = filepath.Join(options.Output, "images")
}
if _, err := os.Stat(imagesDir); err != nil && os.IsNotExist(err) {
if _, err := os.Stat(imagesDir); err != nil {
if err2 := os.MkdirAll(imagesDir, outputDirPermissions); err2 != nil {
return err2
}
Expand All @@ -86,7 +111,7 @@ func (c *imageClient) PullImages(options PullImagesOptions) error {
if newSha, err := c.docker.PullImage(string(name), imagesDir); err != nil {
return err
} else if newSha != string(sha) && sha != "" && !options.ContinueOnMismatch {
return fmt.Errorf("image %q had digest %v in the original manifest, but the pulled version now has digest %s", name, sha, newSha)
return fmt.Errorf("image %q had digest %v in the original manifest, but the pulled version has digest %s", name, sha, newSha)
} else {
newManifest.Images[name] = imageDigest(newSha)
}
Expand Down
Loading

0 comments on commit 3d8bc6a

Please sign in to comment.