feat: Add platform attribute to docker_image resource (#500)

* feat: Add platform attribute to docker_image resource

* docs: Add updated docker_image documentation.
This commit is contained in:
Martin 2022-12-28 11:38:42 +01:00 committed by GitHub
parent 19191883d5
commit 5ffe0f3628
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
6 changed files with 38 additions and 8 deletions

View file

@ -88,6 +88,7 @@ resource "docker_image" "zoo" {
- `build` (Block Set, Max: 1) Configuration to build an image. Please see [docker build command reference](https://docs.docker.com/engine/reference/commandline/build/#options) too. (see [below for nested schema](#nestedblock--build)) - `build` (Block Set, Max: 1) Configuration to build an image. Please see [docker build command reference](https://docs.docker.com/engine/reference/commandline/build/#options) too. (see [below for nested schema](#nestedblock--build))
- `force_remove` (Boolean) If true, then the image is removed forcibly when the resource is destroyed. - `force_remove` (Boolean) If true, then the image is removed forcibly when the resource is destroyed.
- `keep_locally` (Boolean) If true, then the Docker image won't be deleted on destroy operation. If this is false, it will delete the image from the docker local storage on destroy operation. - `keep_locally` (Boolean) If true, then the Docker image won't be deleted on destroy operation. If this is false, it will delete the image from the docker local storage on destroy operation.
- `platform` (String) The platform to use when pulling the image. Defaults to the platform of the current machine.
- `pull_trigger` (String, Deprecated) A value which cause an image pull when changed - `pull_trigger` (String, Deprecated) A value which cause an image pull when changed
- `pull_triggers` (Set of String) List of values which cause an image pull when changed. This is used to store the image digest from the registry when using the [docker_registry_image](../data-sources/registry_image.md). - `pull_triggers` (Set of String) List of values which cause an image pull when changed. This is used to store the image digest from the registry when using the [docker_registry_image](../data-sources/registry_image.md).
- `triggers` (Map of String) A map of arbitrary strings that, when changed, will force the `docker_image` resource to be replaced. This can be used to rebuild an image when contents of source code folders change - `triggers` (Map of String) A map of arbitrary strings that, when changed, will force the `docker_image` resource to be replaced. This can be used to rebuild an image when contents of source code folders change

View file

@ -51,7 +51,7 @@ func resourceDockerContainerCreate(ctx context.Context, d *schema.ResourceData,
client := meta.(*ProviderConfig).DockerClient client := meta.(*ProviderConfig).DockerClient
authConfigs := meta.(*ProviderConfig).AuthConfigs authConfigs := meta.(*ProviderConfig).AuthConfigs
image := d.Get("image").(string) image := d.Get("image").(string)
_, err = findImage(ctx, image, client, authConfigs) _, err = findImage(ctx, image, client, authConfigs, "")
if err != nil { if err != nil {
return diag.Errorf("Unable to create container with image %s: %s", image, err) return diag.Errorf("Unable to create container with image %s: %s", image, err)
} }

View file

@ -161,6 +161,13 @@ func resourceDockerImage() *schema.Resource {
Optional: true, Optional: true,
ForceNew: true, ForceNew: true,
}, },
"platform": {
Type: schema.TypeString,
Description: "The platform to use when pulling the image. Defaults to the platform of the current machine.",
Optional: true,
Default: "",
ForceNew: true,
},
}, },
} }
} }

View file

@ -43,7 +43,7 @@ func resourceDockerImageCreate(ctx context.Context, d *schema.ResourceData, meta
} }
} }
} }
apiImage, err := findImage(ctx, imageName, client, meta.(*ProviderConfig).AuthConfigs) apiImage, err := findImage(ctx, imageName, client, meta.(*ProviderConfig).AuthConfigs, d.Get("platform").(string))
if err != nil { if err != nil {
return diag.Errorf("Unable to read Docker image into resource: %s", err) return diag.Errorf("Unable to read Docker image into resource: %s", err)
} }
@ -89,7 +89,7 @@ func resourceDockerImageUpdate(ctx context.Context, d *schema.ResourceData, meta
// the value of "latest" or others // the value of "latest" or others
client := meta.(*ProviderConfig).DockerClient client := meta.(*ProviderConfig).DockerClient
imageName := d.Get("name").(string) imageName := d.Get("name").(string)
apiImage, err := findImage(ctx, imageName, client, meta.(*ProviderConfig).AuthConfigs) apiImage, err := findImage(ctx, imageName, client, meta.(*ProviderConfig).AuthConfigs, d.Get("platform").(string))
if err != nil { if err != nil {
return diag.Errorf("Unable to read Docker image into resource: %s", err) return diag.Errorf("Unable to read Docker image into resource: %s", err)
} }
@ -195,7 +195,7 @@ func fetchLocalImages(ctx context.Context, data *Data, client *client.Client) er
return nil return nil
} }
func pullImage(ctx context.Context, data *Data, client *client.Client, authConfig *AuthConfigs, image string) error { func pullImage(ctx context.Context, data *Data, client *client.Client, authConfig *AuthConfigs, image string, platform string) error {
pullOpts := parseImageOptions(image) pullOpts := parseImageOptions(image)
auth := types.AuthConfig{} auth := types.AuthConfig{}
@ -210,6 +210,7 @@ func pullImage(ctx context.Context, data *Data, client *client.Client, authConfi
out, err := client.ImagePull(ctx, image, types.ImagePullOptions{ out, err := client.ImagePull(ctx, image, types.ImagePullOptions{
RegistryAuth: base64.URLEncoding.EncodeToString(encodedJSON), RegistryAuth: base64.URLEncoding.EncodeToString(encodedJSON),
Platform: platform,
}) })
if err != nil { if err != nil {
return fmt.Errorf("error pulling image %s: %w", image, err) return fmt.Errorf("error pulling image %s: %w", image, err)
@ -282,7 +283,7 @@ func parseImageOptions(image string) internalPullImageOptions {
return pullOpts return pullOpts
} }
func findImage(ctx context.Context, imageName string, client *client.Client, authConfig *AuthConfigs) (*types.ImageSummary, error) { func findImage(ctx context.Context, imageName string, client *client.Client, authConfig *AuthConfigs, platform string) (*types.ImageSummary, error) {
if imageName == "" { if imageName == "" {
return nil, fmt.Errorf("empty image name is not allowed") return nil, fmt.Errorf("empty image name is not allowed")
} }
@ -292,7 +293,6 @@ func findImage(ctx context.Context, imageName string, client *client.Client, aut
if err := fetchLocalImages(ctx, &data, client); err != nil { if err := fetchLocalImages(ctx, &data, client); err != nil {
return nil, err return nil, err
} }
foundImage, err := searchLocalImages(ctx, client, data, imageName) foundImage, err := searchLocalImages(ctx, client, data, imageName)
if err != nil { if err != nil {
return nil, fmt.Errorf("findImage1: error looking up local image %q: %w", imageName, err) return nil, fmt.Errorf("findImage1: error looking up local image %q: %w", imageName, err)
@ -300,8 +300,7 @@ func findImage(ctx context.Context, imageName string, client *client.Client, aut
if foundImage != nil { if foundImage != nil {
return foundImage, nil return foundImage, nil
} }
if err := pullImage(ctx, &data, client, authConfig, imageName, platform); err != nil {
if err := pullImage(ctx, &data, client, authConfig, imageName); err != nil {
return nil, fmt.Errorf("unable to pull image %s: %s", imageName, err) return nil, fmt.Errorf("unable to pull image %s: %s", imageName, err)
} }

View file

@ -314,6 +314,25 @@ func TestAccDockerImage_tag_sha265(t *testing.T) {
}) })
} }
func TestAccDockerImage_platform(t *testing.T) {
ctx := context.Background()
resource.Test(t, resource.TestCase{
PreCheck: func() { testAccPreCheck(t) },
ProviderFactories: providerFactories,
CheckDestroy: func(state *terraform.State) error {
return testAccDockerImageDestroy(ctx, state)
},
Steps: []resource.TestStep{
{
Config: loadTestConfiguration(t, RESOURCE, "docker_image", "testAccDockerImagePlatform"),
Check: resource.ComposeTestCheckFunc(
resource.TestCheckResourceAttr("docker_image.foo", "image_id", "sha256:8336f9f1d0946781f428a155536995f0d8a31209d65997e2a379a23e7a441b78"),
),
},
},
})
}
func TestAccDockerImage_build(t *testing.T) { func TestAccDockerImage_build(t *testing.T) {
ctx := context.Background() ctx := context.Background()
wd, _ := os.Getwd() wd, _ := os.Getwd()

View file

@ -0,0 +1,4 @@
resource "docker_image" "foo" {
name = "busybox:1.34.0"
platform = "linux/amd64"
}