build using HCL2 (#8423)

This follows #8232 which added the code to generate the code required to parse
HCL files for each packer component.

All old config files of packer will keep on working the same. Packer takes one
argument. When a directory is passed, all files in the folder with a name
ending with  “.pkr.hcl” or “.pkr.json” will be parsed using the HCL2 format.
When a file ending with “.pkr.hcl” or “.pkr.json” is passed it will be parsed
using the HCL2 format. For every other case; the old packer style will be used.

## 1. the hcl2template pkg can create a packer.Build from a set of HCL (v2) files

I had to make the packer.coreBuild (which is our one and only packer.Build ) a public struct with public fields

## 2. Components interfaces get a new ConfigSpec Method to read a file from an HCL file.

  This is a breaking change for packer plugins.

a packer component can be a: builder/provisioner/post-processor

each component interface now gets a `ConfigSpec() hcldec.ObjectSpec`
which allows packer to tell what is the layout of the hcl2 config meant
to configure that specific component.

This ObjectSpec is sent through the wire (RPC) and a cty.Value is now
sent through the already existing configuration entrypoints:

 Provisioner.Prepare(raws ...interface{}) error
 Builder.Prepare(raws ...interface{}) ([]string, error)
 PostProcessor.Configure(raws ...interface{}) error

close #1768


Example hcl files:

```hcl
// file amazon-ebs-kms-key/run.pkr.hcl
build {
    sources = [
        "source.amazon-ebs.first",
    ]

    provisioner "shell" {
        inline = [
            "sleep 5"
        ]
    }

    post-processor "shell-local" {
        inline = [
            "sleep 5"
        ]
    }
}

// amazon-ebs-kms-key/source.pkr.hcl

source "amazon-ebs" "first" {

    ami_name = "hcl2-test"
    region = "us-east-1"
    instance_type = "t2.micro"

    kms_key_id = "c729958f-c6ba-44cd-ab39-35ab68ce0a6c"
    encrypt_boot = true
    source_ami_filter {
        filters {
          virtualization-type = "hvm"
          name =  "amzn-ami-hvm-????.??.?.????????-x86_64-gp2"
          root-device-type = "ebs"
        }
        most_recent = true
        owners = ["amazon"]
    }
    launch_block_device_mappings {
        device_name = "/dev/xvda"
        volume_size = 20
        volume_type = "gp2"
        delete_on_termination = "true"
    }
    launch_block_device_mappings {
        device_name = "/dev/xvdf"
        volume_size = 500
        volume_type = "gp2"
        delete_on_termination = true
        encrypted = true
    }

    ami_regions = ["eu-central-1"]
    run_tags {
        Name = "packer-solr-something"
        stack-name = "DevOps Tools"
    }
    
    communicator = "ssh"
    ssh_pty = true
    ssh_username = "ec2-user"
    associate_public_ip_address = true
}
```
This commit is contained in:
Adrien Delorme 2019-12-17 11:25:56 +01:00 committed by GitHub
parent c57f093efe
commit 0785c2f6fc
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
348 changed files with 5944 additions and 3160 deletions

View File

@ -8,6 +8,7 @@ import (
"context"
"fmt"
"github.com/hashicorp/hcl/v2/hcldec"
"github.com/hashicorp/packer/common"
"github.com/hashicorp/packer/helper/communicator"
"github.com/hashicorp/packer/helper/config"
@ -41,6 +42,8 @@ const (
ALICLOUD_DEFAULT_LONG_TIMEOUT = 3600
)
func (b *Builder) ConfigSpec() hcldec.ObjectSpec { return b.config.FlatMapstructure().HCL2Spec() }
func (b *Builder) Prepare(raws ...interface{}) ([]string, error) {
err := config.Decode(&b.config, &config.DecodeOpts{
Interpolate: true,

View File

@ -22,10 +22,13 @@ type FlatAlicloudDiskDevice struct {
// FlatMapstructure returns a new FlatAlicloudDiskDevice.
// FlatAlicloudDiskDevice is an auto-generated flat version of AlicloudDiskDevice.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*AlicloudDiskDevice) FlatMapstructure() interface{} { return new(FlatAlicloudDiskDevice) }
func (*AlicloudDiskDevice) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatAlicloudDiskDevice)
}
// HCL2Spec returns the hcldec.Spec of a FlatAlicloudDiskDevice.
// This spec is used by HCL to read the fields of FlatAlicloudDiskDevice.
// HCL2Spec returns the hcl spec of a AlicloudDiskDevice.
// This spec is used by HCL to read the fields of AlicloudDiskDevice.
// The decoded values from this spec will then be applied to a FlatAlicloudDiskDevice.
func (*FlatAlicloudDiskDevice) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"disk_name": &hcldec.AttrSpec{Name: "disk_name", Type: cty.String, Required: false},
@ -121,8 +124,8 @@ type FlatConfig struct {
SSHReadWriteTimeout *string `mapstructure:"ssh_read_write_timeout" cty:"ssh_read_write_timeout"`
SSHRemoteTunnels []string `mapstructure:"ssh_remote_tunnels" cty:"ssh_remote_tunnels"`
SSHLocalTunnels []string `mapstructure:"ssh_local_tunnels" cty:"ssh_local_tunnels"`
SSHPublicKey []byte `cty:"ssh_public_key"`
SSHPrivateKey []byte `cty:"ssh_private_key"`
SSHPublicKey []byte `mapstructure:"ssh_public_key" cty:"ssh_public_key"`
SSHPrivateKey []byte `mapstructure:"ssh_private_key" cty:"ssh_private_key"`
WinRMUser *string `mapstructure:"winrm_username" cty:"winrm_username"`
WinRMPassword *string `mapstructure:"winrm_password" cty:"winrm_password"`
WinRMHost *string `mapstructure:"winrm_host" cty:"winrm_host"`
@ -137,10 +140,13 @@ type FlatConfig struct {
// FlatMapstructure returns a new FlatConfig.
// FlatConfig is an auto-generated flat version of Config.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*Config) FlatMapstructure() interface{} { return new(FlatConfig) }
func (*Config) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatConfig)
}
// HCL2Spec returns the hcldec.Spec of a FlatConfig.
// This spec is used by HCL to read the fields of FlatConfig.
// HCL2Spec returns the hcl spec of a Config.
// This spec is used by HCL to read the fields of Config.
// The decoded values from this spec will then be applied to a FlatConfig.
func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"packer_build_name": &hcldec.AttrSpec{Name: "packer_build_name", Type: cty.String, Required: false},
@ -169,7 +175,7 @@ func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
"image_ignore_data_disks": &hcldec.AttrSpec{Name: "image_ignore_data_disks", Type: cty.Bool, Required: false},
"tags": &hcldec.BlockAttrsSpec{TypeName: "tags", ElementType: cty.String, Required: false},
"system_disk_mapping": &hcldec.BlockSpec{TypeName: "system_disk_mapping", Nested: hcldec.ObjectSpec((*FlatAlicloudDiskDevice)(nil).HCL2Spec())},
"image_disk_mappings": &hcldec.BlockListSpec{TypeName: "image_disk_mappings", Nested: &hcldec.BlockSpec{TypeName: "image_disk_mappings", Nested: hcldec.ObjectSpec((*FlatAlicloudDiskDevice)(nil).HCL2Spec())}},
"image_disk_mappings": &hcldec.BlockListSpec{TypeName: "image_disk_mappings", Nested: hcldec.ObjectSpec((*FlatAlicloudDiskDevice)(nil).HCL2Spec())},
"associate_public_ip_address": &hcldec.AttrSpec{Name: "associate_public_ip_address", Type: cty.Bool, Required: false},
"zone_id": &hcldec.AttrSpec{Name: "zone_id", Type: cty.String, Required: false},
"io_optimized": &hcldec.AttrSpec{Name: "io_optimized", Type: cty.Bool, Required: false},

View File

@ -3,9 +3,9 @@ package ecs
import (
"context"
"fmt"
"github.com/aliyun/alibaba-cloud-sdk-go/sdk/errors"
"time"
"github.com/aliyun/alibaba-cloud-sdk-go/sdk/errors"
"github.com/aliyun/alibaba-cloud-sdk-go/services/ecs"
"github.com/hashicorp/packer/helper/multistep"
"github.com/hashicorp/packer/packer"

View File

@ -13,6 +13,7 @@ import (
"runtime"
"github.com/aws/aws-sdk-go/service/ec2"
"github.com/hashicorp/hcl/v2/hcldec"
awscommon "github.com/hashicorp/packer/builder/amazon/common"
"github.com/hashicorp/packer/common"
"github.com/hashicorp/packer/common/chroot"
@ -182,6 +183,8 @@ type Builder struct {
runner multistep.Runner
}
func (b *Builder) ConfigSpec() hcldec.ObjectSpec { return b.config.FlatMapstructure().HCL2Spec() }
func (b *Builder) Prepare(raws ...interface{}) ([]string, error) {
b.config.ctx.Funcs = awscommon.TemplateFuncs
err := config.Decode(&b.config, &config.DecodeOpts{

View File

@ -72,10 +72,13 @@ type FlatConfig struct {
// FlatMapstructure returns a new FlatConfig.
// FlatConfig is an auto-generated flat version of Config.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*Config) FlatMapstructure() interface{} { return new(FlatConfig) }
func (*Config) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatConfig)
}
// HCL2Spec returns the hcldec.Spec of a FlatConfig.
// This spec is used by HCL to read the fields of FlatConfig.
// HCL2Spec returns the hcl spec of a Config.
// This spec is used by HCL to read the fields of Config.
// The decoded values from this spec will then be applied to a FlatConfig.
func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"packer_build_name": &hcldec.AttrSpec{Name: "packer_build_name", Type: cty.String, Required: false},
@ -116,7 +119,7 @@ func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
"skip_metadata_api_check": &hcldec.AttrSpec{Name: "skip_metadata_api_check", Type: cty.Bool, Required: false},
"token": &hcldec.AttrSpec{Name: "token", Type: cty.String, Required: false},
"vault_aws_engine": &hcldec.BlockSpec{TypeName: "vault_aws_engine", Nested: hcldec.ObjectSpec((*common.FlatVaultAWSEngineOptions)(nil).HCL2Spec())},
"ami_block_device_mappings": &hcldec.BlockListSpec{TypeName: "ami_block_device_mappings", Nested: &hcldec.BlockSpec{TypeName: "ami_block_device_mappings", Nested: hcldec.ObjectSpec((*common.FlatBlockDevice)(nil).HCL2Spec())}},
"ami_block_device_mappings": &hcldec.BlockListSpec{TypeName: "ami_block_device_mappings", Nested: hcldec.ObjectSpec((*common.FlatBlockDevice)(nil).HCL2Spec())},
"chroot_mounts": &hcldec.BlockListSpec{TypeName: "chroot_mounts", Nested: &hcldec.AttrSpec{Name: "chroot_mounts", Type: cty.List(cty.String), Required: false}},
"command_wrapper": &hcldec.AttrSpec{Name: "command_wrapper", Type: cty.String, Required: false},
"copy_files": &hcldec.AttrSpec{Name: "copy_files", Type: cty.List(cty.String), Required: false},

View File

@ -18,10 +18,13 @@ type FlatVaultAWSEngineOptions struct {
// FlatMapstructure returns a new FlatVaultAWSEngineOptions.
// FlatVaultAWSEngineOptions is an auto-generated flat version of VaultAWSEngineOptions.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*VaultAWSEngineOptions) FlatMapstructure() interface{} { return new(FlatVaultAWSEngineOptions) }
func (*VaultAWSEngineOptions) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatVaultAWSEngineOptions)
}
// HCL2Spec returns the hcldec.Spec of a FlatVaultAWSEngineOptions.
// This spec is used by HCL to read the fields of FlatVaultAWSEngineOptions.
// HCL2Spec returns the hcl spec of a VaultAWSEngineOptions.
// This spec is used by HCL to read the fields of VaultAWSEngineOptions.
// The decoded values from this spec will then be applied to a FlatVaultAWSEngineOptions.
func (*FlatVaultAWSEngineOptions) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"name": &hcldec.AttrSpec{Name: "name", Type: cty.String, Required: false},

View File

@ -24,10 +24,13 @@ type FlatBlockDevice struct {
// FlatMapstructure returns a new FlatBlockDevice.
// FlatBlockDevice is an auto-generated flat version of BlockDevice.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*BlockDevice) FlatMapstructure() interface{} { return new(FlatBlockDevice) }
func (*BlockDevice) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatBlockDevice)
}
// HCL2Spec returns the hcldec.Spec of a FlatBlockDevice.
// This spec is used by HCL to read the fields of FlatBlockDevice.
// HCL2Spec returns the hcl spec of a BlockDevice.
// This spec is used by HCL to read the fields of BlockDevice.
// The decoded values from this spec will then be applied to a FlatBlockDevice.
func (*FlatBlockDevice) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"delete_on_termination": &hcldec.AttrSpec{Name: "delete_on_termination", Type: cty.Bool, Required: false},

View File

@ -17,10 +17,13 @@ type FlatAmiFilterOptions struct {
// FlatMapstructure returns a new FlatAmiFilterOptions.
// FlatAmiFilterOptions is an auto-generated flat version of AmiFilterOptions.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*AmiFilterOptions) FlatMapstructure() interface{} { return new(FlatAmiFilterOptions) }
func (*AmiFilterOptions) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatAmiFilterOptions)
}
// HCL2Spec returns the hcldec.Spec of a FlatAmiFilterOptions.
// This spec is used by HCL to read the fields of FlatAmiFilterOptions.
// HCL2Spec returns the hcl spec of a AmiFilterOptions.
// This spec is used by HCL to read the fields of AmiFilterOptions.
// The decoded values from this spec will then be applied to a FlatAmiFilterOptions.
func (*FlatAmiFilterOptions) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"filters": &hcldec.BlockAttrsSpec{TypeName: "filters", ElementType: cty.String, Required: false},
@ -40,14 +43,17 @@ type FlatPolicyDocument struct {
// FlatMapstructure returns a new FlatPolicyDocument.
// FlatPolicyDocument is an auto-generated flat version of PolicyDocument.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*PolicyDocument) FlatMapstructure() interface{} { return new(FlatPolicyDocument) }
func (*PolicyDocument) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatPolicyDocument)
}
// HCL2Spec returns the hcldec.Spec of a FlatPolicyDocument.
// This spec is used by HCL to read the fields of FlatPolicyDocument.
// HCL2Spec returns the hcl spec of a PolicyDocument.
// This spec is used by HCL to read the fields of PolicyDocument.
// The decoded values from this spec will then be applied to a FlatPolicyDocument.
func (*FlatPolicyDocument) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"version": &hcldec.AttrSpec{Name: "version", Type: cty.String, Required: false},
"statement": &hcldec.BlockListSpec{TypeName: "statement", Nested: &hcldec.BlockSpec{TypeName: "statement", Nested: hcldec.ObjectSpec((*FlatStatement)(nil).HCL2Spec())}},
"statement": &hcldec.BlockListSpec{TypeName: "statement", Nested: hcldec.ObjectSpec((*FlatStatement)(nil).HCL2Spec())},
}
return s
}
@ -61,12 +67,13 @@ type FlatSecurityGroupFilterOptions struct {
// FlatMapstructure returns a new FlatSecurityGroupFilterOptions.
// FlatSecurityGroupFilterOptions is an auto-generated flat version of SecurityGroupFilterOptions.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*SecurityGroupFilterOptions) FlatMapstructure() interface{} {
func (*SecurityGroupFilterOptions) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatSecurityGroupFilterOptions)
}
// HCL2Spec returns the hcldec.Spec of a FlatSecurityGroupFilterOptions.
// This spec is used by HCL to read the fields of FlatSecurityGroupFilterOptions.
// HCL2Spec returns the hcl spec of a SecurityGroupFilterOptions.
// This spec is used by HCL to read the fields of SecurityGroupFilterOptions.
// The decoded values from this spec will then be applied to a FlatSecurityGroupFilterOptions.
func (*FlatSecurityGroupFilterOptions) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"filters": &hcldec.BlockAttrsSpec{TypeName: "filters", ElementType: cty.String, Required: false},
@ -85,10 +92,13 @@ type FlatStatement struct {
// FlatMapstructure returns a new FlatStatement.
// FlatStatement is an auto-generated flat version of Statement.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*Statement) FlatMapstructure() interface{} { return new(FlatStatement) }
func (*Statement) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatStatement)
}
// HCL2Spec returns the hcldec.Spec of a FlatStatement.
// This spec is used by HCL to read the fields of FlatStatement.
// HCL2Spec returns the hcl spec of a Statement.
// This spec is used by HCL to read the fields of Statement.
// The decoded values from this spec will then be applied to a FlatStatement.
func (*FlatStatement) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"effect": &hcldec.AttrSpec{Name: "effect", Type: cty.String, Required: false},
@ -109,10 +119,13 @@ type FlatSubnetFilterOptions struct {
// FlatMapstructure returns a new FlatSubnetFilterOptions.
// FlatSubnetFilterOptions is an auto-generated flat version of SubnetFilterOptions.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*SubnetFilterOptions) FlatMapstructure() interface{} { return new(FlatSubnetFilterOptions) }
func (*SubnetFilterOptions) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatSubnetFilterOptions)
}
// HCL2Spec returns the hcldec.Spec of a FlatSubnetFilterOptions.
// This spec is used by HCL to read the fields of FlatSubnetFilterOptions.
// HCL2Spec returns the hcl spec of a SubnetFilterOptions.
// This spec is used by HCL to read the fields of SubnetFilterOptions.
// The decoded values from this spec will then be applied to a FlatSubnetFilterOptions.
func (*FlatSubnetFilterOptions) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"filters": &hcldec.BlockAttrsSpec{TypeName: "filters", ElementType: cty.String, Required: false},
@ -131,10 +144,13 @@ type FlatVpcFilterOptions struct {
// FlatMapstructure returns a new FlatVpcFilterOptions.
// FlatVpcFilterOptions is an auto-generated flat version of VpcFilterOptions.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*VpcFilterOptions) FlatMapstructure() interface{} { return new(FlatVpcFilterOptions) }
func (*VpcFilterOptions) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatVpcFilterOptions)
}
// HCL2Spec returns the hcldec.Spec of a FlatVpcFilterOptions.
// This spec is used by HCL to read the fields of FlatVpcFilterOptions.
// HCL2Spec returns the hcl spec of a VpcFilterOptions.
// This spec is used by HCL to read the fields of VpcFilterOptions.
// The decoded values from this spec will then be applied to a FlatVpcFilterOptions.
func (*FlatVpcFilterOptions) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"filters": &hcldec.BlockAttrsSpec{TypeName: "filters", ElementType: cty.String, Required: false},

View File

@ -2,11 +2,10 @@ package common
import (
"context"
"encoding/json"
"fmt"
"log"
"encoding/json"
"github.com/aws/aws-sdk-go/aws"
"github.com/aws/aws-sdk-go/service/iam"
"github.com/hashicorp/packer/common/uuid"

View File

@ -14,6 +14,7 @@ import (
"github.com/aws/aws-sdk-go/service/ec2"
"github.com/aws/aws-sdk-go/service/iam"
"github.com/hashicorp/hcl/v2/hcldec"
awscommon "github.com/hashicorp/packer/builder/amazon/common"
"github.com/hashicorp/packer/common"
"github.com/hashicorp/packer/helper/communicator"
@ -72,6 +73,8 @@ type Builder struct {
runner multistep.Runner
}
func (b *Builder) ConfigSpec() hcldec.ObjectSpec { return b.config.FlatMapstructure().HCL2Spec() }
func (b *Builder) Prepare(raws ...interface{}) ([]string, error) {
b.config.ctx.Funcs = awscommon.TemplateFuncs
err := config.Decode(&b.config, &config.DecodeOpts{

View File

@ -107,8 +107,8 @@ type FlatConfig struct {
SSHReadWriteTimeout *string `mapstructure:"ssh_read_write_timeout" cty:"ssh_read_write_timeout"`
SSHRemoteTunnels []string `mapstructure:"ssh_remote_tunnels" cty:"ssh_remote_tunnels"`
SSHLocalTunnels []string `mapstructure:"ssh_local_tunnels" cty:"ssh_local_tunnels"`
SSHPublicKey []byte `cty:"ssh_public_key"`
SSHPrivateKey []byte `cty:"ssh_private_key"`
SSHPublicKey []byte `mapstructure:"ssh_public_key" cty:"ssh_public_key"`
SSHPrivateKey []byte `mapstructure:"ssh_private_key" cty:"ssh_private_key"`
WinRMUser *string `mapstructure:"winrm_username" cty:"winrm_username"`
WinRMPassword *string `mapstructure:"winrm_password" cty:"winrm_password"`
WinRMHost *string `mapstructure:"winrm_host" cty:"winrm_host"`
@ -127,10 +127,13 @@ type FlatConfig struct {
// FlatMapstructure returns a new FlatConfig.
// FlatConfig is an auto-generated flat version of Config.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*Config) FlatMapstructure() interface{} { return new(FlatConfig) }
func (*Config) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatConfig)
}
// HCL2Spec returns the hcldec.Spec of a FlatConfig.
// This spec is used by HCL to read the fields of FlatConfig.
// HCL2Spec returns the hcl spec of a Config.
// This spec is used by HCL to read the fields of Config.
// The decoded values from this spec will then be applied to a FlatConfig.
func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"packer_build_name": &hcldec.AttrSpec{Name: "packer_build_name", Type: cty.String, Required: false},
@ -241,8 +244,8 @@ func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
"winrm_insecure": &hcldec.AttrSpec{Name: "winrm_insecure", Type: cty.Bool, Required: false},
"winrm_use_ntlm": &hcldec.AttrSpec{Name: "winrm_use_ntlm", Type: cty.Bool, Required: false},
"ssh_interface": &hcldec.AttrSpec{Name: "ssh_interface", Type: cty.String, Required: false},
"ami_block_device_mappings": &hcldec.BlockListSpec{TypeName: "ami_block_device_mappings", Nested: &hcldec.BlockSpec{TypeName: "ami_block_device_mappings", Nested: hcldec.ObjectSpec((*common.FlatBlockDevice)(nil).HCL2Spec())}},
"launch_block_device_mappings": &hcldec.BlockListSpec{TypeName: "launch_block_device_mappings", Nested: &hcldec.BlockSpec{TypeName: "launch_block_device_mappings", Nested: hcldec.ObjectSpec((*common.FlatBlockDevice)(nil).HCL2Spec())}},
"ami_block_device_mappings": &hcldec.BlockListSpec{TypeName: "ami_block_device_mappings", Nested: hcldec.ObjectSpec((*common.FlatBlockDevice)(nil).HCL2Spec())},
"launch_block_device_mappings": &hcldec.BlockListSpec{TypeName: "launch_block_device_mappings", Nested: hcldec.ObjectSpec((*common.FlatBlockDevice)(nil).HCL2Spec())},
"run_volume_tags": &hcldec.BlockAttrsSpec{TypeName: "common.TagMap", ElementType: cty.String, Required: false},
"no_ephemeral": &hcldec.AttrSpec{Name: "no_ephemeral", Type: cty.Bool, Required: false},
}

View File

@ -1,4 +1,5 @@
//go:generate struct-markdown
//go:generate mapstructure-to-hcl2 -type Config,RootBlockDevice,BlockDevice
// The ebssurrogate package contains a packer.Builder implementation that
// builds a new EBS-backed AMI using an ephemeral instance.
@ -11,6 +12,7 @@ import (
"github.com/aws/aws-sdk-go/service/ec2"
"github.com/aws/aws-sdk-go/service/iam"
"github.com/hashicorp/hcl/v2/hcldec"
awscommon "github.com/hashicorp/packer/builder/amazon/common"
"github.com/hashicorp/packer/common"
"github.com/hashicorp/packer/helper/communicator"
@ -70,6 +72,8 @@ type Builder struct {
runner multistep.Runner
}
func (b *Builder) ConfigSpec() hcldec.ObjectSpec { return b.config.FlatMapstructure().HCL2Spec() }
func (b *Builder) Prepare(raws ...interface{}) ([]string, error) {
b.config.ctx.Funcs = awscommon.TemplateFuncs
err := config.Decode(&b.config, &config.DecodeOpts{

View File

@ -0,0 +1,331 @@
// Code generated by "mapstructure-to-hcl2 -type Config,RootBlockDevice,BlockDevice"; DO NOT EDIT.
package ebssurrogate
import (
"github.com/hashicorp/hcl/v2/hcldec"
"github.com/hashicorp/packer/builder/amazon/common"
"github.com/zclconf/go-cty/cty"
)
// FlatBlockDevice is an auto-generated flat version of BlockDevice.
// Where the contents of a field with a `mapstructure:,squash` tag are bubbled up.
type FlatBlockDevice struct {
DeleteOnTermination *bool `mapstructure:"delete_on_termination" required:"false" cty:"delete_on_termination"`
DeviceName *string `mapstructure:"device_name" required:"false" cty:"device_name"`
Encrypted *bool `mapstructure:"encrypted" required:"false" cty:"encrypted"`
IOPS *int64 `mapstructure:"iops" required:"false" cty:"iops"`
NoDevice *bool `mapstructure:"no_device" required:"false" cty:"no_device"`
SnapshotId *string `mapstructure:"snapshot_id" required:"false" cty:"snapshot_id"`
VirtualName *string `mapstructure:"virtual_name" required:"false" cty:"virtual_name"`
VolumeType *string `mapstructure:"volume_type" required:"false" cty:"volume_type"`
VolumeSize *int64 `mapstructure:"volume_size" required:"false" cty:"volume_size"`
KmsKeyId *string `mapstructure:"kms_key_id" required:"false" cty:"kms_key_id"`
OmitFromArtifact *bool `mapstructure:"omit_from_artifact" cty:"omit_from_artifact"`
}
// FlatMapstructure returns a new FlatBlockDevice.
// FlatBlockDevice is an auto-generated flat version of BlockDevice.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*BlockDevice) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatBlockDevice)
}
// HCL2Spec returns the hcl spec of a BlockDevice.
// This spec is used by HCL to read the fields of BlockDevice.
// The decoded values from this spec will then be applied to a FlatBlockDevice.
func (*FlatBlockDevice) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"delete_on_termination": &hcldec.AttrSpec{Name: "delete_on_termination", Type: cty.Bool, Required: false},
"device_name": &hcldec.AttrSpec{Name: "device_name", Type: cty.String, Required: false},
"encrypted": &hcldec.AttrSpec{Name: "encrypted", Type: cty.Bool, Required: false},
"iops": &hcldec.AttrSpec{Name: "iops", Type: cty.Number, Required: false},
"no_device": &hcldec.AttrSpec{Name: "no_device", Type: cty.Bool, Required: false},
"snapshot_id": &hcldec.AttrSpec{Name: "snapshot_id", Type: cty.String, Required: false},
"virtual_name": &hcldec.AttrSpec{Name: "virtual_name", Type: cty.String, Required: false},
"volume_type": &hcldec.AttrSpec{Name: "volume_type", Type: cty.String, Required: false},
"volume_size": &hcldec.AttrSpec{Name: "volume_size", Type: cty.Number, Required: false},
"kms_key_id": &hcldec.AttrSpec{Name: "kms_key_id", Type: cty.String, Required: false},
"omit_from_artifact": &hcldec.AttrSpec{Name: "omit_from_artifact", Type: cty.Bool, Required: false},
}
return s
}
// FlatConfig is an auto-generated flat version of Config.
// Where the contents of a field with a `mapstructure:,squash` tag are bubbled up.
type FlatConfig struct {
PackerBuildName *string `mapstructure:"packer_build_name" cty:"packer_build_name"`
PackerBuilderType *string `mapstructure:"packer_builder_type" cty:"packer_builder_type"`
PackerDebug *bool `mapstructure:"packer_debug" cty:"packer_debug"`
PackerForce *bool `mapstructure:"packer_force" cty:"packer_force"`
PackerOnError *string `mapstructure:"packer_on_error" cty:"packer_on_error"`
PackerUserVars map[string]string `mapstructure:"packer_user_variables" cty:"packer_user_variables"`
PackerSensitiveVars []string `mapstructure:"packer_sensitive_variables" cty:"packer_sensitive_variables"`
AccessKey *string `mapstructure:"access_key" required:"true" cty:"access_key"`
CustomEndpointEc2 *string `mapstructure:"custom_endpoint_ec2" required:"false" cty:"custom_endpoint_ec2"`
DecodeAuthZMessages *bool `mapstructure:"decode_authorization_messages" required:"false" cty:"decode_authorization_messages"`
InsecureSkipTLSVerify *bool `mapstructure:"insecure_skip_tls_verify" required:"false" cty:"insecure_skip_tls_verify"`
MFACode *string `mapstructure:"mfa_code" required:"false" cty:"mfa_code"`
ProfileName *string `mapstructure:"profile" required:"false" cty:"profile"`
RawRegion *string `mapstructure:"region" required:"true" cty:"region"`
SecretKey *string `mapstructure:"secret_key" required:"true" cty:"secret_key"`
SkipValidation *bool `mapstructure:"skip_region_validation" required:"false" cty:"skip_region_validation"`
SkipMetadataApiCheck *bool `mapstructure:"skip_metadata_api_check" cty:"skip_metadata_api_check"`
Token *string `mapstructure:"token" required:"false" cty:"token"`
VaultAWSEngine *common.FlatVaultAWSEngineOptions `mapstructure:"vault_aws_engine" required:"false" cty:"vault_aws_engine"`
AssociatePublicIpAddress *bool `mapstructure:"associate_public_ip_address" required:"false" cty:"associate_public_ip_address"`
AvailabilityZone *string `mapstructure:"availability_zone" required:"false" cty:"availability_zone"`
BlockDurationMinutes *int64 `mapstructure:"block_duration_minutes" required:"false" cty:"block_duration_minutes"`
DisableStopInstance *bool `mapstructure:"disable_stop_instance" required:"false" cty:"disable_stop_instance"`
EbsOptimized *bool `mapstructure:"ebs_optimized" required:"false" cty:"ebs_optimized"`
EnableT2Unlimited *bool `mapstructure:"enable_t2_unlimited" required:"false" cty:"enable_t2_unlimited"`
IamInstanceProfile *string `mapstructure:"iam_instance_profile" required:"false" cty:"iam_instance_profile"`
SkipProfileValidation *bool `mapstructure:"skip_profile_validation" required:"false" cty:"skip_profile_validation"`
TemporaryIamInstanceProfilePolicyDocument *common.FlatPolicyDocument `mapstructure:"temporary_iam_instance_profile_policy_document" required:"false" cty:"temporary_iam_instance_profile_policy_document"`
InstanceInitiatedShutdownBehavior *string `mapstructure:"shutdown_behavior" required:"false" cty:"shutdown_behavior"`
InstanceType *string `mapstructure:"instance_type" required:"true" cty:"instance_type"`
SecurityGroupFilter *common.FlatSecurityGroupFilterOptions `mapstructure:"security_group_filter" required:"false" cty:"security_group_filter"`
RunTags map[string]string `mapstructure:"run_tags" required:"false" cty:"run_tags"`
SecurityGroupId *string `mapstructure:"security_group_id" required:"false" cty:"security_group_id"`
SecurityGroupIds []string `mapstructure:"security_group_ids" required:"false" cty:"security_group_ids"`
SourceAmi *string `mapstructure:"source_ami" required:"true" cty:"source_ami"`
SourceAmiFilter *common.FlatAmiFilterOptions `mapstructure:"source_ami_filter" required:"false" cty:"source_ami_filter"`
SpotInstanceTypes []string `mapstructure:"spot_instance_types" required:"false" cty:"spot_instance_types"`
SpotPrice *string `mapstructure:"spot_price" required:"false" cty:"spot_price"`
SpotPriceAutoProduct *string `mapstructure:"spot_price_auto_product" required:"false" cty:"spot_price_auto_product"`
SpotTags map[string]string `mapstructure:"spot_tags" required:"false" cty:"spot_tags"`
SubnetFilter *common.FlatSubnetFilterOptions `mapstructure:"subnet_filter" required:"false" cty:"subnet_filter"`
SubnetId *string `mapstructure:"subnet_id" required:"false" cty:"subnet_id"`
TemporaryKeyPairName *string `mapstructure:"temporary_key_pair_name" required:"false" cty:"temporary_key_pair_name"`
TemporarySGSourceCidrs []string `mapstructure:"temporary_security_group_source_cidrs" required:"false" cty:"temporary_security_group_source_cidrs"`
UserData *string `mapstructure:"user_data" required:"false" cty:"user_data"`
UserDataFile *string `mapstructure:"user_data_file" required:"false" cty:"user_data_file"`
VpcFilter *common.FlatVpcFilterOptions `mapstructure:"vpc_filter" required:"false" cty:"vpc_filter"`
VpcId *string `mapstructure:"vpc_id" required:"false" cty:"vpc_id"`
WindowsPasswordTimeout *string `mapstructure:"windows_password_timeout" required:"false" cty:"windows_password_timeout"`
Type *string `mapstructure:"communicator" cty:"communicator"`
PauseBeforeConnect *string `mapstructure:"pause_before_connecting" cty:"pause_before_connecting"`
SSHHost *string `mapstructure:"ssh_host" cty:"ssh_host"`
SSHPort *int `mapstructure:"ssh_port" cty:"ssh_port"`
SSHUsername *string `mapstructure:"ssh_username" cty:"ssh_username"`
SSHPassword *string `mapstructure:"ssh_password" cty:"ssh_password"`
SSHKeyPairName *string `mapstructure:"ssh_keypair_name" cty:"ssh_keypair_name"`
SSHClearAuthorizedKeys *bool `mapstructure:"ssh_clear_authorized_keys" cty:"ssh_clear_authorized_keys"`
SSHPrivateKeyFile *string `mapstructure:"ssh_private_key_file" cty:"ssh_private_key_file"`
SSHPty *bool `mapstructure:"ssh_pty" cty:"ssh_pty"`
SSHTimeout *string `mapstructure:"ssh_timeout" cty:"ssh_timeout"`
SSHAgentAuth *bool `mapstructure:"ssh_agent_auth" cty:"ssh_agent_auth"`
SSHDisableAgentForwarding *bool `mapstructure:"ssh_disable_agent_forwarding" cty:"ssh_disable_agent_forwarding"`
SSHHandshakeAttempts *int `mapstructure:"ssh_handshake_attempts" cty:"ssh_handshake_attempts"`
SSHBastionHost *string `mapstructure:"ssh_bastion_host" cty:"ssh_bastion_host"`
SSHBastionPort *int `mapstructure:"ssh_bastion_port" cty:"ssh_bastion_port"`
SSHBastionAgentAuth *bool `mapstructure:"ssh_bastion_agent_auth" cty:"ssh_bastion_agent_auth"`
SSHBastionUsername *string `mapstructure:"ssh_bastion_username" cty:"ssh_bastion_username"`
SSHBastionPassword *string `mapstructure:"ssh_bastion_password" cty:"ssh_bastion_password"`
SSHBastionPrivateKeyFile *string `mapstructure:"ssh_bastion_private_key_file" cty:"ssh_bastion_private_key_file"`
SSHFileTransferMethod *string `mapstructure:"ssh_file_transfer_method" cty:"ssh_file_transfer_method"`
SSHProxyHost *string `mapstructure:"ssh_proxy_host" cty:"ssh_proxy_host"`
SSHProxyPort *int `mapstructure:"ssh_proxy_port" cty:"ssh_proxy_port"`
SSHProxyUsername *string `mapstructure:"ssh_proxy_username" cty:"ssh_proxy_username"`
SSHProxyPassword *string `mapstructure:"ssh_proxy_password" cty:"ssh_proxy_password"`
SSHKeepAliveInterval *string `mapstructure:"ssh_keep_alive_interval" cty:"ssh_keep_alive_interval"`
SSHReadWriteTimeout *string `mapstructure:"ssh_read_write_timeout" cty:"ssh_read_write_timeout"`
SSHRemoteTunnels []string `mapstructure:"ssh_remote_tunnels" cty:"ssh_remote_tunnels"`
SSHLocalTunnels []string `mapstructure:"ssh_local_tunnels" cty:"ssh_local_tunnels"`
SSHPublicKey []byte `mapstructure:"ssh_public_key" cty:"ssh_public_key"`
SSHPrivateKey []byte `mapstructure:"ssh_private_key" cty:"ssh_private_key"`
WinRMUser *string `mapstructure:"winrm_username" cty:"winrm_username"`
WinRMPassword *string `mapstructure:"winrm_password" cty:"winrm_password"`
WinRMHost *string `mapstructure:"winrm_host" cty:"winrm_host"`
WinRMPort *int `mapstructure:"winrm_port" cty:"winrm_port"`
WinRMTimeout *string `mapstructure:"winrm_timeout" cty:"winrm_timeout"`
WinRMUseSSL *bool `mapstructure:"winrm_use_ssl" cty:"winrm_use_ssl"`
WinRMInsecure *bool `mapstructure:"winrm_insecure" cty:"winrm_insecure"`
WinRMUseNTLM *bool `mapstructure:"winrm_use_ntlm" cty:"winrm_use_ntlm"`
SSHInterface *string `mapstructure:"ssh_interface" cty:"ssh_interface"`
AMIName *string `mapstructure:"ami_name" required:"true" cty:"ami_name"`
AMIDescription *string `mapstructure:"ami_description" required:"false" cty:"ami_description"`
AMIVirtType *string `mapstructure:"ami_virtualization_type" required:"false" cty:"ami_virtualization_type"`
AMIUsers []string `mapstructure:"ami_users" required:"false" cty:"ami_users"`
AMIGroups []string `mapstructure:"ami_groups" required:"false" cty:"ami_groups"`
AMIProductCodes []string `mapstructure:"ami_product_codes" required:"false" cty:"ami_product_codes"`
AMIRegions []string `mapstructure:"ami_regions" required:"false" cty:"ami_regions"`
AMITags common.TagMap `mapstructure:"tags" required:"false" cty:"tags"`
AMIENASupport *bool `mapstructure:"ena_support" required:"false" cty:"ena_support"`
AMISriovNetSupport *bool `mapstructure:"sriov_support" required:"false" cty:"sriov_support"`
AMIForceDeregister *bool `mapstructure:"force_deregister" required:"false" cty:"force_deregister"`
AMIForceDeleteSnapshot *bool `mapstructure:"force_delete_snapshot" required:"false" cty:"force_delete_snapshot"`
AMIEncryptBootVolume *bool `mapstructure:"encrypt_boot" required:"false" cty:"encrypt_boot"`
AMIKmsKeyId *string `mapstructure:"kms_key_id" required:"false" cty:"kms_key_id"`
AMIRegionKMSKeyIDs map[string]string `mapstructure:"region_kms_key_ids" required:"false" cty:"region_kms_key_ids"`
AMISkipBuildRegion *bool `mapstructure:"skip_save_build_region" cty:"skip_save_build_region"`
SnapshotTags common.TagMap `mapstructure:"snapshot_tags" required:"false" cty:"snapshot_tags"`
SnapshotUsers []string `mapstructure:"snapshot_users" required:"false" cty:"snapshot_users"`
SnapshotGroups []string `mapstructure:"snapshot_groups" required:"false" cty:"snapshot_groups"`
AMIMappings []common.FlatBlockDevice `mapstructure:"ami_block_device_mappings" required:"false" cty:"ami_block_device_mappings"`
LaunchMappings []FlatBlockDevice `mapstructure:"launch_block_device_mappings" required:"false" cty:"launch_block_device_mappings"`
RootDevice *FlatRootBlockDevice `mapstructure:"ami_root_device" required:"true" cty:"ami_root_device"`
VolumeRunTags common.TagMap `mapstructure:"run_volume_tags" cty:"run_volume_tags"`
Architecture *string `mapstructure:"ami_architecture" required:"false" cty:"ami_architecture"`
}
// FlatMapstructure returns a new FlatConfig.
// FlatConfig is an auto-generated flat version of Config.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*Config) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatConfig)
}
// HCL2Spec returns the hcl spec of a Config.
// This spec is used by HCL to read the fields of Config.
// The decoded values from this spec will then be applied to a FlatConfig.
func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"packer_build_name": &hcldec.AttrSpec{Name: "packer_build_name", Type: cty.String, Required: false},
"packer_builder_type": &hcldec.AttrSpec{Name: "packer_builder_type", Type: cty.String, Required: false},
"packer_debug": &hcldec.AttrSpec{Name: "packer_debug", Type: cty.Bool, Required: false},
"packer_force": &hcldec.AttrSpec{Name: "packer_force", Type: cty.Bool, Required: false},
"packer_on_error": &hcldec.AttrSpec{Name: "packer_on_error", Type: cty.String, Required: false},
"packer_user_variables": &hcldec.BlockAttrsSpec{TypeName: "packer_user_variables", ElementType: cty.String, Required: false},
"packer_sensitive_variables": &hcldec.AttrSpec{Name: "packer_sensitive_variables", Type: cty.List(cty.String), Required: false},
"access_key": &hcldec.AttrSpec{Name: "access_key", Type: cty.String, Required: false},
"custom_endpoint_ec2": &hcldec.AttrSpec{Name: "custom_endpoint_ec2", Type: cty.String, Required: false},
"decode_authorization_messages": &hcldec.AttrSpec{Name: "decode_authorization_messages", Type: cty.Bool, Required: false},
"insecure_skip_tls_verify": &hcldec.AttrSpec{Name: "insecure_skip_tls_verify", Type: cty.Bool, Required: false},
"mfa_code": &hcldec.AttrSpec{Name: "mfa_code", Type: cty.String, Required: false},
"profile": &hcldec.AttrSpec{Name: "profile", Type: cty.String, Required: false},
"region": &hcldec.AttrSpec{Name: "region", Type: cty.String, Required: false},
"secret_key": &hcldec.AttrSpec{Name: "secret_key", Type: cty.String, Required: false},
"skip_region_validation": &hcldec.AttrSpec{Name: "skip_region_validation", Type: cty.Bool, Required: false},
"skip_metadata_api_check": &hcldec.AttrSpec{Name: "skip_metadata_api_check", Type: cty.Bool, Required: false},
"token": &hcldec.AttrSpec{Name: "token", Type: cty.String, Required: false},
"vault_aws_engine": &hcldec.BlockSpec{TypeName: "vault_aws_engine", Nested: hcldec.ObjectSpec((*common.FlatVaultAWSEngineOptions)(nil).HCL2Spec())},
"associate_public_ip_address": &hcldec.AttrSpec{Name: "associate_public_ip_address", Type: cty.Bool, Required: false},
"availability_zone": &hcldec.AttrSpec{Name: "availability_zone", Type: cty.String, Required: false},
"block_duration_minutes": &hcldec.AttrSpec{Name: "block_duration_minutes", Type: cty.Number, Required: false},
"disable_stop_instance": &hcldec.AttrSpec{Name: "disable_stop_instance", Type: cty.Bool, Required: false},
"ebs_optimized": &hcldec.AttrSpec{Name: "ebs_optimized", Type: cty.Bool, Required: false},
"enable_t2_unlimited": &hcldec.AttrSpec{Name: "enable_t2_unlimited", Type: cty.Bool, Required: false},
"iam_instance_profile": &hcldec.AttrSpec{Name: "iam_instance_profile", Type: cty.String, Required: false},
"skip_profile_validation": &hcldec.AttrSpec{Name: "skip_profile_validation", Type: cty.Bool, Required: false},
"temporary_iam_instance_profile_policy_document": &hcldec.BlockSpec{TypeName: "temporary_iam_instance_profile_policy_document", Nested: hcldec.ObjectSpec((*common.FlatPolicyDocument)(nil).HCL2Spec())},
"shutdown_behavior": &hcldec.AttrSpec{Name: "shutdown_behavior", Type: cty.String, Required: false},
"instance_type": &hcldec.AttrSpec{Name: "instance_type", Type: cty.String, Required: false},
"security_group_filter": &hcldec.BlockSpec{TypeName: "security_group_filter", Nested: hcldec.ObjectSpec((*common.FlatSecurityGroupFilterOptions)(nil).HCL2Spec())},
"run_tags": &hcldec.BlockAttrsSpec{TypeName: "run_tags", ElementType: cty.String, Required: false},
"security_group_id": &hcldec.AttrSpec{Name: "security_group_id", Type: cty.String, Required: false},
"security_group_ids": &hcldec.AttrSpec{Name: "security_group_ids", Type: cty.List(cty.String), Required: false},
"source_ami": &hcldec.AttrSpec{Name: "source_ami", Type: cty.String, Required: false},
"source_ami_filter": &hcldec.BlockSpec{TypeName: "source_ami_filter", Nested: hcldec.ObjectSpec((*common.FlatAmiFilterOptions)(nil).HCL2Spec())},
"spot_instance_types": &hcldec.AttrSpec{Name: "spot_instance_types", Type: cty.List(cty.String), Required: false},
"spot_price": &hcldec.AttrSpec{Name: "spot_price", Type: cty.String, Required: false},
"spot_price_auto_product": &hcldec.AttrSpec{Name: "spot_price_auto_product", Type: cty.String, Required: false},
"spot_tags": &hcldec.BlockAttrsSpec{TypeName: "spot_tags", ElementType: cty.String, Required: false},
"subnet_filter": &hcldec.BlockSpec{TypeName: "subnet_filter", Nested: hcldec.ObjectSpec((*common.FlatSubnetFilterOptions)(nil).HCL2Spec())},
"subnet_id": &hcldec.AttrSpec{Name: "subnet_id", Type: cty.String, Required: false},
"temporary_key_pair_name": &hcldec.AttrSpec{Name: "temporary_key_pair_name", Type: cty.String, Required: false},
"temporary_security_group_source_cidrs": &hcldec.AttrSpec{Name: "temporary_security_group_source_cidrs", Type: cty.List(cty.String), Required: false},
"user_data": &hcldec.AttrSpec{Name: "user_data", Type: cty.String, Required: false},
"user_data_file": &hcldec.AttrSpec{Name: "user_data_file", Type: cty.String, Required: false},
"vpc_filter": &hcldec.BlockSpec{TypeName: "vpc_filter", Nested: hcldec.ObjectSpec((*common.FlatVpcFilterOptions)(nil).HCL2Spec())},
"vpc_id": &hcldec.AttrSpec{Name: "vpc_id", Type: cty.String, Required: false},
"windows_password_timeout": &hcldec.AttrSpec{Name: "windows_password_timeout", Type: cty.String, Required: false},
"communicator": &hcldec.AttrSpec{Name: "communicator", Type: cty.String, Required: false},
"pause_before_connecting": &hcldec.AttrSpec{Name: "pause_before_connecting", Type: cty.String, Required: false},
"ssh_host": &hcldec.AttrSpec{Name: "ssh_host", Type: cty.String, Required: false},
"ssh_port": &hcldec.AttrSpec{Name: "ssh_port", Type: cty.Number, Required: false},
"ssh_username": &hcldec.AttrSpec{Name: "ssh_username", Type: cty.String, Required: false},
"ssh_password": &hcldec.AttrSpec{Name: "ssh_password", Type: cty.String, Required: false},
"ssh_keypair_name": &hcldec.AttrSpec{Name: "ssh_keypair_name", Type: cty.String, Required: false},
"ssh_clear_authorized_keys": &hcldec.AttrSpec{Name: "ssh_clear_authorized_keys", Type: cty.Bool, Required: false},
"ssh_private_key_file": &hcldec.AttrSpec{Name: "ssh_private_key_file", Type: cty.String, Required: false},
"ssh_pty": &hcldec.AttrSpec{Name: "ssh_pty", Type: cty.Bool, Required: false},
"ssh_timeout": &hcldec.AttrSpec{Name: "ssh_timeout", Type: cty.String, Required: false},
"ssh_agent_auth": &hcldec.AttrSpec{Name: "ssh_agent_auth", Type: cty.Bool, Required: false},
"ssh_disable_agent_forwarding": &hcldec.AttrSpec{Name: "ssh_disable_agent_forwarding", Type: cty.Bool, Required: false},
"ssh_handshake_attempts": &hcldec.AttrSpec{Name: "ssh_handshake_attempts", Type: cty.Number, Required: false},
"ssh_bastion_host": &hcldec.AttrSpec{Name: "ssh_bastion_host", Type: cty.String, Required: false},
"ssh_bastion_port": &hcldec.AttrSpec{Name: "ssh_bastion_port", Type: cty.Number, Required: false},
"ssh_bastion_agent_auth": &hcldec.AttrSpec{Name: "ssh_bastion_agent_auth", Type: cty.Bool, Required: false},
"ssh_bastion_username": &hcldec.AttrSpec{Name: "ssh_bastion_username", Type: cty.String, Required: false},
"ssh_bastion_password": &hcldec.AttrSpec{Name: "ssh_bastion_password", Type: cty.String, Required: false},
"ssh_bastion_private_key_file": &hcldec.AttrSpec{Name: "ssh_bastion_private_key_file", Type: cty.String, Required: false},
"ssh_file_transfer_method": &hcldec.AttrSpec{Name: "ssh_file_transfer_method", Type: cty.String, Required: false},
"ssh_proxy_host": &hcldec.AttrSpec{Name: "ssh_proxy_host", Type: cty.String, Required: false},
"ssh_proxy_port": &hcldec.AttrSpec{Name: "ssh_proxy_port", Type: cty.Number, Required: false},
"ssh_proxy_username": &hcldec.AttrSpec{Name: "ssh_proxy_username", Type: cty.String, Required: false},
"ssh_proxy_password": &hcldec.AttrSpec{Name: "ssh_proxy_password", Type: cty.String, Required: false},
"ssh_keep_alive_interval": &hcldec.AttrSpec{Name: "ssh_keep_alive_interval", Type: cty.String, Required: false},
"ssh_read_write_timeout": &hcldec.AttrSpec{Name: "ssh_read_write_timeout", Type: cty.String, Required: false},
"ssh_remote_tunnels": &hcldec.AttrSpec{Name: "ssh_remote_tunnels", Type: cty.List(cty.String), Required: false},
"ssh_local_tunnels": &hcldec.AttrSpec{Name: "ssh_local_tunnels", Type: cty.List(cty.String), Required: false},
"ssh_public_key": &hcldec.AttrSpec{Name: "ssh_public_key", Type: cty.List(cty.Number), Required: false},
"ssh_private_key": &hcldec.AttrSpec{Name: "ssh_private_key", Type: cty.List(cty.Number), Required: false},
"winrm_username": &hcldec.AttrSpec{Name: "winrm_username", Type: cty.String, Required: false},
"winrm_password": &hcldec.AttrSpec{Name: "winrm_password", Type: cty.String, Required: false},
"winrm_host": &hcldec.AttrSpec{Name: "winrm_host", Type: cty.String, Required: false},
"winrm_port": &hcldec.AttrSpec{Name: "winrm_port", Type: cty.Number, Required: false},
"winrm_timeout": &hcldec.AttrSpec{Name: "winrm_timeout", Type: cty.String, Required: false},
"winrm_use_ssl": &hcldec.AttrSpec{Name: "winrm_use_ssl", Type: cty.Bool, Required: false},
"winrm_insecure": &hcldec.AttrSpec{Name: "winrm_insecure", Type: cty.Bool, Required: false},
"winrm_use_ntlm": &hcldec.AttrSpec{Name: "winrm_use_ntlm", Type: cty.Bool, Required: false},
"ssh_interface": &hcldec.AttrSpec{Name: "ssh_interface", Type: cty.String, Required: false},
"ami_name": &hcldec.AttrSpec{Name: "ami_name", Type: cty.String, Required: false},
"ami_description": &hcldec.AttrSpec{Name: "ami_description", Type: cty.String, Required: false},
"ami_virtualization_type": &hcldec.AttrSpec{Name: "ami_virtualization_type", Type: cty.String, Required: false},
"ami_users": &hcldec.AttrSpec{Name: "ami_users", Type: cty.List(cty.String), Required: false},
"ami_groups": &hcldec.AttrSpec{Name: "ami_groups", Type: cty.List(cty.String), Required: false},
"ami_product_codes": &hcldec.AttrSpec{Name: "ami_product_codes", Type: cty.List(cty.String), Required: false},
"ami_regions": &hcldec.AttrSpec{Name: "ami_regions", Type: cty.List(cty.String), Required: false},
"tags": &hcldec.BlockAttrsSpec{TypeName: "common.TagMap", ElementType: cty.String, Required: false},
"ena_support": &hcldec.AttrSpec{Name: "ena_support", Type: cty.Bool, Required: false},
"sriov_support": &hcldec.AttrSpec{Name: "sriov_support", Type: cty.Bool, Required: false},
"force_deregister": &hcldec.AttrSpec{Name: "force_deregister", Type: cty.Bool, Required: false},
"force_delete_snapshot": &hcldec.AttrSpec{Name: "force_delete_snapshot", Type: cty.Bool, Required: false},
"encrypt_boot": &hcldec.AttrSpec{Name: "encrypt_boot", Type: cty.Bool, Required: false},
"kms_key_id": &hcldec.AttrSpec{Name: "kms_key_id", Type: cty.String, Required: false},
"region_kms_key_ids": &hcldec.BlockAttrsSpec{TypeName: "region_kms_key_ids", ElementType: cty.String, Required: false},
"skip_save_build_region": &hcldec.AttrSpec{Name: "skip_save_build_region", Type: cty.Bool, Required: false},
"snapshot_tags": &hcldec.BlockAttrsSpec{TypeName: "common.TagMap", ElementType: cty.String, Required: false},
"snapshot_users": &hcldec.AttrSpec{Name: "snapshot_users", Type: cty.List(cty.String), Required: false},
"snapshot_groups": &hcldec.AttrSpec{Name: "snapshot_groups", Type: cty.List(cty.String), Required: false},
"ami_block_device_mappings": &hcldec.BlockListSpec{TypeName: "ami_block_device_mappings", Nested: hcldec.ObjectSpec((*common.FlatBlockDevice)(nil).HCL2Spec())},
"launch_block_device_mappings": &hcldec.BlockListSpec{TypeName: "launch_block_device_mappings", Nested: hcldec.ObjectSpec((*FlatBlockDevice)(nil).HCL2Spec())},
"ami_root_device": &hcldec.BlockSpec{TypeName: "ami_root_device", Nested: hcldec.ObjectSpec((*FlatRootBlockDevice)(nil).HCL2Spec())},
"run_volume_tags": &hcldec.BlockAttrsSpec{TypeName: "common.TagMap", ElementType: cty.String, Required: false},
"ami_architecture": &hcldec.AttrSpec{Name: "ami_architecture", Type: cty.String, Required: false},
}
return s
}
// FlatRootBlockDevice is an auto-generated flat version of RootBlockDevice.
// Where the contents of a field with a `mapstructure:,squash` tag are bubbled up.
type FlatRootBlockDevice struct {
SourceDeviceName *string `mapstructure:"source_device_name" cty:"source_device_name"`
DeviceName *string `mapstructure:"device_name" required:"false" cty:"device_name"`
DeleteOnTermination *bool `mapstructure:"delete_on_termination" required:"false" cty:"delete_on_termination"`
IOPS *int64 `mapstructure:"iops" required:"false" cty:"iops"`
VolumeType *string `mapstructure:"volume_type" required:"false" cty:"volume_type"`
VolumeSize *int64 `mapstructure:"volume_size" required:"false" cty:"volume_size"`
}
// FlatMapstructure returns a new FlatRootBlockDevice.
// FlatRootBlockDevice is an auto-generated flat version of RootBlockDevice.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*RootBlockDevice) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatRootBlockDevice)
}
// HCL2Spec returns the hcl spec of a RootBlockDevice.
// This spec is used by HCL to read the fields of RootBlockDevice.
// The decoded values from this spec will then be applied to a FlatRootBlockDevice.
func (*FlatRootBlockDevice) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"source_device_name": &hcldec.AttrSpec{Name: "source_device_name", Type: cty.String, Required: false},
"device_name": &hcldec.AttrSpec{Name: "device_name", Type: cty.String, Required: false},
"delete_on_termination": &hcldec.AttrSpec{Name: "delete_on_termination", Type: cty.Bool, Required: false},
"iops": &hcldec.AttrSpec{Name: "iops", Type: cty.Number, Required: false},
"volume_type": &hcldec.AttrSpec{Name: "volume_type", Type: cty.String, Required: false},
"volume_size": &hcldec.AttrSpec{Name: "volume_size", Type: cty.Number, Required: false},
}
return s
}

View File

@ -1,4 +1,5 @@
//go:generate struct-markdown
//go:generate mapstructure-to-hcl2 -type Config,BlockDevice
// The ebsvolume package contains a packer.Builder implementation that builds
// EBS volumes for Amazon EC2 using an ephemeral instance,
@ -10,6 +11,7 @@ import (
"github.com/aws/aws-sdk-go/service/ec2"
"github.com/aws/aws-sdk-go/service/iam"
"github.com/hashicorp/hcl/v2/hcldec"
awscommon "github.com/hashicorp/packer/builder/amazon/common"
"github.com/hashicorp/packer/common"
"github.com/hashicorp/packer/helper/communicator"
@ -79,6 +81,8 @@ type EngineVarsTemplate struct {
SourceAMI string
}
func (b *Builder) ConfigSpec() hcldec.ObjectSpec { return b.config.FlatMapstructure().HCL2Spec() }
func (b *Builder) Prepare(raws ...interface{}) ([]string, error) {
b.config.ctx.Funcs = awscommon.TemplateFuncs
// Create passthrough for {{ .BuildRegion }} and {{ .SourceAMI }} variables

View File

@ -0,0 +1,258 @@
// Code generated by "mapstructure-to-hcl2 -type Config,BlockDevice"; DO NOT EDIT.
package ebsvolume
import (
"github.com/hashicorp/hcl/v2/hcldec"
"github.com/hashicorp/packer/builder/amazon/common"
"github.com/zclconf/go-cty/cty"
)
// FlatBlockDevice is an auto-generated flat version of BlockDevice.
// Where the contents of a field with a `mapstructure:,squash` tag are bubbled up.
type FlatBlockDevice struct {
DeleteOnTermination *bool `mapstructure:"delete_on_termination" required:"false" cty:"delete_on_termination"`
DeviceName *string `mapstructure:"device_name" required:"false" cty:"device_name"`
Encrypted *bool `mapstructure:"encrypted" required:"false" cty:"encrypted"`
IOPS *int64 `mapstructure:"iops" required:"false" cty:"iops"`
NoDevice *bool `mapstructure:"no_device" required:"false" cty:"no_device"`
SnapshotId *string `mapstructure:"snapshot_id" required:"false" cty:"snapshot_id"`
VirtualName *string `mapstructure:"virtual_name" required:"false" cty:"virtual_name"`
VolumeType *string `mapstructure:"volume_type" required:"false" cty:"volume_type"`
VolumeSize *int64 `mapstructure:"volume_size" required:"false" cty:"volume_size"`
KmsKeyId *string `mapstructure:"kms_key_id" required:"false" cty:"kms_key_id"`
Tags common.TagMap `mapstructure:"tags" required:"false" cty:"tags"`
}
// FlatMapstructure returns a new FlatBlockDevice.
// FlatBlockDevice is an auto-generated flat version of BlockDevice.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*BlockDevice) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatBlockDevice)
}
// HCL2Spec returns the hcl spec of a BlockDevice.
// This spec is used by HCL to read the fields of BlockDevice.
// The decoded values from this spec will then be applied to a FlatBlockDevice.
func (*FlatBlockDevice) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"delete_on_termination": &hcldec.AttrSpec{Name: "delete_on_termination", Type: cty.Bool, Required: false},
"device_name": &hcldec.AttrSpec{Name: "device_name", Type: cty.String, Required: false},
"encrypted": &hcldec.AttrSpec{Name: "encrypted", Type: cty.Bool, Required: false},
"iops": &hcldec.AttrSpec{Name: "iops", Type: cty.Number, Required: false},
"no_device": &hcldec.AttrSpec{Name: "no_device", Type: cty.Bool, Required: false},
"snapshot_id": &hcldec.AttrSpec{Name: "snapshot_id", Type: cty.String, Required: false},
"virtual_name": &hcldec.AttrSpec{Name: "virtual_name", Type: cty.String, Required: false},
"volume_type": &hcldec.AttrSpec{Name: "volume_type", Type: cty.String, Required: false},
"volume_size": &hcldec.AttrSpec{Name: "volume_size", Type: cty.Number, Required: false},
"kms_key_id": &hcldec.AttrSpec{Name: "kms_key_id", Type: cty.String, Required: false},
"tags": &hcldec.BlockAttrsSpec{TypeName: "common.TagMap", ElementType: cty.String, Required: false},
}
return s
}
// FlatConfig is an auto-generated flat version of Config.
// Where the contents of a field with a `mapstructure:,squash` tag are bubbled up.
type FlatConfig struct {
PackerBuildName *string `mapstructure:"packer_build_name" cty:"packer_build_name"`
PackerBuilderType *string `mapstructure:"packer_builder_type" cty:"packer_builder_type"`
PackerDebug *bool `mapstructure:"packer_debug" cty:"packer_debug"`
PackerForce *bool `mapstructure:"packer_force" cty:"packer_force"`
PackerOnError *string `mapstructure:"packer_on_error" cty:"packer_on_error"`
PackerUserVars map[string]string `mapstructure:"packer_user_variables" cty:"packer_user_variables"`
PackerSensitiveVars []string `mapstructure:"packer_sensitive_variables" cty:"packer_sensitive_variables"`
AccessKey *string `mapstructure:"access_key" required:"true" cty:"access_key"`
CustomEndpointEc2 *string `mapstructure:"custom_endpoint_ec2" required:"false" cty:"custom_endpoint_ec2"`
DecodeAuthZMessages *bool `mapstructure:"decode_authorization_messages" required:"false" cty:"decode_authorization_messages"`
InsecureSkipTLSVerify *bool `mapstructure:"insecure_skip_tls_verify" required:"false" cty:"insecure_skip_tls_verify"`
MFACode *string `mapstructure:"mfa_code" required:"false" cty:"mfa_code"`
ProfileName *string `mapstructure:"profile" required:"false" cty:"profile"`
RawRegion *string `mapstructure:"region" required:"true" cty:"region"`
SecretKey *string `mapstructure:"secret_key" required:"true" cty:"secret_key"`
SkipValidation *bool `mapstructure:"skip_region_validation" required:"false" cty:"skip_region_validation"`
SkipMetadataApiCheck *bool `mapstructure:"skip_metadata_api_check" cty:"skip_metadata_api_check"`
Token *string `mapstructure:"token" required:"false" cty:"token"`
VaultAWSEngine *common.FlatVaultAWSEngineOptions `mapstructure:"vault_aws_engine" required:"false" cty:"vault_aws_engine"`
AssociatePublicIpAddress *bool `mapstructure:"associate_public_ip_address" required:"false" cty:"associate_public_ip_address"`
AvailabilityZone *string `mapstructure:"availability_zone" required:"false" cty:"availability_zone"`
BlockDurationMinutes *int64 `mapstructure:"block_duration_minutes" required:"false" cty:"block_duration_minutes"`
DisableStopInstance *bool `mapstructure:"disable_stop_instance" required:"false" cty:"disable_stop_instance"`
EbsOptimized *bool `mapstructure:"ebs_optimized" required:"false" cty:"ebs_optimized"`
EnableT2Unlimited *bool `mapstructure:"enable_t2_unlimited" required:"false" cty:"enable_t2_unlimited"`
IamInstanceProfile *string `mapstructure:"iam_instance_profile" required:"false" cty:"iam_instance_profile"`
SkipProfileValidation *bool `mapstructure:"skip_profile_validation" required:"false" cty:"skip_profile_validation"`
TemporaryIamInstanceProfilePolicyDocument *common.FlatPolicyDocument `mapstructure:"temporary_iam_instance_profile_policy_document" required:"false" cty:"temporary_iam_instance_profile_policy_document"`
InstanceInitiatedShutdownBehavior *string `mapstructure:"shutdown_behavior" required:"false" cty:"shutdown_behavior"`
InstanceType *string `mapstructure:"instance_type" required:"true" cty:"instance_type"`
SecurityGroupFilter *common.FlatSecurityGroupFilterOptions `mapstructure:"security_group_filter" required:"false" cty:"security_group_filter"`
RunTags map[string]string `mapstructure:"run_tags" required:"false" cty:"run_tags"`
SecurityGroupId *string `mapstructure:"security_group_id" required:"false" cty:"security_group_id"`
SecurityGroupIds []string `mapstructure:"security_group_ids" required:"false" cty:"security_group_ids"`
SourceAmi *string `mapstructure:"source_ami" required:"true" cty:"source_ami"`
SourceAmiFilter *common.FlatAmiFilterOptions `mapstructure:"source_ami_filter" required:"false" cty:"source_ami_filter"`
SpotInstanceTypes []string `mapstructure:"spot_instance_types" required:"false" cty:"spot_instance_types"`
SpotPrice *string `mapstructure:"spot_price" required:"false" cty:"spot_price"`
SpotPriceAutoProduct *string `mapstructure:"spot_price_auto_product" required:"false" cty:"spot_price_auto_product"`
SpotTags map[string]string `mapstructure:"spot_tags" required:"false" cty:"spot_tags"`
SubnetFilter *common.FlatSubnetFilterOptions `mapstructure:"subnet_filter" required:"false" cty:"subnet_filter"`
SubnetId *string `mapstructure:"subnet_id" required:"false" cty:"subnet_id"`
TemporaryKeyPairName *string `mapstructure:"temporary_key_pair_name" required:"false" cty:"temporary_key_pair_name"`
TemporarySGSourceCidrs []string `mapstructure:"temporary_security_group_source_cidrs" required:"false" cty:"temporary_security_group_source_cidrs"`
UserData *string `mapstructure:"user_data" required:"false" cty:"user_data"`
UserDataFile *string `mapstructure:"user_data_file" required:"false" cty:"user_data_file"`
VpcFilter *common.FlatVpcFilterOptions `mapstructure:"vpc_filter" required:"false" cty:"vpc_filter"`
VpcId *string `mapstructure:"vpc_id" required:"false" cty:"vpc_id"`
WindowsPasswordTimeout *string `mapstructure:"windows_password_timeout" required:"false" cty:"windows_password_timeout"`
Type *string `mapstructure:"communicator" cty:"communicator"`
PauseBeforeConnect *string `mapstructure:"pause_before_connecting" cty:"pause_before_connecting"`
SSHHost *string `mapstructure:"ssh_host" cty:"ssh_host"`
SSHPort *int `mapstructure:"ssh_port" cty:"ssh_port"`
SSHUsername *string `mapstructure:"ssh_username" cty:"ssh_username"`
SSHPassword *string `mapstructure:"ssh_password" cty:"ssh_password"`
SSHKeyPairName *string `mapstructure:"ssh_keypair_name" cty:"ssh_keypair_name"`
SSHClearAuthorizedKeys *bool `mapstructure:"ssh_clear_authorized_keys" cty:"ssh_clear_authorized_keys"`
SSHPrivateKeyFile *string `mapstructure:"ssh_private_key_file" cty:"ssh_private_key_file"`
SSHPty *bool `mapstructure:"ssh_pty" cty:"ssh_pty"`
SSHTimeout *string `mapstructure:"ssh_timeout" cty:"ssh_timeout"`
SSHAgentAuth *bool `mapstructure:"ssh_agent_auth" cty:"ssh_agent_auth"`
SSHDisableAgentForwarding *bool `mapstructure:"ssh_disable_agent_forwarding" cty:"ssh_disable_agent_forwarding"`
SSHHandshakeAttempts *int `mapstructure:"ssh_handshake_attempts" cty:"ssh_handshake_attempts"`
SSHBastionHost *string `mapstructure:"ssh_bastion_host" cty:"ssh_bastion_host"`
SSHBastionPort *int `mapstructure:"ssh_bastion_port" cty:"ssh_bastion_port"`
SSHBastionAgentAuth *bool `mapstructure:"ssh_bastion_agent_auth" cty:"ssh_bastion_agent_auth"`
SSHBastionUsername *string `mapstructure:"ssh_bastion_username" cty:"ssh_bastion_username"`
SSHBastionPassword *string `mapstructure:"ssh_bastion_password" cty:"ssh_bastion_password"`
SSHBastionPrivateKeyFile *string `mapstructure:"ssh_bastion_private_key_file" cty:"ssh_bastion_private_key_file"`
SSHFileTransferMethod *string `mapstructure:"ssh_file_transfer_method" cty:"ssh_file_transfer_method"`
SSHProxyHost *string `mapstructure:"ssh_proxy_host" cty:"ssh_proxy_host"`
SSHProxyPort *int `mapstructure:"ssh_proxy_port" cty:"ssh_proxy_port"`
SSHProxyUsername *string `mapstructure:"ssh_proxy_username" cty:"ssh_proxy_username"`
SSHProxyPassword *string `mapstructure:"ssh_proxy_password" cty:"ssh_proxy_password"`
SSHKeepAliveInterval *string `mapstructure:"ssh_keep_alive_interval" cty:"ssh_keep_alive_interval"`
SSHReadWriteTimeout *string `mapstructure:"ssh_read_write_timeout" cty:"ssh_read_write_timeout"`
SSHRemoteTunnels []string `mapstructure:"ssh_remote_tunnels" cty:"ssh_remote_tunnels"`
SSHLocalTunnels []string `mapstructure:"ssh_local_tunnels" cty:"ssh_local_tunnels"`
SSHPublicKey []byte `mapstructure:"ssh_public_key" cty:"ssh_public_key"`
SSHPrivateKey []byte `mapstructure:"ssh_private_key" cty:"ssh_private_key"`
WinRMUser *string `mapstructure:"winrm_username" cty:"winrm_username"`
WinRMPassword *string `mapstructure:"winrm_password" cty:"winrm_password"`
WinRMHost *string `mapstructure:"winrm_host" cty:"winrm_host"`
WinRMPort *int `mapstructure:"winrm_port" cty:"winrm_port"`
WinRMTimeout *string `mapstructure:"winrm_timeout" cty:"winrm_timeout"`
WinRMUseSSL *bool `mapstructure:"winrm_use_ssl" cty:"winrm_use_ssl"`
WinRMInsecure *bool `mapstructure:"winrm_insecure" cty:"winrm_insecure"`
WinRMUseNTLM *bool `mapstructure:"winrm_use_ntlm" cty:"winrm_use_ntlm"`
SSHInterface *string `mapstructure:"ssh_interface" cty:"ssh_interface"`
AMIENASupport *bool `mapstructure:"ena_support" required:"false" cty:"ena_support"`
AMISriovNetSupport *bool `mapstructure:"sriov_support" required:"false" cty:"sriov_support"`
VolumeMappings []FlatBlockDevice `mapstructure:"ebs_volumes" required:"false" cty:"ebs_volumes"`
VolumeRunTags common.TagMap `mapstructure:"run_volume_tags" cty:"run_volume_tags"`
}
// FlatMapstructure returns a new FlatConfig.
// FlatConfig is an auto-generated flat version of Config.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*Config) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatConfig)
}
// HCL2Spec returns the hcl spec of a Config.
// This spec is used by HCL to read the fields of Config.
// The decoded values from this spec will then be applied to a FlatConfig.
func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"packer_build_name": &hcldec.AttrSpec{Name: "packer_build_name", Type: cty.String, Required: false},
"packer_builder_type": &hcldec.AttrSpec{Name: "packer_builder_type", Type: cty.String, Required: false},
"packer_debug": &hcldec.AttrSpec{Name: "packer_debug", Type: cty.Bool, Required: false},
"packer_force": &hcldec.AttrSpec{Name: "packer_force", Type: cty.Bool, Required: false},
"packer_on_error": &hcldec.AttrSpec{Name: "packer_on_error", Type: cty.String, Required: false},
"packer_user_variables": &hcldec.BlockAttrsSpec{TypeName: "packer_user_variables", ElementType: cty.String, Required: false},
"packer_sensitive_variables": &hcldec.AttrSpec{Name: "packer_sensitive_variables", Type: cty.List(cty.String), Required: false},
"access_key": &hcldec.AttrSpec{Name: "access_key", Type: cty.String, Required: false},
"custom_endpoint_ec2": &hcldec.AttrSpec{Name: "custom_endpoint_ec2", Type: cty.String, Required: false},
"decode_authorization_messages": &hcldec.AttrSpec{Name: "decode_authorization_messages", Type: cty.Bool, Required: false},
"insecure_skip_tls_verify": &hcldec.AttrSpec{Name: "insecure_skip_tls_verify", Type: cty.Bool, Required: false},
"mfa_code": &hcldec.AttrSpec{Name: "mfa_code", Type: cty.String, Required: false},
"profile": &hcldec.AttrSpec{Name: "profile", Type: cty.String, Required: false},
"region": &hcldec.AttrSpec{Name: "region", Type: cty.String, Required: false},
"secret_key": &hcldec.AttrSpec{Name: "secret_key", Type: cty.String, Required: false},
"skip_region_validation": &hcldec.AttrSpec{Name: "skip_region_validation", Type: cty.Bool, Required: false},
"skip_metadata_api_check": &hcldec.AttrSpec{Name: "skip_metadata_api_check", Type: cty.Bool, Required: false},
"token": &hcldec.AttrSpec{Name: "token", Type: cty.String, Required: false},
"vault_aws_engine": &hcldec.BlockSpec{TypeName: "vault_aws_engine", Nested: hcldec.ObjectSpec((*common.FlatVaultAWSEngineOptions)(nil).HCL2Spec())},
"associate_public_ip_address": &hcldec.AttrSpec{Name: "associate_public_ip_address", Type: cty.Bool, Required: false},
"availability_zone": &hcldec.AttrSpec{Name: "availability_zone", Type: cty.String, Required: false},
"block_duration_minutes": &hcldec.AttrSpec{Name: "block_duration_minutes", Type: cty.Number, Required: false},
"disable_stop_instance": &hcldec.AttrSpec{Name: "disable_stop_instance", Type: cty.Bool, Required: false},
"ebs_optimized": &hcldec.AttrSpec{Name: "ebs_optimized", Type: cty.Bool, Required: false},
"enable_t2_unlimited": &hcldec.AttrSpec{Name: "enable_t2_unlimited", Type: cty.Bool, Required: false},
"iam_instance_profile": &hcldec.AttrSpec{Name: "iam_instance_profile", Type: cty.String, Required: false},
"skip_profile_validation": &hcldec.AttrSpec{Name: "skip_profile_validation", Type: cty.Bool, Required: false},
"temporary_iam_instance_profile_policy_document": &hcldec.BlockSpec{TypeName: "temporary_iam_instance_profile_policy_document", Nested: hcldec.ObjectSpec((*common.FlatPolicyDocument)(nil).HCL2Spec())},
"shutdown_behavior": &hcldec.AttrSpec{Name: "shutdown_behavior", Type: cty.String, Required: false},
"instance_type": &hcldec.AttrSpec{Name: "instance_type", Type: cty.String, Required: false},
"security_group_filter": &hcldec.BlockSpec{TypeName: "security_group_filter", Nested: hcldec.ObjectSpec((*common.FlatSecurityGroupFilterOptions)(nil).HCL2Spec())},
"run_tags": &hcldec.BlockAttrsSpec{TypeName: "run_tags", ElementType: cty.String, Required: false},
"security_group_id": &hcldec.AttrSpec{Name: "security_group_id", Type: cty.String, Required: false},
"security_group_ids": &hcldec.AttrSpec{Name: "security_group_ids", Type: cty.List(cty.String), Required: false},
"source_ami": &hcldec.AttrSpec{Name: "source_ami", Type: cty.String, Required: false},
"source_ami_filter": &hcldec.BlockSpec{TypeName: "source_ami_filter", Nested: hcldec.ObjectSpec((*common.FlatAmiFilterOptions)(nil).HCL2Spec())},
"spot_instance_types": &hcldec.AttrSpec{Name: "spot_instance_types", Type: cty.List(cty.String), Required: false},
"spot_price": &hcldec.AttrSpec{Name: "spot_price", Type: cty.String, Required: false},
"spot_price_auto_product": &hcldec.AttrSpec{Name: "spot_price_auto_product", Type: cty.String, Required: false},
"spot_tags": &hcldec.BlockAttrsSpec{TypeName: "spot_tags", ElementType: cty.String, Required: false},
"subnet_filter": &hcldec.BlockSpec{TypeName: "subnet_filter", Nested: hcldec.ObjectSpec((*common.FlatSubnetFilterOptions)(nil).HCL2Spec())},
"subnet_id": &hcldec.AttrSpec{Name: "subnet_id", Type: cty.String, Required: false},
"temporary_key_pair_name": &hcldec.AttrSpec{Name: "temporary_key_pair_name", Type: cty.String, Required: false},
"temporary_security_group_source_cidrs": &hcldec.AttrSpec{Name: "temporary_security_group_source_cidrs", Type: cty.List(cty.String), Required: false},
"user_data": &hcldec.AttrSpec{Name: "user_data", Type: cty.String, Required: false},
"user_data_file": &hcldec.AttrSpec{Name: "user_data_file", Type: cty.String, Required: false},
"vpc_filter": &hcldec.BlockSpec{TypeName: "vpc_filter", Nested: hcldec.ObjectSpec((*common.FlatVpcFilterOptions)(nil).HCL2Spec())},
"vpc_id": &hcldec.AttrSpec{Name: "vpc_id", Type: cty.String, Required: false},
"windows_password_timeout": &hcldec.AttrSpec{Name: "windows_password_timeout", Type: cty.String, Required: false},
"communicator": &hcldec.AttrSpec{Name: "communicator", Type: cty.String, Required: false},
"pause_before_connecting": &hcldec.AttrSpec{Name: "pause_before_connecting", Type: cty.String, Required: false},
"ssh_host": &hcldec.AttrSpec{Name: "ssh_host", Type: cty.String, Required: false},
"ssh_port": &hcldec.AttrSpec{Name: "ssh_port", Type: cty.Number, Required: false},
"ssh_username": &hcldec.AttrSpec{Name: "ssh_username", Type: cty.String, Required: false},
"ssh_password": &hcldec.AttrSpec{Name: "ssh_password", Type: cty.String, Required: false},
"ssh_keypair_name": &hcldec.AttrSpec{Name: "ssh_keypair_name", Type: cty.String, Required: false},
"ssh_clear_authorized_keys": &hcldec.AttrSpec{Name: "ssh_clear_authorized_keys", Type: cty.Bool, Required: false},
"ssh_private_key_file": &hcldec.AttrSpec{Name: "ssh_private_key_file", Type: cty.String, Required: false},
"ssh_pty": &hcldec.AttrSpec{Name: "ssh_pty", Type: cty.Bool, Required: false},
"ssh_timeout": &hcldec.AttrSpec{Name: "ssh_timeout", Type: cty.String, Required: false},
"ssh_agent_auth": &hcldec.AttrSpec{Name: "ssh_agent_auth", Type: cty.Bool, Required: false},
"ssh_disable_agent_forwarding": &hcldec.AttrSpec{Name: "ssh_disable_agent_forwarding", Type: cty.Bool, Required: false},
"ssh_handshake_attempts": &hcldec.AttrSpec{Name: "ssh_handshake_attempts", Type: cty.Number, Required: false},
"ssh_bastion_host": &hcldec.AttrSpec{Name: "ssh_bastion_host", Type: cty.String, Required: false},
"ssh_bastion_port": &hcldec.AttrSpec{Name: "ssh_bastion_port", Type: cty.Number, Required: false},
"ssh_bastion_agent_auth": &hcldec.AttrSpec{Name: "ssh_bastion_agent_auth", Type: cty.Bool, Required: false},
"ssh_bastion_username": &hcldec.AttrSpec{Name: "ssh_bastion_username", Type: cty.String, Required: false},
"ssh_bastion_password": &hcldec.AttrSpec{Name: "ssh_bastion_password", Type: cty.String, Required: false},
"ssh_bastion_private_key_file": &hcldec.AttrSpec{Name: "ssh_bastion_private_key_file", Type: cty.String, Required: false},
"ssh_file_transfer_method": &hcldec.AttrSpec{Name: "ssh_file_transfer_method", Type: cty.String, Required: false},
"ssh_proxy_host": &hcldec.AttrSpec{Name: "ssh_proxy_host", Type: cty.String, Required: false},
"ssh_proxy_port": &hcldec.AttrSpec{Name: "ssh_proxy_port", Type: cty.Number, Required: false},
"ssh_proxy_username": &hcldec.AttrSpec{Name: "ssh_proxy_username", Type: cty.String, Required: false},
"ssh_proxy_password": &hcldec.AttrSpec{Name: "ssh_proxy_password", Type: cty.String, Required: false},
"ssh_keep_alive_interval": &hcldec.AttrSpec{Name: "ssh_keep_alive_interval", Type: cty.String, Required: false},
"ssh_read_write_timeout": &hcldec.AttrSpec{Name: "ssh_read_write_timeout", Type: cty.String, Required: false},
"ssh_remote_tunnels": &hcldec.AttrSpec{Name: "ssh_remote_tunnels", Type: cty.List(cty.String), Required: false},
"ssh_local_tunnels": &hcldec.AttrSpec{Name: "ssh_local_tunnels", Type: cty.List(cty.String), Required: false},
"ssh_public_key": &hcldec.AttrSpec{Name: "ssh_public_key", Type: cty.List(cty.Number), Required: false},
"ssh_private_key": &hcldec.AttrSpec{Name: "ssh_private_key", Type: cty.List(cty.Number), Required: false},
"winrm_username": &hcldec.AttrSpec{Name: "winrm_username", Type: cty.String, Required: false},
"winrm_password": &hcldec.AttrSpec{Name: "winrm_password", Type: cty.String, Required: false},
"winrm_host": &hcldec.AttrSpec{Name: "winrm_host", Type: cty.String, Required: false},
"winrm_port": &hcldec.AttrSpec{Name: "winrm_port", Type: cty.Number, Required: false},
"winrm_timeout": &hcldec.AttrSpec{Name: "winrm_timeout", Type: cty.String, Required: false},
"winrm_use_ssl": &hcldec.AttrSpec{Name: "winrm_use_ssl", Type: cty.Bool, Required: false},
"winrm_insecure": &hcldec.AttrSpec{Name: "winrm_insecure", Type: cty.Bool, Required: false},
"winrm_use_ntlm": &hcldec.AttrSpec{Name: "winrm_use_ntlm", Type: cty.Bool, Required: false},
"ssh_interface": &hcldec.AttrSpec{Name: "ssh_interface", Type: cty.String, Required: false},
"ena_support": &hcldec.AttrSpec{Name: "ena_support", Type: cty.Bool, Required: false},
"sriov_support": &hcldec.AttrSpec{Name: "sriov_support", Type: cty.Bool, Required: false},
"ebs_volumes": &hcldec.BlockListSpec{TypeName: "ebs_volumes", Nested: hcldec.ObjectSpec((*FlatBlockDevice)(nil).HCL2Spec())},
"run_volume_tags": &hcldec.BlockAttrsSpec{TypeName: "common.TagMap", ElementType: cty.String, Required: false},
}
return s
}

View File

@ -1,4 +1,5 @@
//go:generate struct-markdown
//go:generate mapstructure-to-hcl2 -type Config
// The instance package contains a packer.Builder implementation that builds
// AMIs for Amazon EC2 backed by instance storage, as opposed to EBS storage.
@ -13,6 +14,7 @@ import (
"github.com/aws/aws-sdk-go/service/ec2"
"github.com/aws/aws-sdk-go/service/iam"
"github.com/hashicorp/hcl/v2/hcldec"
awscommon "github.com/hashicorp/packer/builder/amazon/common"
"github.com/hashicorp/packer/common"
"github.com/hashicorp/packer/helper/communicator"
@ -93,6 +95,8 @@ type Builder struct {
runner multistep.Runner
}
func (b *Builder) ConfigSpec() hcldec.ObjectSpec { return b.config.FlatMapstructure().HCL2Spec() }
func (b *Builder) Prepare(raws ...interface{}) ([]string, error) {
configs := make([]interface{}, len(raws)+1)
configs[0] = map[string]interface{}{

View File

@ -0,0 +1,267 @@
// Code generated by "mapstructure-to-hcl2 -type Config"; DO NOT EDIT.
package instance
import (
"github.com/hashicorp/hcl/v2/hcldec"
"github.com/hashicorp/packer/builder/amazon/common"
"github.com/zclconf/go-cty/cty"
)
// FlatConfig is an auto-generated flat version of Config.
// Where the contents of a field with a `mapstructure:,squash` tag are bubbled up.
type FlatConfig struct {
PackerBuildName *string `mapstructure:"packer_build_name" cty:"packer_build_name"`
PackerBuilderType *string `mapstructure:"packer_builder_type" cty:"packer_builder_type"`
PackerDebug *bool `mapstructure:"packer_debug" cty:"packer_debug"`
PackerForce *bool `mapstructure:"packer_force" cty:"packer_force"`
PackerOnError *string `mapstructure:"packer_on_error" cty:"packer_on_error"`
PackerUserVars map[string]string `mapstructure:"packer_user_variables" cty:"packer_user_variables"`
PackerSensitiveVars []string `mapstructure:"packer_sensitive_variables" cty:"packer_sensitive_variables"`
AccessKey *string `mapstructure:"access_key" required:"true" cty:"access_key"`
CustomEndpointEc2 *string `mapstructure:"custom_endpoint_ec2" required:"false" cty:"custom_endpoint_ec2"`
DecodeAuthZMessages *bool `mapstructure:"decode_authorization_messages" required:"false" cty:"decode_authorization_messages"`
InsecureSkipTLSVerify *bool `mapstructure:"insecure_skip_tls_verify" required:"false" cty:"insecure_skip_tls_verify"`
MFACode *string `mapstructure:"mfa_code" required:"false" cty:"mfa_code"`
ProfileName *string `mapstructure:"profile" required:"false" cty:"profile"`
RawRegion *string `mapstructure:"region" required:"true" cty:"region"`
SecretKey *string `mapstructure:"secret_key" required:"true" cty:"secret_key"`
SkipValidation *bool `mapstructure:"skip_region_validation" required:"false" cty:"skip_region_validation"`
SkipMetadataApiCheck *bool `mapstructure:"skip_metadata_api_check" cty:"skip_metadata_api_check"`
Token *string `mapstructure:"token" required:"false" cty:"token"`
VaultAWSEngine *common.FlatVaultAWSEngineOptions `mapstructure:"vault_aws_engine" required:"false" cty:"vault_aws_engine"`
AMIName *string `mapstructure:"ami_name" required:"true" cty:"ami_name"`
AMIDescription *string `mapstructure:"ami_description" required:"false" cty:"ami_description"`
AMIVirtType *string `mapstructure:"ami_virtualization_type" required:"false" cty:"ami_virtualization_type"`
AMIUsers []string `mapstructure:"ami_users" required:"false" cty:"ami_users"`
AMIGroups []string `mapstructure:"ami_groups" required:"false" cty:"ami_groups"`
AMIProductCodes []string `mapstructure:"ami_product_codes" required:"false" cty:"ami_product_codes"`
AMIRegions []string `mapstructure:"ami_regions" required:"false" cty:"ami_regions"`
AMITags common.TagMap `mapstructure:"tags" required:"false" cty:"tags"`
AMIENASupport *bool `mapstructure:"ena_support" required:"false" cty:"ena_support"`
AMISriovNetSupport *bool `mapstructure:"sriov_support" required:"false" cty:"sriov_support"`
AMIForceDeregister *bool `mapstructure:"force_deregister" required:"false" cty:"force_deregister"`
AMIForceDeleteSnapshot *bool `mapstructure:"force_delete_snapshot" required:"false" cty:"force_delete_snapshot"`
AMIEncryptBootVolume *bool `mapstructure:"encrypt_boot" required:"false" cty:"encrypt_boot"`
AMIKmsKeyId *string `mapstructure:"kms_key_id" required:"false" cty:"kms_key_id"`
AMIRegionKMSKeyIDs map[string]string `mapstructure:"region_kms_key_ids" required:"false" cty:"region_kms_key_ids"`
AMISkipBuildRegion *bool `mapstructure:"skip_save_build_region" cty:"skip_save_build_region"`
SnapshotTags common.TagMap `mapstructure:"snapshot_tags" required:"false" cty:"snapshot_tags"`
SnapshotUsers []string `mapstructure:"snapshot_users" required:"false" cty:"snapshot_users"`
SnapshotGroups []string `mapstructure:"snapshot_groups" required:"false" cty:"snapshot_groups"`
AssociatePublicIpAddress *bool `mapstructure:"associate_public_ip_address" required:"false" cty:"associate_public_ip_address"`
AvailabilityZone *string `mapstructure:"availability_zone" required:"false" cty:"availability_zone"`
BlockDurationMinutes *int64 `mapstructure:"block_duration_minutes" required:"false" cty:"block_duration_minutes"`
DisableStopInstance *bool `mapstructure:"disable_stop_instance" required:"false" cty:"disable_stop_instance"`
EbsOptimized *bool `mapstructure:"ebs_optimized" required:"false" cty:"ebs_optimized"`
EnableT2Unlimited *bool `mapstructure:"enable_t2_unlimited" required:"false" cty:"enable_t2_unlimited"`
IamInstanceProfile *string `mapstructure:"iam_instance_profile" required:"false" cty:"iam_instance_profile"`
SkipProfileValidation *bool `mapstructure:"skip_profile_validation" required:"false" cty:"skip_profile_validation"`
TemporaryIamInstanceProfilePolicyDocument *common.FlatPolicyDocument `mapstructure:"temporary_iam_instance_profile_policy_document" required:"false" cty:"temporary_iam_instance_profile_policy_document"`
InstanceInitiatedShutdownBehavior *string `mapstructure:"shutdown_behavior" required:"false" cty:"shutdown_behavior"`
InstanceType *string `mapstructure:"instance_type" required:"true" cty:"instance_type"`
SecurityGroupFilter *common.FlatSecurityGroupFilterOptions `mapstructure:"security_group_filter" required:"false" cty:"security_group_filter"`
RunTags map[string]string `mapstructure:"run_tags" required:"false" cty:"run_tags"`
SecurityGroupId *string `mapstructure:"security_group_id" required:"false" cty:"security_group_id"`
SecurityGroupIds []string `mapstructure:"security_group_ids" required:"false" cty:"security_group_ids"`
SourceAmi *string `mapstructure:"source_ami" required:"true" cty:"source_ami"`
SourceAmiFilter *common.FlatAmiFilterOptions `mapstructure:"source_ami_filter" required:"false" cty:"source_ami_filter"`
SpotInstanceTypes []string `mapstructure:"spot_instance_types" required:"false" cty:"spot_instance_types"`
SpotPrice *string `mapstructure:"spot_price" required:"false" cty:"spot_price"`
SpotPriceAutoProduct *string `mapstructure:"spot_price_auto_product" required:"false" cty:"spot_price_auto_product"`
SpotTags map[string]string `mapstructure:"spot_tags" required:"false" cty:"spot_tags"`
SubnetFilter *common.FlatSubnetFilterOptions `mapstructure:"subnet_filter" required:"false" cty:"subnet_filter"`
SubnetId *string `mapstructure:"subnet_id" required:"false" cty:"subnet_id"`
TemporaryKeyPairName *string `mapstructure:"temporary_key_pair_name" required:"false" cty:"temporary_key_pair_name"`
TemporarySGSourceCidrs []string `mapstructure:"temporary_security_group_source_cidrs" required:"false" cty:"temporary_security_group_source_cidrs"`
UserData *string `mapstructure:"user_data" required:"false" cty:"user_data"`
UserDataFile *string `mapstructure:"user_data_file" required:"false" cty:"user_data_file"`
VpcFilter *common.FlatVpcFilterOptions `mapstructure:"vpc_filter" required:"false" cty:"vpc_filter"`
VpcId *string `mapstructure:"vpc_id" required:"false" cty:"vpc_id"`
WindowsPasswordTimeout *string `mapstructure:"windows_password_timeout" required:"false" cty:"windows_password_timeout"`
Type *string `mapstructure:"communicator" cty:"communicator"`
PauseBeforeConnect *string `mapstructure:"pause_before_connecting" cty:"pause_before_connecting"`
SSHHost *string `mapstructure:"ssh_host" cty:"ssh_host"`
SSHPort *int `mapstructure:"ssh_port" cty:"ssh_port"`
SSHUsername *string `mapstructure:"ssh_username" cty:"ssh_username"`
SSHPassword *string `mapstructure:"ssh_password" cty:"ssh_password"`
SSHKeyPairName *string `mapstructure:"ssh_keypair_name" cty:"ssh_keypair_name"`
SSHClearAuthorizedKeys *bool `mapstructure:"ssh_clear_authorized_keys" cty:"ssh_clear_authorized_keys"`
SSHPrivateKeyFile *string `mapstructure:"ssh_private_key_file" cty:"ssh_private_key_file"`
SSHPty *bool `mapstructure:"ssh_pty" cty:"ssh_pty"`
SSHTimeout *string `mapstructure:"ssh_timeout" cty:"ssh_timeout"`
SSHAgentAuth *bool `mapstructure:"ssh_agent_auth" cty:"ssh_agent_auth"`
SSHDisableAgentForwarding *bool `mapstructure:"ssh_disable_agent_forwarding" cty:"ssh_disable_agent_forwarding"`
SSHHandshakeAttempts *int `mapstructure:"ssh_handshake_attempts" cty:"ssh_handshake_attempts"`
SSHBastionHost *string `mapstructure:"ssh_bastion_host" cty:"ssh_bastion_host"`
SSHBastionPort *int `mapstructure:"ssh_bastion_port" cty:"ssh_bastion_port"`
SSHBastionAgentAuth *bool `mapstructure:"ssh_bastion_agent_auth" cty:"ssh_bastion_agent_auth"`
SSHBastionUsername *string `mapstructure:"ssh_bastion_username" cty:"ssh_bastion_username"`
SSHBastionPassword *string `mapstructure:"ssh_bastion_password" cty:"ssh_bastion_password"`
SSHBastionPrivateKeyFile *string `mapstructure:"ssh_bastion_private_key_file" cty:"ssh_bastion_private_key_file"`
SSHFileTransferMethod *string `mapstructure:"ssh_file_transfer_method" cty:"ssh_file_transfer_method"`
SSHProxyHost *string `mapstructure:"ssh_proxy_host" cty:"ssh_proxy_host"`
SSHProxyPort *int `mapstructure:"ssh_proxy_port" cty:"ssh_proxy_port"`
SSHProxyUsername *string `mapstructure:"ssh_proxy_username" cty:"ssh_proxy_username"`
SSHProxyPassword *string `mapstructure:"ssh_proxy_password" cty:"ssh_proxy_password"`
SSHKeepAliveInterval *string `mapstructure:"ssh_keep_alive_interval" cty:"ssh_keep_alive_interval"`
SSHReadWriteTimeout *string `mapstructure:"ssh_read_write_timeout" cty:"ssh_read_write_timeout"`
SSHRemoteTunnels []string `mapstructure:"ssh_remote_tunnels" cty:"ssh_remote_tunnels"`
SSHLocalTunnels []string `mapstructure:"ssh_local_tunnels" cty:"ssh_local_tunnels"`
SSHPublicKey []byte `mapstructure:"ssh_public_key" cty:"ssh_public_key"`
SSHPrivateKey []byte `mapstructure:"ssh_private_key" cty:"ssh_private_key"`
WinRMUser *string `mapstructure:"winrm_username" cty:"winrm_username"`
WinRMPassword *string `mapstructure:"winrm_password" cty:"winrm_password"`
WinRMHost *string `mapstructure:"winrm_host" cty:"winrm_host"`
WinRMPort *int `mapstructure:"winrm_port" cty:"winrm_port"`
WinRMTimeout *string `mapstructure:"winrm_timeout" cty:"winrm_timeout"`
WinRMUseSSL *bool `mapstructure:"winrm_use_ssl" cty:"winrm_use_ssl"`
WinRMInsecure *bool `mapstructure:"winrm_insecure" cty:"winrm_insecure"`
WinRMUseNTLM *bool `mapstructure:"winrm_use_ntlm" cty:"winrm_use_ntlm"`
SSHInterface *string `mapstructure:"ssh_interface" cty:"ssh_interface"`
AMIMappings []common.FlatBlockDevice `mapstructure:"ami_block_device_mappings" required:"false" cty:"ami_block_device_mappings"`
LaunchMappings []common.FlatBlockDevice `mapstructure:"launch_block_device_mappings" required:"false" cty:"launch_block_device_mappings"`
AccountId *string `mapstructure:"account_id" required:"true" cty:"account_id"`
BundleDestination *string `mapstructure:"bundle_destination" required:"false" cty:"bundle_destination"`
BundlePrefix *string `mapstructure:"bundle_prefix" required:"false" cty:"bundle_prefix"`
BundleUploadCommand *string `mapstructure:"bundle_upload_command" required:"false" cty:"bundle_upload_command"`
BundleVolCommand *string `mapstructure:"bundle_vol_command" required:"false" cty:"bundle_vol_command"`
S3Bucket *string `mapstructure:"s3_bucket" required:"true" cty:"s3_bucket"`
X509CertPath *string `mapstructure:"x509_cert_path" required:"true" cty:"x509_cert_path"`
X509KeyPath *string `mapstructure:"x509_key_path" required:"true" cty:"x509_key_path"`
X509UploadPath *string `mapstructure:"x509_upload_path" required:"false" cty:"x509_upload_path"`
}
// FlatMapstructure returns a new FlatConfig.
// FlatConfig is an auto-generated flat version of Config.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*Config) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatConfig)
}
// HCL2Spec returns the hcl spec of a Config.
// This spec is used by HCL to read the fields of Config.
// The decoded values from this spec will then be applied to a FlatConfig.
func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"packer_build_name": &hcldec.AttrSpec{Name: "packer_build_name", Type: cty.String, Required: false},
"packer_builder_type": &hcldec.AttrSpec{Name: "packer_builder_type", Type: cty.String, Required: false},
"packer_debug": &hcldec.AttrSpec{Name: "packer_debug", Type: cty.Bool, Required: false},
"packer_force": &hcldec.AttrSpec{Name: "packer_force", Type: cty.Bool, Required: false},
"packer_on_error": &hcldec.AttrSpec{Name: "packer_on_error", Type: cty.String, Required: false},
"packer_user_variables": &hcldec.BlockAttrsSpec{TypeName: "packer_user_variables", ElementType: cty.String, Required: false},
"packer_sensitive_variables": &hcldec.AttrSpec{Name: "packer_sensitive_variables", Type: cty.List(cty.String), Required: false},
"access_key": &hcldec.AttrSpec{Name: "access_key", Type: cty.String, Required: false},
"custom_endpoint_ec2": &hcldec.AttrSpec{Name: "custom_endpoint_ec2", Type: cty.String, Required: false},
"decode_authorization_messages": &hcldec.AttrSpec{Name: "decode_authorization_messages", Type: cty.Bool, Required: false},
"insecure_skip_tls_verify": &hcldec.AttrSpec{Name: "insecure_skip_tls_verify", Type: cty.Bool, Required: false},
"mfa_code": &hcldec.AttrSpec{Name: "mfa_code", Type: cty.String, Required: false},
"profile": &hcldec.AttrSpec{Name: "profile", Type: cty.String, Required: false},
"region": &hcldec.AttrSpec{Name: "region", Type: cty.String, Required: false},
"secret_key": &hcldec.AttrSpec{Name: "secret_key", Type: cty.String, Required: false},
"skip_region_validation": &hcldec.AttrSpec{Name: "skip_region_validation", Type: cty.Bool, Required: false},
"skip_metadata_api_check": &hcldec.AttrSpec{Name: "skip_metadata_api_check", Type: cty.Bool, Required: false},
"token": &hcldec.AttrSpec{Name: "token", Type: cty.String, Required: false},
"vault_aws_engine": &hcldec.BlockSpec{TypeName: "vault_aws_engine", Nested: hcldec.ObjectSpec((*common.FlatVaultAWSEngineOptions)(nil).HCL2Spec())},
"ami_name": &hcldec.AttrSpec{Name: "ami_name", Type: cty.String, Required: false},
"ami_description": &hcldec.AttrSpec{Name: "ami_description", Type: cty.String, Required: false},
"ami_virtualization_type": &hcldec.AttrSpec{Name: "ami_virtualization_type", Type: cty.String, Required: false},
"ami_users": &hcldec.AttrSpec{Name: "ami_users", Type: cty.List(cty.String), Required: false},
"ami_groups": &hcldec.AttrSpec{Name: "ami_groups", Type: cty.List(cty.String), Required: false},
"ami_product_codes": &hcldec.AttrSpec{Name: "ami_product_codes", Type: cty.List(cty.String), Required: false},
"ami_regions": &hcldec.AttrSpec{Name: "ami_regions", Type: cty.List(cty.String), Required: false},
"tags": &hcldec.BlockAttrsSpec{TypeName: "common.TagMap", ElementType: cty.String, Required: false},
"ena_support": &hcldec.AttrSpec{Name: "ena_support", Type: cty.Bool, Required: false},
"sriov_support": &hcldec.AttrSpec{Name: "sriov_support", Type: cty.Bool, Required: false},
"force_deregister": &hcldec.AttrSpec{Name: "force_deregister", Type: cty.Bool, Required: false},
"force_delete_snapshot": &hcldec.AttrSpec{Name: "force_delete_snapshot", Type: cty.Bool, Required: false},
"encrypt_boot": &hcldec.AttrSpec{Name: "encrypt_boot", Type: cty.Bool, Required: false},
"kms_key_id": &hcldec.AttrSpec{Name: "kms_key_id", Type: cty.String, Required: false},
"region_kms_key_ids": &hcldec.BlockAttrsSpec{TypeName: "region_kms_key_ids", ElementType: cty.String, Required: false},
"skip_save_build_region": &hcldec.AttrSpec{Name: "skip_save_build_region", Type: cty.Bool, Required: false},
"snapshot_tags": &hcldec.BlockAttrsSpec{TypeName: "common.TagMap", ElementType: cty.String, Required: false},
"snapshot_users": &hcldec.AttrSpec{Name: "snapshot_users", Type: cty.List(cty.String), Required: false},
"snapshot_groups": &hcldec.AttrSpec{Name: "snapshot_groups", Type: cty.List(cty.String), Required: false},
"associate_public_ip_address": &hcldec.AttrSpec{Name: "associate_public_ip_address", Type: cty.Bool, Required: false},
"availability_zone": &hcldec.AttrSpec{Name: "availability_zone", Type: cty.String, Required: false},
"block_duration_minutes": &hcldec.AttrSpec{Name: "block_duration_minutes", Type: cty.Number, Required: false},
"disable_stop_instance": &hcldec.AttrSpec{Name: "disable_stop_instance", Type: cty.Bool, Required: false},
"ebs_optimized": &hcldec.AttrSpec{Name: "ebs_optimized", Type: cty.Bool, Required: false},
"enable_t2_unlimited": &hcldec.AttrSpec{Name: "enable_t2_unlimited", Type: cty.Bool, Required: false},
"iam_instance_profile": &hcldec.AttrSpec{Name: "iam_instance_profile", Type: cty.String, Required: false},
"skip_profile_validation": &hcldec.AttrSpec{Name: "skip_profile_validation", Type: cty.Bool, Required: false},
"temporary_iam_instance_profile_policy_document": &hcldec.BlockSpec{TypeName: "temporary_iam_instance_profile_policy_document", Nested: hcldec.ObjectSpec((*common.FlatPolicyDocument)(nil).HCL2Spec())},
"shutdown_behavior": &hcldec.AttrSpec{Name: "shutdown_behavior", Type: cty.String, Required: false},
"instance_type": &hcldec.AttrSpec{Name: "instance_type", Type: cty.String, Required: false},
"security_group_filter": &hcldec.BlockSpec{TypeName: "security_group_filter", Nested: hcldec.ObjectSpec((*common.FlatSecurityGroupFilterOptions)(nil).HCL2Spec())},
"run_tags": &hcldec.BlockAttrsSpec{TypeName: "run_tags", ElementType: cty.String, Required: false},
"security_group_id": &hcldec.AttrSpec{Name: "security_group_id", Type: cty.String, Required: false},
"security_group_ids": &hcldec.AttrSpec{Name: "security_group_ids", Type: cty.List(cty.String), Required: false},
"source_ami": &hcldec.AttrSpec{Name: "source_ami", Type: cty.String, Required: false},
"source_ami_filter": &hcldec.BlockSpec{TypeName: "source_ami_filter", Nested: hcldec.ObjectSpec((*common.FlatAmiFilterOptions)(nil).HCL2Spec())},
"spot_instance_types": &hcldec.AttrSpec{Name: "spot_instance_types", Type: cty.List(cty.String), Required: false},
"spot_price": &hcldec.AttrSpec{Name: "spot_price", Type: cty.String, Required: false},
"spot_price_auto_product": &hcldec.AttrSpec{Name: "spot_price_auto_product", Type: cty.String, Required: false},
"spot_tags": &hcldec.BlockAttrsSpec{TypeName: "spot_tags", ElementType: cty.String, Required: false},
"subnet_filter": &hcldec.BlockSpec{TypeName: "subnet_filter", Nested: hcldec.ObjectSpec((*common.FlatSubnetFilterOptions)(nil).HCL2Spec())},
"subnet_id": &hcldec.AttrSpec{Name: "subnet_id", Type: cty.String, Required: false},
"temporary_key_pair_name": &hcldec.AttrSpec{Name: "temporary_key_pair_name", Type: cty.String, Required: false},
"temporary_security_group_source_cidrs": &hcldec.AttrSpec{Name: "temporary_security_group_source_cidrs", Type: cty.List(cty.String), Required: false},
"user_data": &hcldec.AttrSpec{Name: "user_data", Type: cty.String, Required: false},
"user_data_file": &hcldec.AttrSpec{Name: "user_data_file", Type: cty.String, Required: false},
"vpc_filter": &hcldec.BlockSpec{TypeName: "vpc_filter", Nested: hcldec.ObjectSpec((*common.FlatVpcFilterOptions)(nil).HCL2Spec())},
"vpc_id": &hcldec.AttrSpec{Name: "vpc_id", Type: cty.String, Required: false},
"windows_password_timeout": &hcldec.AttrSpec{Name: "windows_password_timeout", Type: cty.String, Required: false},
"communicator": &hcldec.AttrSpec{Name: "communicator", Type: cty.String, Required: false},
"pause_before_connecting": &hcldec.AttrSpec{Name: "pause_before_connecting", Type: cty.String, Required: false},
"ssh_host": &hcldec.AttrSpec{Name: "ssh_host", Type: cty.String, Required: false},
"ssh_port": &hcldec.AttrSpec{Name: "ssh_port", Type: cty.Number, Required: false},
"ssh_username": &hcldec.AttrSpec{Name: "ssh_username", Type: cty.String, Required: false},
"ssh_password": &hcldec.AttrSpec{Name: "ssh_password", Type: cty.String, Required: false},
"ssh_keypair_name": &hcldec.AttrSpec{Name: "ssh_keypair_name", Type: cty.String, Required: false},
"ssh_clear_authorized_keys": &hcldec.AttrSpec{Name: "ssh_clear_authorized_keys", Type: cty.Bool, Required: false},
"ssh_private_key_file": &hcldec.AttrSpec{Name: "ssh_private_key_file", Type: cty.String, Required: false},
"ssh_pty": &hcldec.AttrSpec{Name: "ssh_pty", Type: cty.Bool, Required: false},
"ssh_timeout": &hcldec.AttrSpec{Name: "ssh_timeout", Type: cty.String, Required: false},
"ssh_agent_auth": &hcldec.AttrSpec{Name: "ssh_agent_auth", Type: cty.Bool, Required: false},
"ssh_disable_agent_forwarding": &hcldec.AttrSpec{Name: "ssh_disable_agent_forwarding", Type: cty.Bool, Required: false},
"ssh_handshake_attempts": &hcldec.AttrSpec{Name: "ssh_handshake_attempts", Type: cty.Number, Required: false},
"ssh_bastion_host": &hcldec.AttrSpec{Name: "ssh_bastion_host", Type: cty.String, Required: false},
"ssh_bastion_port": &hcldec.AttrSpec{Name: "ssh_bastion_port", Type: cty.Number, Required: false},
"ssh_bastion_agent_auth": &hcldec.AttrSpec{Name: "ssh_bastion_agent_auth", Type: cty.Bool, Required: false},
"ssh_bastion_username": &hcldec.AttrSpec{Name: "ssh_bastion_username", Type: cty.String, Required: false},
"ssh_bastion_password": &hcldec.AttrSpec{Name: "ssh_bastion_password", Type: cty.String, Required: false},
"ssh_bastion_private_key_file": &hcldec.AttrSpec{Name: "ssh_bastion_private_key_file", Type: cty.String, Required: false},
"ssh_file_transfer_method": &hcldec.AttrSpec{Name: "ssh_file_transfer_method", Type: cty.String, Required: false},
"ssh_proxy_host": &hcldec.AttrSpec{Name: "ssh_proxy_host", Type: cty.String, Required: false},
"ssh_proxy_port": &hcldec.AttrSpec{Name: "ssh_proxy_port", Type: cty.Number, Required: false},
"ssh_proxy_username": &hcldec.AttrSpec{Name: "ssh_proxy_username", Type: cty.String, Required: false},
"ssh_proxy_password": &hcldec.AttrSpec{Name: "ssh_proxy_password", Type: cty.String, Required: false},
"ssh_keep_alive_interval": &hcldec.AttrSpec{Name: "ssh_keep_alive_interval", Type: cty.String, Required: false},
"ssh_read_write_timeout": &hcldec.AttrSpec{Name: "ssh_read_write_timeout", Type: cty.String, Required: false},
"ssh_remote_tunnels": &hcldec.AttrSpec{Name: "ssh_remote_tunnels", Type: cty.List(cty.String), Required: false},
"ssh_local_tunnels": &hcldec.AttrSpec{Name: "ssh_local_tunnels", Type: cty.List(cty.String), Required: false},
"ssh_public_key": &hcldec.AttrSpec{Name: "ssh_public_key", Type: cty.List(cty.Number), Required: false},
"ssh_private_key": &hcldec.AttrSpec{Name: "ssh_private_key", Type: cty.List(cty.Number), Required: false},
"winrm_username": &hcldec.AttrSpec{Name: "winrm_username", Type: cty.String, Required: false},
"winrm_password": &hcldec.AttrSpec{Name: "winrm_password", Type: cty.String, Required: false},
"winrm_host": &hcldec.AttrSpec{Name: "winrm_host", Type: cty.String, Required: false},
"winrm_port": &hcldec.AttrSpec{Name: "winrm_port", Type: cty.Number, Required: false},
"winrm_timeout": &hcldec.AttrSpec{Name: "winrm_timeout", Type: cty.String, Required: false},
"winrm_use_ssl": &hcldec.AttrSpec{Name: "winrm_use_ssl", Type: cty.Bool, Required: false},
"winrm_insecure": &hcldec.AttrSpec{Name: "winrm_insecure", Type: cty.Bool, Required: false},
"winrm_use_ntlm": &hcldec.AttrSpec{Name: "winrm_use_ntlm", Type: cty.Bool, Required: false},
"ssh_interface": &hcldec.AttrSpec{Name: "ssh_interface", Type: cty.String, Required: false},
"ami_block_device_mappings": &hcldec.BlockListSpec{TypeName: "ami_block_device_mappings", Nested: hcldec.ObjectSpec((*common.FlatBlockDevice)(nil).HCL2Spec())},
"launch_block_device_mappings": &hcldec.BlockListSpec{TypeName: "launch_block_device_mappings", Nested: hcldec.ObjectSpec((*common.FlatBlockDevice)(nil).HCL2Spec())},
"account_id": &hcldec.AttrSpec{Name: "account_id", Type: cty.String, Required: false},
"bundle_destination": &hcldec.AttrSpec{Name: "bundle_destination", Type: cty.String, Required: false},
"bundle_prefix": &hcldec.AttrSpec{Name: "bundle_prefix", Type: cty.String, Required: false},
"bundle_upload_command": &hcldec.AttrSpec{Name: "bundle_upload_command", Type: cty.String, Required: false},
"bundle_vol_command": &hcldec.AttrSpec{Name: "bundle_vol_command", Type: cty.String, Required: false},
"s3_bucket": &hcldec.AttrSpec{Name: "s3_bucket", Type: cty.String, Required: false},
"x509_cert_path": &hcldec.AttrSpec{Name: "x509_cert_path", Type: cty.String, Required: false},
"x509_key_path": &hcldec.AttrSpec{Name: "x509_key_path", Type: cty.String, Required: false},
"x509_upload_path": &hcldec.AttrSpec{Name: "x509_upload_path", Type: cty.String, Required: false},
}
return s
}

View File

@ -14,6 +14,7 @@ import (
"github.com/Azure/azure-sdk-for-go/storage"
"github.com/Azure/go-autorest/autorest/adal"
"github.com/dgrijalva/jwt-go"
"github.com/hashicorp/hcl/v2/hcldec"
packerAzureCommon "github.com/hashicorp/packer/builder/azure/common"
"github.com/hashicorp/packer/builder/azure/common/constants"
"github.com/hashicorp/packer/builder/azure/common/lin"
@ -24,7 +25,7 @@ import (
)
type Builder struct {
config *Config
config Config
stateBag multistep.StateBag
runner multistep.Runner
}
@ -34,14 +35,14 @@ const (
DefaultSecretName = "packerKeyVaultSecret"
)
func (b *Builder) ConfigSpec() hcldec.ObjectSpec { return b.config.FlatMapstructure().HCL2Spec() }
func (b *Builder) Prepare(raws ...interface{}) ([]string, error) {
c, warnings, errs := newConfig(raws...)
warnings, errs := b.config.Prepare(raws...)
if errs != nil {
return warnings, errs
}
b.config = c
b.stateBag = new(multistep.BasicStateBag)
b.configureStateBag(b.stateBag)
b.setTemplateParameters(b.stateBag)
@ -64,7 +65,7 @@ func (b *Builder) Run(ctx context.Context, ui packer.Ui, hook packer.Hook) (pack
}
log.Print(":: Configuration")
packerAzureCommon.DumpConfig(b.config, func(s string) { log.Print(s) })
packerAzureCommon.DumpConfig(&b.config, func(s string) { log.Print(s) })
b.stateBag.Put("hook", hook)
b.stateBag.Put(constants.Ui, ui)
@ -90,7 +91,7 @@ func (b *Builder) Run(ctx context.Context, ui packer.Ui, hook packer.Hook) (pack
}
resolver := newResourceResolver(azureClient)
if err := resolver.Resolve(b.config); err != nil {
if err := resolver.Resolve(&b.config); err != nil {
return nil, err
}
if b.config.ClientConfig.ObjectID == "" {
@ -197,8 +198,8 @@ func (b *Builder) Run(ctx context.Context, ui packer.Ui, hook packer.Hook) (pack
if b.config.OSType == constants.Target_Linux {
steps = []multistep.Step{
NewStepCreateResourceGroup(azureClient, ui),
NewStepValidateTemplate(azureClient, ui, b.config, GetVirtualMachineDeployment),
NewStepDeployTemplate(azureClient, ui, b.config, deploymentName, GetVirtualMachineDeployment),
NewStepValidateTemplate(azureClient, ui, &b.config, GetVirtualMachineDeployment),
NewStepDeployTemplate(azureClient, ui, &b.config, deploymentName, GetVirtualMachineDeployment),
NewStepGetIPAddress(azureClient, ui, endpointConnectType),
&communicator.StepConnectSSH{
Config: &b.config.Comm,
@ -212,10 +213,10 @@ func (b *Builder) Run(ctx context.Context, ui packer.Ui, hook packer.Hook) (pack
NewStepGetOSDisk(azureClient, ui),
NewStepGetAdditionalDisks(azureClient, ui),
NewStepPowerOffCompute(azureClient, ui),
NewStepSnapshotOSDisk(azureClient, ui, b.config),
NewStepSnapshotDataDisks(azureClient, ui, b.config),
NewStepSnapshotOSDisk(azureClient, ui, &b.config),
NewStepSnapshotDataDisks(azureClient, ui, &b.config),
NewStepCaptureImage(azureClient, ui),
NewStepPublishToSharedImageGallery(azureClient, ui, b.config),
NewStepPublishToSharedImageGallery(azureClient, ui, &b.config),
NewStepDeleteResourceGroup(azureClient, ui),
NewStepDeleteOSDisk(azureClient, ui),
NewStepDeleteAdditionalDisks(azureClient, ui),
@ -224,12 +225,12 @@ func (b *Builder) Run(ctx context.Context, ui packer.Ui, hook packer.Hook) (pack
keyVaultDeploymentName := b.stateBag.Get(constants.ArmKeyVaultDeploymentName).(string)
steps = []multistep.Step{
NewStepCreateResourceGroup(azureClient, ui),
NewStepValidateTemplate(azureClient, ui, b.config, GetKeyVaultDeployment),
NewStepDeployTemplate(azureClient, ui, b.config, keyVaultDeploymentName, GetKeyVaultDeployment),
NewStepValidateTemplate(azureClient, ui, &b.config, GetKeyVaultDeployment),
NewStepDeployTemplate(azureClient, ui, &b.config, keyVaultDeploymentName, GetKeyVaultDeployment),
NewStepGetCertificate(azureClient, ui),
NewStepSetCertificate(b.config, ui),
NewStepValidateTemplate(azureClient, ui, b.config, GetVirtualMachineDeployment),
NewStepDeployTemplate(azureClient, ui, b.config, deploymentName, GetVirtualMachineDeployment),
NewStepSetCertificate(&b.config, ui),
NewStepValidateTemplate(azureClient, ui, &b.config, GetVirtualMachineDeployment),
NewStepDeployTemplate(azureClient, ui, &b.config, deploymentName, GetVirtualMachineDeployment),
NewStepGetIPAddress(azureClient, ui, endpointConnectType),
&StepSaveWinRMPassword{
Password: b.config.tmpAdminPassword,
@ -251,10 +252,10 @@ func (b *Builder) Run(ctx context.Context, ui packer.Ui, hook packer.Hook) (pack
NewStepGetOSDisk(azureClient, ui),
NewStepGetAdditionalDisks(azureClient, ui),
NewStepPowerOffCompute(azureClient, ui),
NewStepSnapshotOSDisk(azureClient, ui, b.config),
NewStepSnapshotDataDisks(azureClient, ui, b.config),
NewStepSnapshotOSDisk(azureClient, ui, &b.config),
NewStepSnapshotDataDisks(azureClient, ui, &b.config),
NewStepCaptureImage(azureClient, ui),
NewStepPublishToSharedImageGallery(azureClient, ui, b.config),
NewStepPublishToSharedImageGallery(azureClient, ui, &b.config),
NewStepDeleteResourceGroup(azureClient, ui),
NewStepDeleteOSDisk(azureClient, ui),
NewStepDeleteAdditionalDisks(azureClient, ui),

View File

@ -7,7 +7,7 @@ import (
)
func TestStateBagShouldBePopulatedExpectedValues(t *testing.T) {
var testSubject = &Builder{}
var testSubject Builder
_, err := testSubject.Prepare(getArmBuilderConfiguration(), getPackerConfiguration())
if err != nil {
t.Fatalf("failed to prepare: %s", err)

View File

@ -493,58 +493,57 @@ func (c *Config) createCertificate() (string, error) {
return base64.StdEncoding.EncodeToString(bytes), nil
}
func newConfig(raws ...interface{}) (*Config, []string, error) {
var c Config
func (c *Config) Prepare(raws ...interface{}) ([]string, error) {
c.ctx.Funcs = azcommon.TemplateFuncs
err := config.Decode(&c, &config.DecodeOpts{
err := config.Decode(c, &config.DecodeOpts{
Interpolate: true,
InterpolateContext: &c.ctx,
}, raws...)
if err != nil {
return nil, nil, err
return nil, err
}
provideDefaultValues(&c)
setRuntimeValues(&c)
setUserNamePassword(&c)
provideDefaultValues(c)
setRuntimeValues(c)
setUserNamePassword(c)
err = c.ClientConfig.SetDefaultValues()
if err != nil {
return nil, nil, err
return nil, err
}
err = setCustomData(&c)
err = setCustomData(c)
if err != nil {
return nil, nil, err
return nil, err
}
// NOTE: if the user did not specify a communicator, then default to both
// SSH and WinRM. This is for backwards compatibility because the code did
// not specifically force the user to set a communicator.
if c.Comm.Type == "" || strings.EqualFold(c.Comm.Type, "ssh") {
err = setSshValues(&c)
err = setSshValues(c)
if err != nil {
return nil, nil, err
return nil, err
}
}
if c.Comm.Type == "" || strings.EqualFold(c.Comm.Type, "winrm") {
err = setWinRMCertificate(&c)
err = setWinRMCertificate(c)
if err != nil {
return nil, nil, err
return nil, err
}
}
var errs *packer.MultiError
errs = packer.MultiErrorAppend(errs, c.Comm.Prepare(&c.ctx)...)
assertRequiredParametersSet(&c, errs)
assertTagProperties(&c, errs)
assertRequiredParametersSet(c, errs)
assertTagProperties(c, errs)
if errs != nil && len(errs.Errors) > 0 {
return nil, nil, errs
return nil, errs
}
return &c, nil, nil
return nil, nil
}
func setSshValues(c *Config) error {

View File

@ -94,8 +94,8 @@ type FlatConfig struct {
SSHReadWriteTimeout *string `mapstructure:"ssh_read_write_timeout" cty:"ssh_read_write_timeout"`
SSHRemoteTunnels []string `mapstructure:"ssh_remote_tunnels" cty:"ssh_remote_tunnels"`
SSHLocalTunnels []string `mapstructure:"ssh_local_tunnels" cty:"ssh_local_tunnels"`
SSHPublicKey []byte `cty:"ssh_public_key"`
SSHPrivateKey []byte `cty:"ssh_private_key"`
SSHPublicKey []byte `mapstructure:"ssh_public_key" cty:"ssh_public_key"`
SSHPrivateKey []byte `mapstructure:"ssh_private_key" cty:"ssh_private_key"`
WinRMUser *string `mapstructure:"winrm_username" cty:"winrm_username"`
WinRMPassword *string `mapstructure:"winrm_password" cty:"winrm_password"`
WinRMHost *string `mapstructure:"winrm_host" cty:"winrm_host"`
@ -110,10 +110,13 @@ type FlatConfig struct {
// FlatMapstructure returns a new FlatConfig.
// FlatConfig is an auto-generated flat version of Config.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*Config) FlatMapstructure() interface{} { return new(FlatConfig) }
func (*Config) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatConfig)
}
// HCL2Spec returns the hcldec.Spec of a FlatConfig.
// This spec is used by HCL to read the fields of FlatConfig.
// HCL2Spec returns the hcl spec of a Config.
// This spec is used by HCL to read the fields of Config.
// The decoded values from this spec will then be applied to a FlatConfig.
func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"packer_build_name": &hcldec.AttrSpec{Name: "packer_build_name", Type: cty.String, Required: false},
@ -228,10 +231,13 @@ type FlatPlanInformation struct {
// FlatMapstructure returns a new FlatPlanInformation.
// FlatPlanInformation is an auto-generated flat version of PlanInformation.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*PlanInformation) FlatMapstructure() interface{} { return new(FlatPlanInformation) }
func (*PlanInformation) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatPlanInformation)
}
// HCL2Spec returns the hcldec.Spec of a FlatPlanInformation.
// This spec is used by HCL to read the fields of FlatPlanInformation.
// HCL2Spec returns the hcl spec of a PlanInformation.
// This spec is used by HCL to read the fields of PlanInformation.
// The decoded values from this spec will then be applied to a FlatPlanInformation.
func (*FlatPlanInformation) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"plan_name": &hcldec.AttrSpec{Name: "plan_name", Type: cty.String, Required: false},
@ -255,10 +261,13 @@ type FlatSharedImageGallery struct {
// FlatMapstructure returns a new FlatSharedImageGallery.
// FlatSharedImageGallery is an auto-generated flat version of SharedImageGallery.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*SharedImageGallery) FlatMapstructure() interface{} { return new(FlatSharedImageGallery) }
func (*SharedImageGallery) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatSharedImageGallery)
}
// HCL2Spec returns the hcldec.Spec of a FlatSharedImageGallery.
// This spec is used by HCL to read the fields of FlatSharedImageGallery.
// HCL2Spec returns the hcl spec of a SharedImageGallery.
// This spec is used by HCL to read the fields of SharedImageGallery.
// The decoded values from this spec will then be applied to a FlatSharedImageGallery.
func (*FlatSharedImageGallery) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"subscription": &hcldec.AttrSpec{Name: "subscription", Type: cty.String, Required: false},
@ -283,12 +292,13 @@ type FlatSharedImageGalleryDestination struct {
// FlatMapstructure returns a new FlatSharedImageGalleryDestination.
// FlatSharedImageGalleryDestination is an auto-generated flat version of SharedImageGalleryDestination.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*SharedImageGalleryDestination) FlatMapstructure() interface{} {
func (*SharedImageGalleryDestination) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatSharedImageGalleryDestination)
}
// HCL2Spec returns the hcldec.Spec of a FlatSharedImageGalleryDestination.
// This spec is used by HCL to read the fields of FlatSharedImageGalleryDestination.
// HCL2Spec returns the hcl spec of a SharedImageGalleryDestination.
// This spec is used by HCL to read the fields of SharedImageGalleryDestination.
// The decoded values from this spec will then be applied to a FlatSharedImageGalleryDestination.
func (*FlatSharedImageGalleryDestination) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"resource_group": &hcldec.AttrSpec{Name: "resource_group", Type: cty.String, Required: false},

View File

@ -26,7 +26,8 @@ var requiredConfigValues = []string{
}
func TestConfigShouldProvideReasonableDefaultValues(t *testing.T) {
c, _, err := newConfig(getArmBuilderConfiguration(), getPackerConfiguration())
var c Config
_, err := c.Prepare(getArmBuilderConfiguration(), getPackerConfiguration())
if err != nil {
t.Error("Expected configuration creation to succeed, but it failed!\n")
@ -63,7 +64,8 @@ func TestConfigShouldBeAbleToOverrideDefaultedValues(t *testing.T) {
builderValues["managed_image_storage_account_type"] = "Premium_LRS"
builderValues["disk_caching_type"] = "None"
c, _, err := newConfig(builderValues, getPackerConfiguration())
var c Config
_, err := c.Prepare(builderValues, getPackerConfiguration())
if err != nil {
t.Fatalf("newConfig failed: %s", err)
@ -99,7 +101,8 @@ func TestConfigShouldBeAbleToOverrideDefaultedValues(t *testing.T) {
}
func TestConfigShouldDefaultVMSizeToStandardA1(t *testing.T) {
c, _, _ := newConfig(getArmBuilderConfiguration(), getPackerConfiguration())
var c Config
c.Prepare(getArmBuilderConfiguration(), getPackerConfiguration())
if c.VMSize != "Standard_A1" {
t.Errorf("Expected 'VMSize' to default to 'Standard_A1', but got '%s'.", c.VMSize)
@ -107,7 +110,8 @@ func TestConfigShouldDefaultVMSizeToStandardA1(t *testing.T) {
}
func TestConfigShouldDefaultImageVersionToLatest(t *testing.T) {
c, _, _ := newConfig(getArmBuilderConfiguration(), getPackerConfiguration())
var c Config
c.Prepare(getArmBuilderConfiguration(), getPackerConfiguration())
if c.ImageVersion != "latest" {
t.Errorf("Expected 'ImageVersion' to default to 'latest', but got '%s'.", c.ImageVersion)
@ -127,7 +131,8 @@ func TestConfigShouldNotDefaultImageVersionIfCustomImage(t *testing.T) {
"communicator": "none",
}
c, _, _ := newConfig(config, getPackerConfiguration())
var c Config
c.Prepare(config, getPackerConfiguration())
if c.ImageVersion != "" {
t.Errorf("Expected 'ImageVersion' to empty, but got '%s'.", c.ImageVersion)
}
@ -153,7 +158,8 @@ func TestConfigShouldNormalizeOSTypeCase(t *testing.T) {
for k, v := range os_types {
for _, os_type := range v {
config["os_type"] = os_type
c, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Fatalf("Expected config to accept the value %q, but it did not", os_type)
}
@ -167,7 +173,8 @@ func TestConfigShouldNormalizeOSTypeCase(t *testing.T) {
bad_os_types := []string{"", "does-not-exist"}
for _, os_type := range bad_os_types {
config["os_type"] = os_type
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err == nil {
t.Fatalf("Expected config to not accept the value %q, but it did", os_type)
}
@ -191,7 +198,8 @@ func TestConfigShouldRejectCustomImageAndMarketPlace(t *testing.T) {
for _, x := range marketPlace {
config[x] = "ignore"
_, _, err := newConfig(config, packerConfiguration)
var c Config
_, err := c.Prepare(config, packerConfiguration)
if err == nil {
t.Errorf("Expected Config to reject image_url and %s, but it did not", x)
}
@ -212,7 +220,8 @@ func TestConfigVirtualNetworkNameIsOptional(t *testing.T) {
"virtual_network_name": "MyVirtualNetwork",
}
c, _, _ := newConfig(config, getPackerConfiguration())
var c Config
c.Prepare(config, getPackerConfiguration())
if c.VirtualNetworkName != "MyVirtualNetwork" {
t.Errorf("Expected Config to set virtual_network_name to MyVirtualNetwork, but got %q", c.VirtualNetworkName)
}
@ -241,7 +250,8 @@ func TestConfigVirtualNetworkResourceGroupNameMustBeSetWithVirtualNetworkName(t
"virtual_network_resource_group_name": "MyVirtualNetworkRG",
}
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err == nil {
t.Error("Expected Config to reject virtual_network_resource_group_name, if virtual_network_name is not set.")
}
@ -264,7 +274,8 @@ func TestConfigVirtualNetworkSubnetNameMustBeSetWithVirtualNetworkName(t *testin
"virtual_network_subnet_name": "MyVirtualNetworkRG",
}
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err == nil {
t.Error("Expected Config to reject virtual_network_subnet_name, if virtual_network_name is not set.")
}
@ -284,7 +295,8 @@ func TestConfigAllowedInboundIpAddressesIsOptional(t *testing.T) {
"virtual_network_name": "MyVirtualNetwork",
}
c, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Fatal(err)
}
@ -311,7 +323,8 @@ func TestConfigShouldAcceptCorrectInboundIpAddresses(t *testing.T) {
}
config["allowed_inbound_ip_addresses"] = ipValue0
c, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Fatal(err)
}
@ -321,7 +334,7 @@ func TestConfigShouldAcceptCorrectInboundIpAddresses(t *testing.T) {
}
config["allowed_inbound_ip_addresses"] = cidrValue2
c, _, err = newConfig(config, getPackerConfiguration())
_, err = c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Fatal(err)
}
@ -331,7 +344,7 @@ func TestConfigShouldAcceptCorrectInboundIpAddresses(t *testing.T) {
}
config["allowed_inbound_ip_addresses"] = []string{ipValue0, cidrValue2, ipValue1, cidrValue3}
c, _, err = newConfig(config, getPackerConfiguration())
_, err = c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Fatal(err)
}
@ -357,13 +370,14 @@ func TestConfigShouldRejectIncorrectInboundIpAddresses(t *testing.T) {
}
config["allowed_inbound_ip_addresses"] = []string{"127.0.0.1", "127.0.0.two"}
c, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err == nil {
t.Errorf("Expected configuration creation to fail, but it succeeded with the malformed allowed_inbound_ip_addresses set to %v", c.AllowedInboundIpAddresses)
}
config["allowed_inbound_ip_addresses"] = []string{"192.168.100.1000/24", "10.10.1.16/32"}
c, _, err = newConfig(config, getPackerConfiguration())
_, err = c.Prepare(config, getPackerConfiguration())
if err == nil {
// 192.168.100.1000/24 is invalid
t.Errorf("Expected configuration creation to fail, but it succeeded with the malformed allowed_inbound_ip_addresses set to %v", c.AllowedInboundIpAddresses)
@ -384,20 +398,22 @@ func TestConfigShouldRejectInboundIpAddressesWithVirtualNetwork(t *testing.T) {
"allowed_inbound_ip_addresses": "127.0.0.1",
}
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Fatal(err)
}
config["virtual_network_name"] = "some_vnet_name"
_, _, err = newConfig(config, getPackerConfiguration())
_, err = c.Prepare(config, getPackerConfiguration())
if err == nil {
t.Errorf("Expected configuration creation to fail, but it succeeded with allowed_inbound_ip_addresses and virtual_network_name both specified")
}
}
func TestConfigShouldDefaultToPublicCloud(t *testing.T) {
c, _, _ := newConfig(getArmBuilderConfiguration(), getPackerConfiguration())
var c Config
c.Prepare(getArmBuilderConfiguration(), getPackerConfiguration())
if c.ClientConfig.CloudEnvironmentName != "Public" {
t.Errorf("Expected 'CloudEnvironmentName' to default to 'Public', but got '%s'.", c.ClientConfig.CloudEnvironmentName)
@ -448,7 +464,8 @@ func TestConfigInstantiatesCorrectAzureEnvironment(t *testing.T) {
for _, x := range table {
config["cloud_environment_name"] = x.name
c, _, err := newConfig(config, packerConfiguration)
var c Config
_, err := c.Prepare(config, packerConfiguration)
if err != nil {
t.Fatal(err)
}
@ -463,7 +480,8 @@ func TestUserShouldProvideRequiredValues(t *testing.T) {
builderValues := getArmBuilderConfiguration()
// Ensure we can successfully create a config.
_, _, err := newConfig(builderValues, getPackerConfiguration())
var c Config
_, err := c.Prepare(builderValues, getPackerConfiguration())
if err != nil {
t.Error("Expected configuration creation to succeed, but it failed!\n")
t.Fatalf(" -> %+v\n", builderValues)
@ -474,7 +492,8 @@ func TestUserShouldProvideRequiredValues(t *testing.T) {
originalValue := builderValues[v]
delete(builderValues, v)
_, _, err := newConfig(builderValues, getPackerConfiguration())
var c Config
_, err := c.Prepare(builderValues, getPackerConfiguration())
if err == nil {
t.Error("Expected configuration creation to fail, but it succeeded!\n")
t.Fatalf(" -> %+v\n", builderValues)
@ -485,7 +504,8 @@ func TestUserShouldProvideRequiredValues(t *testing.T) {
}
func TestSystemShouldDefineRuntimeValues(t *testing.T) {
c, _, _ := newConfig(getArmBuilderConfiguration(), getPackerConfiguration())
var c Config
c.Prepare(getArmBuilderConfiguration(), getPackerConfiguration())
if c.Password == "" {
t.Errorf("Expected Password to not be empty, but it was '%s'!", c.Password)
@ -513,7 +533,8 @@ func TestSystemShouldDefineRuntimeValues(t *testing.T) {
}
func TestConfigShouldTransformToVirtualMachineCaptureParameters(t *testing.T) {
c, _, _ := newConfig(getArmBuilderConfiguration(), getPackerConfiguration())
var c Config
c.Prepare(getArmBuilderConfiguration(), getPackerConfiguration())
parameters := c.toVirtualMachineCaptureParameters()
if *parameters.DestinationContainerName != c.CaptureContainerName {
@ -530,7 +551,8 @@ func TestConfigShouldTransformToVirtualMachineCaptureParameters(t *testing.T) {
}
func TestConfigShouldSupportPackersConfigElements(t *testing.T) {
c, _, err := newConfig(
var c Config
_, err := c.Prepare(
getArmBuilderConfiguration(),
getPackerConfiguration(),
getPackerCommunicatorConfiguration())
@ -554,7 +576,8 @@ func TestWinRMConfigShouldSetRoundTripDecorator(t *testing.T) {
config["winrm_username"] = "username"
config["winrm_password"] = "password"
c, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Fatal(err)
}
@ -579,7 +602,8 @@ func TestUserDeviceLoginIsEnabledForLinux(t *testing.T) {
"communicator": "none",
}
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Fatalf("failed to use device login for Linux: %s", err)
}
@ -610,7 +634,8 @@ func TestConfigShouldRejectMalformedCaptureNamePrefix(t *testing.T) {
for _, x := range wellFormedCaptureNamePrefix {
config["capture_name_prefix"] = x
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Errorf("Expected test to pass, but it failed with the well-formed capture_name_prefix set to %q.", x)
@ -628,7 +653,8 @@ func TestConfigShouldRejectMalformedCaptureNamePrefix(t *testing.T) {
for _, x := range malformedCaptureNamePrefix {
config["capture_name_prefix"] = x
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err == nil {
t.Errorf("Expected test to fail, but it succeeded with the malformed capture_name_prefix set to %q.", x)
@ -660,7 +686,8 @@ func TestConfigShouldRejectMalformedCaptureContainerName(t *testing.T) {
for _, x := range wellFormedCaptureContainerName {
config["capture_container_name"] = x
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Errorf("Expected test to pass, but it failed with the well-formed capture_container_name set to %q.", x)
@ -678,7 +705,8 @@ func TestConfigShouldRejectMalformedCaptureContainerName(t *testing.T) {
for _, x := range malformedCaptureContainerName {
config["capture_container_name"] = x
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err == nil {
t.Errorf("Expected test to fail, but it succeeded with the malformed capture_container_name set to %q.", x)
@ -710,7 +738,8 @@ func TestConfigShouldRejectMalformedManagedImageOSDiskSnapshotName(t *testing.T)
for _, x := range wellFormedManagedImageOSDiskSnapshotName {
config["managed_image_os_disk_snapshot_name"] = x
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Errorf("Expected test to pass, but it failed with the well-formed managed_image_os_disk_snapshot_name set to %q.", x)
@ -727,7 +756,8 @@ func TestConfigShouldRejectMalformedManagedImageOSDiskSnapshotName(t *testing.T)
for _, x := range malformedManagedImageOSDiskSnapshotName {
config["managed_image_os_disk_snapshot_name"] = x
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err == nil {
t.Errorf("Expected test to fail, but it succeeded with the malformed managed_image_os_disk_snapshot_name set to %q.", x)
@ -760,7 +790,8 @@ func TestConfigShouldRejectMalformedManagedImageDataDiskSnapshotPrefix(t *testin
for _, x := range wellFormedManagedImageDataDiskSnapshotPrefix {
config["managed_image_data_disk_snapshot_prefix"] = x
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Errorf("Expected test to pass, but it failed with the well-formed managed_image_data_disk_snapshot_prefix set to %q.", x)
@ -777,7 +808,8 @@ func TestConfigShouldRejectMalformedManagedImageDataDiskSnapshotPrefix(t *testin
for _, x := range malformedManagedImageDataDiskSnapshotPrefix {
config["managed_image_data_disk_snapshot_prefix"] = x
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err == nil {
t.Errorf("Expected test to fail, but it succeeded with the malformed managed_image_data_disk_snapshot_prefix set to %q.", x)
@ -805,7 +837,8 @@ func TestConfigShouldAcceptTags(t *testing.T) {
},
}
c, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Fatal(err)
@ -855,7 +888,8 @@ func TestConfigShouldRejectTagsInExcessOf15AcceptTags(t *testing.T) {
"azure_tags": tooManyTags,
}
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err == nil {
t.Fatal("expected config to reject based on an excessive amount of tags (> 15)")
@ -887,7 +921,8 @@ func TestConfigShouldRejectExcessiveTagNameLength(t *testing.T) {
"azure_tags": tags,
}
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err == nil {
t.Fatal("expected config to reject tag name based on length (> 512)")
}
@ -918,7 +953,8 @@ func TestConfigShouldRejectExcessiveTagValueLength(t *testing.T) {
"azure_tags": tags,
}
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err == nil {
t.Fatal("expected config to reject tag value based on length (> 256)")
}
@ -935,7 +971,8 @@ func TestConfigZoneResilientShouldDefaultToFalse(t *testing.T) {
"os_type": "linux",
}
c, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Fatal(err)
}
@ -958,7 +995,8 @@ func TestConfigZoneResilientSetFromConfig(t *testing.T) {
"managed_image_zone_resilient": true,
}
c, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Fatal(err)
}
@ -986,7 +1024,8 @@ func TestConfigShouldRejectMissingCustomDataFile(t *testing.T) {
"custom_data_file": "/this/file/does/not/exist",
}
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err == nil {
t.Fatal("expected config to reject missing custom data file")
}
@ -1006,7 +1045,8 @@ func TestConfigShouldRejectManagedImageOSDiskSnapshotNameWithoutManagedImageName
"os_type": constants.Target_Linux,
}
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err == nil {
t.Fatal("expected config to reject Managed Image build with OS disk snapshot name but without managed image name")
}
@ -1026,7 +1066,8 @@ func TestConfigShouldRejectManagedImageOSDiskSnapshotNameWithoutManagedImageReso
"os_type": constants.Target_Linux,
}
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err == nil {
t.Fatal("expected config to reject Managed Image build with OS disk snapshot name but without managed image resource group name")
}
@ -1046,7 +1087,8 @@ func TestConfigShouldRejectImageDataDiskSnapshotPrefixWithoutManagedImageName(t
"os_type": constants.Target_Linux,
}
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err == nil {
t.Fatal("expected config to reject Managed Image build with data disk snapshot prefix but without managed image name")
}
@ -1066,7 +1108,8 @@ func TestConfigShouldRejectImageDataDiskSnapshotPrefixWithoutManagedImageResourc
"os_type": constants.Target_Linux,
}
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err == nil {
t.Fatal("expected config to reject Managed Image build with data disk snapshot prefix but without managed image resource group name")
}
@ -1088,7 +1131,8 @@ func TestConfigShouldAcceptManagedImageOSDiskSnapshotNameAndManagedImageDataDisk
"os_type": constants.Target_Linux,
}
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Fatal("expected config to accept platform managed image build")
}
@ -1109,7 +1153,8 @@ func TestConfigShouldRejectManagedImageOSDiskSnapshotNameAndManagedImageDataDisk
"os_type": constants.Target_Linux,
}
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err == nil {
t.Fatal("expected config to reject Managed Image build with data disk snapshot prefix and OS disk snapshot name with capture container name")
}
@ -1130,7 +1175,8 @@ func TestConfigShouldRejectManagedImageOSDiskSnapshotNameAndManagedImageDataDisk
"os_type": constants.Target_Linux,
}
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err == nil {
t.Fatal("expected config to reject Managed Image build with data disk snapshot prefix and OS disk snapshot name with capture name prefix")
}
@ -1151,7 +1197,8 @@ func TestConfigShouldAcceptPlatformManagedImageBuild(t *testing.T) {
"os_type": constants.Target_Linux,
}
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Fatal("expected config to accept platform managed image build")
}
@ -1175,7 +1222,8 @@ func TestConfigShouldRejectVhdAndManagedImageOutput(t *testing.T) {
"os_type": constants.Target_Linux,
}
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err == nil {
t.Fatal("expected config to reject VHD and Managed Image build")
}
@ -1195,7 +1243,8 @@ func TestConfigShouldRejectManagedImageSourceAndVhdOutput(t *testing.T) {
"os_type": constants.Target_Linux,
}
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err == nil {
t.Fatal("expected config to reject VHD and Managed Image build")
}
@ -1218,7 +1267,8 @@ func TestConfigShouldRejectCustomAndPlatformManagedImageBuild(t *testing.T) {
"os_type": constants.Target_Linux,
}
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err == nil {
t.Fatal("expected config to reject custom and platform input for a managed image build")
}
@ -1239,7 +1289,8 @@ func TestConfigShouldRejectCustomAndImageUrlForManagedImageBuild(t *testing.T) {
"os_type": constants.Target_Linux,
}
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err == nil {
t.Fatal("expected config to reject custom and platform input for a managed image build")
}
@ -1260,7 +1311,8 @@ func TestConfigShouldRejectMalformedManageImageStorageAccountTypes(t *testing.T)
"os_type": constants.Target_Linux,
}
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err == nil {
t.Fatal("expected config to reject custom and platform input for a managed image build")
}
@ -1281,7 +1333,8 @@ func TestConfigShouldRejectMalformedDiskCachingType(t *testing.T) {
"os_type": constants.Target_Linux,
}
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err == nil {
t.Fatal("expected config to reject custom and platform input for a managed image build")
}
@ -1305,7 +1358,8 @@ func TestConfigShouldAcceptManagedImageStorageAccountTypes(t *testing.T) {
for _, x := range storage_account_types {
config["managed_image_storage_account_type"] = x
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Fatalf("expected config to accept a managed_image_storage_account_type of %q", x)
}
@ -1330,7 +1384,8 @@ func TestConfigShouldAcceptDiskCachingTypes(t *testing.T) {
for _, x := range storage_account_types {
config["disk_caching_type"] = x
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Fatalf("expected config to accept a disk_caching_type of %q", x)
}
@ -1355,7 +1410,8 @@ func TestConfigShouldRejectTempAndBuildResourceGroupName(t *testing.T) {
"build_resource_group_name": "rgn00",
}
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err == nil {
t.Fatal("expected config to reject the use of both temp_resource_group_name and build_resource_group_name")
}
@ -1402,7 +1458,8 @@ func TestConfigShouldRejectInvalidResourceGroupNames(t *testing.T) {
for _, y := range tests {
config[x] = y.name
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if !y.ok && err == nil {
t.Errorf("expected config to reject %q for setting %q", y.name, x)
} else if y.ok && err != nil {
@ -1452,7 +1509,8 @@ func TestConfigShouldRejectManagedDiskNames(t *testing.T) {
for _, y := range testsResourceGroupNames {
config[settingUnderTest] = y.name
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if !y.ok && err == nil {
t.Errorf("expected config to reject %q for setting %q", y.name, settingUnderTest)
} else if y.ok && err != nil {
@ -1486,7 +1544,8 @@ func TestConfigShouldRejectManagedDiskNames(t *testing.T) {
for _, y := range testNames {
config[settingUnderTest] = y.name
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if !y.ok && err == nil {
t.Logf("expected config to reject %q for setting %q", y.name, settingUnderTest)
} else if y.ok && err != nil {
@ -1496,7 +1555,8 @@ func TestConfigShouldRejectManagedDiskNames(t *testing.T) {
}
func TestConfigAdditionalDiskDefaultIsNil(t *testing.T) {
c, _, _ := newConfig(getArmBuilderConfiguration(), getPackerConfiguration())
var c Config
c.Prepare(getArmBuilderConfiguration(), getPackerConfiguration())
if c.AdditionalDiskSize != nil {
t.Errorf("Expected Config to not have a set of additional disks, but got a non nil value")
}
@ -1519,7 +1579,8 @@ func TestConfigAdditionalDiskOverrideDefault(t *testing.T) {
"disk_additional_size": {32, 64},
}
c, _, _ := newConfig(config, diskconfig, getPackerConfiguration())
var c Config
c.Prepare(config, diskconfig, getPackerConfiguration())
if c.AdditionalDiskSize == nil {
t.Errorf("Expected Config to have a set of additional disks, but got nil")
}
@ -1561,19 +1622,20 @@ func TestPlanInfoConfiguration(t *testing.T) {
}
config["plan_info"] = planInfo
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err == nil {
t.Fatal("expected config to reject the use of plan_name without plan_product and plan_publisher")
}
planInfo["plan_product"] = "--plan-product--"
_, _, err = newConfig(config, getPackerConfiguration())
_, err = c.Prepare(config, getPackerConfiguration())
if err == nil {
t.Fatal("expected config to reject the use of plan_name and plan_product without plan_publisher")
}
planInfo["plan_publisher"] = "--plan-publisher--"
c, _, err := newConfig(config, getPackerConfiguration())
_, err = c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Fatalf("expected config to accept a complete plan configuration: %s", err)
}
@ -1610,7 +1672,8 @@ func TestPlanInfoPromotionCode(t *testing.T) {
},
}
c, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Fatalf("expected config to accept plan_info configuration, but got %s", err)
}
@ -1659,7 +1722,8 @@ func TestPlanInfoTooManyTagsErrors(t *testing.T) {
},
}
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err == nil {
t.Fatal("expected config to reject configuration due to excess tags")
}
@ -1682,7 +1746,8 @@ func TestConfigShouldAllowTempNameOverrides(t *testing.T) {
"temp_compute_name": "myTempComputeName",
}
c, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Errorf("newConfig failed with %q", err)
}
@ -1716,7 +1781,8 @@ func TestConfigShouldAllowAsyncResourceGroupOverride(t *testing.T) {
"async_resourcegroup_delete": "true",
}
c, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Errorf("newConfig failed with %q", err)
}
@ -1738,7 +1804,8 @@ func TestConfigShouldAllowAsyncResourceGroupOverrideNoValue(t *testing.T) {
"managed_image_resource_group_name": "ignore",
}
c, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Errorf("newConfig failed with %q", err)
}
@ -1761,10 +1828,10 @@ func TestConfigShouldAllowAsyncResourceGroupOverrideBadValue(t *testing.T) {
"async_resourcegroup_delete": "asdasda",
}
c, _, err := newConfig(config, getPackerConfiguration())
if err != nil && c == nil {
t.Log("newConfig failed which is expected ", err)
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Log("newConfig failed which is expected ", err)
}
}
@ -1782,7 +1849,8 @@ func TestConfigShouldAllowSharedImageGalleryOptions(t *testing.T) {
},
}
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err == nil {
t.Log("expected config to accept Shared Image Gallery options", err)
}
@ -1807,7 +1875,8 @@ func TestConfigShouldRejectSharedImageGalleryWithVhdTarget(t *testing.T) {
"capture_name_prefix": "ignore",
}
_, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Log("expected an error if Shared Image Gallery source is used with VHD target", err)
}
@ -1818,7 +1887,8 @@ func Test_GivenZoneNotSupportingResiliency_ConfigValidate_ShouldWarn(t *testing.
builderValues["managed_image_zone_resilient"] = "true"
builderValues["location"] = "ukwest"
c, _, err := newConfig(builderValues, getPackerConfiguration())
var c Config
_, err := c.Prepare(builderValues, getPackerConfiguration())
if err != nil {
t.Errorf("newConfig failed with %q", err)
}
@ -1836,7 +1906,8 @@ func Test_GivenZoneSupportingResiliency_ConfigValidate_ShouldNotWarn(t *testing.
builderValues["managed_image_zone_resilient"] = "true"
builderValues["location"] = "westeurope"
c, _, err := newConfig(builderValues, getPackerConfiguration())
var c Config
_, err := c.Prepare(builderValues, getPackerConfiguration())
if err != nil {
t.Errorf("newConfig failed with %q", err)
}

View File

@ -5,14 +5,15 @@ import (
)
func TestResourceResolverIgnoresEmptyVirtualNetworkName(t *testing.T) {
c, _, _ := newConfig(getArmBuilderConfiguration(), getPackerConfiguration())
var c Config
c.Prepare(getArmBuilderConfiguration(), getPackerConfiguration())
if c.VirtualNetworkName != "" {
t.Fatalf("Expected VirtualNetworkName to be empty by default")
}
sut := newTestResourceResolver()
sut.findVirtualNetworkResourceGroup = nil // assert that this is not even called
sut.Resolve(c)
sut.Resolve(&c)
if c.VirtualNetworkName != "" {
t.Fatalf("Expected VirtualNetworkName to be empty")
@ -25,7 +26,8 @@ func TestResourceResolverIgnoresEmptyVirtualNetworkName(t *testing.T) {
// If the user fully specified the virtual network name and resource group then
// there is no need to do a lookup.
func TestResourceResolverIgnoresSetVirtualNetwork(t *testing.T) {
c, _, _ := newConfig(getArmBuilderConfiguration(), getPackerConfiguration())
var c Config
c.Prepare(getArmBuilderConfiguration(), getPackerConfiguration())
c.VirtualNetworkName = "--virtual-network-name--"
c.VirtualNetworkResourceGroupName = "--virtual-network-resource-group-name--"
c.VirtualNetworkSubnetName = "--virtual-network-subnet-name--"
@ -33,7 +35,7 @@ func TestResourceResolverIgnoresSetVirtualNetwork(t *testing.T) {
sut := newTestResourceResolver()
sut.findVirtualNetworkResourceGroup = nil // assert that this is not even called
sut.findVirtualNetworkSubnet = nil // assert that this is not even called
sut.Resolve(c)
sut.Resolve(&c)
if c.VirtualNetworkName != "--virtual-network-name--" {
t.Fatalf("Expected VirtualNetworkName to be --virtual-network-name--")
@ -49,11 +51,12 @@ func TestResourceResolverIgnoresSetVirtualNetwork(t *testing.T) {
// If the user set virtual network name then the code should resolve virtual network
// resource group name.
func TestResourceResolverSetVirtualNetworkResourceGroupName(t *testing.T) {
c, _, _ := newConfig(getArmBuilderConfiguration(), getPackerConfiguration())
var c Config
c.Prepare(getArmBuilderConfiguration(), getPackerConfiguration())
c.VirtualNetworkName = "--virtual-network-name--"
sut := newTestResourceResolver()
sut.Resolve(c)
sut.Resolve(&c)
if c.VirtualNetworkResourceGroupName != "findVirtualNetworkResourceGroup is mocked" {
t.Fatalf("Expected VirtualNetworkResourceGroupName to be 'findVirtualNetworkResourceGroup is mocked'")

View File

@ -3,6 +3,7 @@ package arm
import (
"context"
"fmt"
"github.com/Azure/azure-sdk-for-go/services/compute/mgmt/2019-03-01/compute"
"github.com/hashicorp/packer/builder/azure/common/constants"
"github.com/hashicorp/packer/helper/multistep"

View File

@ -2,9 +2,10 @@ package arm
import (
"context"
"testing"
"github.com/hashicorp/packer/builder/azure/common/constants"
"github.com/hashicorp/packer/helper/multistep"
"testing"
)
func TestStepPublishToSharedImageGalleryShouldNotPublishForVhd(t *testing.T) {

View File

@ -13,8 +13,9 @@ import (
// Ensure the link values are not set, and the concrete values are set.
func TestVirtualMachineDeployment00(t *testing.T) {
c, _, _ := newConfig(getArmBuilderConfiguration(), getPackerConfiguration())
deployment, err := GetVirtualMachineDeployment(c)
var c Config
c.Prepare(getArmBuilderConfiguration(), getPackerConfiguration())
deployment, err := GetVirtualMachineDeployment(&c)
if err != nil {
t.Fatal(err)
}
@ -42,8 +43,9 @@ func TestVirtualMachineDeployment00(t *testing.T) {
// Ensure the Virtual Machine template is a valid JSON document.
func TestVirtualMachineDeployment01(t *testing.T) {
c, _, _ := newConfig(getArmBuilderConfiguration(), getPackerConfiguration())
deployment, err := GetVirtualMachineDeployment(c)
var c Config
c.Prepare(getArmBuilderConfiguration(), getPackerConfiguration())
deployment, err := GetVirtualMachineDeployment(&c)
if err != nil {
t.Fatal(err)
}
@ -56,8 +58,9 @@ func TestVirtualMachineDeployment01(t *testing.T) {
// Ensure the Virtual Machine template parameters are correct.
func TestVirtualMachineDeployment02(t *testing.T) {
c, _, _ := newConfig(getArmBuilderConfiguration(), getPackerConfiguration())
deployment, err := GetVirtualMachineDeployment(c)
var c Config
c.Prepare(getArmBuilderConfiguration(), getPackerConfiguration())
deployment, err := GetVirtualMachineDeployment(&c)
if err != nil {
t.Fatal(err)
}
@ -104,8 +107,9 @@ func TestVirtualMachineDeployment03(t *testing.T) {
m["image_sku"] = "ImageSku"
m["image_version"] = "ImageVersion"
c, _, _ := newConfig(m, getPackerConfiguration())
deployment, err := GetVirtualMachineDeployment(c)
var c Config
c.Prepare(m, getPackerConfiguration())
deployment, err := GetVirtualMachineDeployment(&c)
if err != nil {
t.Fatal(err)
}
@ -130,12 +134,13 @@ func TestVirtualMachineDeployment04(t *testing.T) {
"communicator": "none",
}
c, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Fatal(err)
}
deployment, err := GetVirtualMachineDeployment(c)
deployment, err := GetVirtualMachineDeployment(&c)
if err != nil {
t.Fatal(err)
}
@ -162,12 +167,13 @@ func TestVirtualMachineDeployment05(t *testing.T) {
"virtual_network_subnet_name": "virtualNetworkSubnetName",
}
c, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Fatal(err)
}
deployment, err := GetVirtualMachineDeployment(c)
deployment, err := GetVirtualMachineDeployment(&c)
if err != nil {
t.Fatal(err)
}
@ -197,12 +203,13 @@ func TestVirtualMachineDeployment06(t *testing.T) {
},
}
c, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Fatal(err)
}
deployment, err := GetVirtualMachineDeployment(c)
deployment, err := GetVirtualMachineDeployment(&c)
if err != nil {
t.Fatal(err)
}
@ -227,7 +234,8 @@ func TestVirtualMachineDeployment07(t *testing.T) {
"communicator": "none",
}
c, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Fatal(err)
}
@ -247,7 +255,7 @@ growpart:
base64CustomData := base64.StdEncoding.EncodeToString([]byte(customData))
c.customData = base64CustomData
deployment, err := GetVirtualMachineDeployment(c)
deployment, err := GetVirtualMachineDeployment(&c)
if err != nil {
t.Fatal(err)
}
@ -271,12 +279,13 @@ func TestVirtualMachineDeployment08(t *testing.T) {
"managed_image_resource_group_name": "ManagedImageResourceGroupName",
}
c, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Fatal(err)
}
deployment, err := GetVirtualMachineDeployment(c)
deployment, err := GetVirtualMachineDeployment(&c)
if err != nil {
t.Fatal(err)
}
@ -302,12 +311,13 @@ func TestVirtualMachineDeployment09(t *testing.T) {
"managed_image_resource_group_name": "ManagedImageResourceGroupName",
}
c, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Fatal(err)
}
deployment, err := GetVirtualMachineDeployment(c)
deployment, err := GetVirtualMachineDeployment(&c)
if err != nil {
t.Fatal(err)
}
@ -339,12 +349,13 @@ func TestVirtualMachineDeployment10(t *testing.T) {
"managed_image_resource_group_name": "ManagedImageResourceGroupName",
}
c, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Fatal(err)
}
deployment, err := GetVirtualMachineDeployment(c)
deployment, err := GetVirtualMachineDeployment(&c)
if err != nil {
t.Fatal(err)
}
@ -375,12 +386,13 @@ func TestVirtualMachineDeployment11(t *testing.T) {
"capture_container_name": "packerimages",
}
c, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Fatal(err)
}
deployment, err := GetVirtualMachineDeployment(c)
deployment, err := GetVirtualMachineDeployment(&c)
if err != nil {
t.Fatal(err)
}
@ -409,12 +421,13 @@ func TestVirtualMachineDeployment12(t *testing.T) {
"managed_image_resource_group_name": "ManagedImageResourceGroupName",
}
c, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Fatal(err)
}
deployment, err := GetVirtualMachineDeployment(c)
deployment, err := GetVirtualMachineDeployment(&c)
if err != nil {
t.Fatal(err)
}
@ -442,13 +455,14 @@ func TestVirtualMachineDeployment13(t *testing.T) {
"allowed_inbound_ip_addresses": []string{"127.0.0.1", "192.168.100.0/24"},
}
c, _, err := newConfig(config, getPackerConfiguration())
var c Config
_, err := c.Prepare(config, getPackerConfiguration())
if err != nil {
t.Fatal(err)
}
c.tmpKeyVaultName = "--keyvault-name--"
deployment, err := GetVirtualMachineDeployment(c)
deployment, err := GetVirtualMachineDeployment(&c)
if err != nil {
t.Fatal(err)
}
@ -461,8 +475,9 @@ func TestVirtualMachineDeployment13(t *testing.T) {
// Ensure the link values are not set, and the concrete values are set.
func TestKeyVaultDeployment00(t *testing.T) {
c, _, _ := newConfig(getArmBuilderConfiguration(), getPackerConfiguration())
deployment, err := GetKeyVaultDeployment(c)
var c Config
c.Prepare(getArmBuilderConfiguration(), getPackerConfiguration())
deployment, err := GetKeyVaultDeployment(&c)
if err != nil {
t.Fatal(err)
}
@ -490,8 +505,9 @@ func TestKeyVaultDeployment00(t *testing.T) {
// Ensure the KeyVault template is a valid JSON document.
func TestKeyVaultDeployment01(t *testing.T) {
c, _, _ := newConfig(getArmBuilderConfiguration(), getPackerConfiguration())
deployment, err := GetKeyVaultDeployment(c)
var c Config
c.Prepare(getArmBuilderConfiguration(), getPackerConfiguration())
deployment, err := GetKeyVaultDeployment(&c)
if err != nil {
t.Fatal(err)
}
@ -504,9 +520,10 @@ func TestKeyVaultDeployment01(t *testing.T) {
// Ensure the KeyVault template parameters are correct.
func TestKeyVaultDeployment02(t *testing.T) {
c, _, _ := newConfig(getArmBuilderConfigurationWithWindows(), getPackerConfiguration())
var c Config
c.Prepare(getArmBuilderConfigurationWithWindows(), getPackerConfiguration())
deployment, err := GetKeyVaultDeployment(c)
deployment, err := GetKeyVaultDeployment(&c)
if err != nil {
t.Fatal(err)
}
@ -546,8 +563,9 @@ func TestKeyVaultDeployment03(t *testing.T) {
},
}
c, _, _ := newConfig(tags, getArmBuilderConfigurationWithWindows(), getPackerConfiguration())
deployment, err := GetKeyVaultDeployment(c)
var c Config
c.Prepare(tags, getArmBuilderConfigurationWithWindows(), getPackerConfiguration())
deployment, err := GetKeyVaultDeployment(&c)
if err != nil {
t.Fatal(err)
}
@ -567,8 +585,9 @@ func TestPlanInfo01(t *testing.T) {
},
}
c, _, _ := newConfig(planInfo, getArmBuilderConfiguration(), getPackerConfiguration())
deployment, err := GetVirtualMachineDeployment(c)
var c Config
c.Prepare(planInfo, getArmBuilderConfiguration(), getPackerConfiguration())
deployment, err := GetVirtualMachineDeployment(&c)
if err != nil {
t.Fatal(err)
}
@ -592,8 +611,9 @@ func TestPlanInfo02(t *testing.T) {
},
}
c, _, _ := newConfig(planInfo, getArmBuilderConfiguration(), getPackerConfiguration())
deployment, err := GetVirtualMachineDeployment(c)
var c Config
c.Prepare(planInfo, getArmBuilderConfiguration(), getPackerConfiguration())
deployment, err := GetVirtualMachineDeployment(&c)
if err != nil {
t.Fatal(err)
}

View File

@ -1,4 +1,5 @@
//go:generate struct-markdown
//go:generate mapstructure-to-hcl2 -type Config
// Package chroot is able to create an Azure managed image without requiring the
// launch of a new virtual machine for every build. It does this by attaching and
@ -14,6 +15,7 @@ import (
"runtime"
"strings"
"github.com/hashicorp/hcl/v2/hcldec"
azcommon "github.com/hashicorp/packer/builder/azure/common"
"github.com/hashicorp/packer/builder/azure/common/client"
"github.com/hashicorp/packer/common"
@ -116,6 +118,8 @@ type Builder struct {
runner multistep.Runner
}
func (b *Builder) ConfigSpec() hcldec.ObjectSpec { return b.config.FlatMapstructure().HCL2Spec() }
func (b *Builder) Prepare(raws ...interface{}) ([]string, error) {
b.config.ctx.Funcs = azcommon.TemplateFuncs
b.config.ctx.Funcs["vm"] = CreateVMMetadataTemplateFunc()

View File

@ -0,0 +1,92 @@
// Code generated by "mapstructure-to-hcl2 -type Config"; DO NOT EDIT.
package chroot
import (
"github.com/hashicorp/hcl/v2/hcldec"
"github.com/zclconf/go-cty/cty"
)
// FlatConfig is an auto-generated flat version of Config.
// Where the contents of a field with a `mapstructure:,squash` tag are bubbled up.
type FlatConfig struct {
PackerBuildName *string `mapstructure:"packer_build_name" cty:"packer_build_name"`
PackerBuilderType *string `mapstructure:"packer_builder_type" cty:"packer_builder_type"`
PackerDebug *bool `mapstructure:"packer_debug" cty:"packer_debug"`
PackerForce *bool `mapstructure:"packer_force" cty:"packer_force"`
PackerOnError *string `mapstructure:"packer_on_error" cty:"packer_on_error"`
PackerUserVars map[string]string `mapstructure:"packer_user_variables" cty:"packer_user_variables"`
PackerSensitiveVars []string `mapstructure:"packer_sensitive_variables" cty:"packer_sensitive_variables"`
CloudEnvironmentName *string `mapstructure:"cloud_environment_name" required:"false" cty:"cloud_environment_name"`
ClientID *string `mapstructure:"client_id" cty:"client_id"`
ClientSecret *string `mapstructure:"client_secret" cty:"client_secret"`
ClientCertPath *string `mapstructure:"client_cert_path" cty:"client_cert_path"`
ClientJWT *string `mapstructure:"client_jwt" cty:"client_jwt"`
ObjectID *string `mapstructure:"object_id" cty:"object_id"`
TenantID *string `mapstructure:"tenant_id" required:"false" cty:"tenant_id"`
SubscriptionID *string `mapstructure:"subscription_id" cty:"subscription_id"`
FromScratch *bool `mapstructure:"from_scratch" cty:"from_scratch"`
Source *string `mapstructure:"source" required:"true" cty:"source"`
CommandWrapper *string `mapstructure:"command_wrapper" cty:"command_wrapper"`
PreMountCommands []string `mapstructure:"pre_mount_commands" cty:"pre_mount_commands"`
MountOptions []string `mapstructure:"mount_options" cty:"mount_options"`
MountPartition *string `mapstructure:"mount_partition" cty:"mount_partition"`
MountPath *string `mapstructure:"mount_path" cty:"mount_path"`
PostMountCommands []string `mapstructure:"post_mount_commands" cty:"post_mount_commands"`
ChrootMounts [][]string `mapstructure:"chroot_mounts" cty:"chroot_mounts"`
CopyFiles []string `mapstructure:"copy_files" cty:"copy_files"`
TemporaryOSDiskName *string `mapstructure:"temporary_os_disk_name" cty:"temporary_os_disk_name"`
OSDiskSizeGB *int32 `mapstructure:"os_disk_size_gb" cty:"os_disk_size_gb"`
OSDiskStorageAccountType *string `mapstructure:"os_disk_storage_account_type" cty:"os_disk_storage_account_type"`
OSDiskCacheType *string `mapstructure:"os_disk_cache_type" cty:"os_disk_cache_type"`
OSDiskSkipCleanup *bool `mapstructure:"os_disk_skip_cleanup" cty:"os_disk_skip_cleanup"`
ImageResourceID *string `mapstructure:"image_resource_id" required:"true" cty:"image_resource_id"`
ImageHyperVGeneration *string `mapstructure:"image_hyperv_generation" cty:"image_hyperv_generation"`
}
// FlatMapstructure returns a new FlatConfig.
// FlatConfig is an auto-generated flat version of Config.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*Config) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatConfig)
}
// HCL2Spec returns the hcl spec of a Config.
// This spec is used by HCL to read the fields of Config.
// The decoded values from this spec will then be applied to a FlatConfig.
func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"packer_build_name": &hcldec.AttrSpec{Name: "packer_build_name", Type: cty.String, Required: false},
"packer_builder_type": &hcldec.AttrSpec{Name: "packer_builder_type", Type: cty.String, Required: false},
"packer_debug": &hcldec.AttrSpec{Name: "packer_debug", Type: cty.Bool, Required: false},
"packer_force": &hcldec.AttrSpec{Name: "packer_force", Type: cty.Bool, Required: false},
"packer_on_error": &hcldec.AttrSpec{Name: "packer_on_error", Type: cty.String, Required: false},
"packer_user_variables": &hcldec.BlockAttrsSpec{TypeName: "packer_user_variables", ElementType: cty.String, Required: false},
"packer_sensitive_variables": &hcldec.AttrSpec{Name: "packer_sensitive_variables", Type: cty.List(cty.String), Required: false},
"cloud_environment_name": &hcldec.AttrSpec{Name: "cloud_environment_name", Type: cty.String, Required: false},
"client_id": &hcldec.AttrSpec{Name: "client_id", Type: cty.String, Required: false},
"client_secret": &hcldec.AttrSpec{Name: "client_secret", Type: cty.String, Required: false},
"client_cert_path": &hcldec.AttrSpec{Name: "client_cert_path", Type: cty.String, Required: false},
"client_jwt": &hcldec.AttrSpec{Name: "client_jwt", Type: cty.String, Required: false},
"object_id": &hcldec.AttrSpec{Name: "object_id", Type: cty.String, Required: false},
"tenant_id": &hcldec.AttrSpec{Name: "tenant_id", Type: cty.String, Required: false},
"subscription_id": &hcldec.AttrSpec{Name: "subscription_id", Type: cty.String, Required: false},
"from_scratch": &hcldec.AttrSpec{Name: "from_scratch", Type: cty.Bool, Required: false},
"source": &hcldec.AttrSpec{Name: "source", Type: cty.String, Required: false},
"command_wrapper": &hcldec.AttrSpec{Name: "command_wrapper", Type: cty.String, Required: false},
"pre_mount_commands": &hcldec.AttrSpec{Name: "pre_mount_commands", Type: cty.List(cty.String), Required: false},
"mount_options": &hcldec.AttrSpec{Name: "mount_options", Type: cty.List(cty.String), Required: false},
"mount_partition": &hcldec.AttrSpec{Name: "mount_partition", Type: cty.String, Required: false},
"mount_path": &hcldec.AttrSpec{Name: "mount_path", Type: cty.String, Required: false},
"post_mount_commands": &hcldec.AttrSpec{Name: "post_mount_commands", Type: cty.List(cty.String), Required: false},
"chroot_mounts": &hcldec.BlockListSpec{TypeName: "chroot_mounts", Nested: &hcldec.AttrSpec{Name: "chroot_mounts", Type: cty.List(cty.String), Required: false}},
"copy_files": &hcldec.AttrSpec{Name: "copy_files", Type: cty.List(cty.String), Required: false},
"temporary_os_disk_name": &hcldec.AttrSpec{Name: "temporary_os_disk_name", Type: cty.String, Required: false},
"os_disk_size_gb": &hcldec.AttrSpec{Name: "os_disk_size_gb", Type: cty.Number, Required: false},
"os_disk_storage_account_type": &hcldec.AttrSpec{Name: "os_disk_storage_account_type", Type: cty.String, Required: false},
"os_disk_cache_type": &hcldec.AttrSpec{Name: "os_disk_cache_type", Type: cty.String, Required: false},
"os_disk_skip_cleanup": &hcldec.AttrSpec{Name: "os_disk_skip_cleanup", Type: cty.Bool, Required: false},
"image_resource_id": &hcldec.AttrSpec{Name: "image_resource_id", Type: cty.String, Required: false},
"image_hyperv_generation": &hcldec.AttrSpec{Name: "image_hyperv_generation", Type: cty.String, Required: false},
}
return s
}

View File

@ -2,9 +2,10 @@ package chroot
import (
"context"
"github.com/Azure/go-autorest/autorest/to"
"testing"
"github.com/Azure/go-autorest/autorest/to"
"github.com/Azure/azure-sdk-for-go/services/compute/mgmt/2019-03-01/compute"
"github.com/hashicorp/packer/builder/azure/common/client"
"github.com/stretchr/testify/assert"

View File

@ -3,13 +3,14 @@ package chroot
import (
"context"
"fmt"
"log"
"github.com/Azure/azure-sdk-for-go/services/compute/mgmt/2019-03-01/compute"
"github.com/Azure/go-autorest/autorest/azure"
"github.com/Azure/go-autorest/autorest/to"
"github.com/hashicorp/packer/builder/azure/common/client"
"github.com/hashicorp/packer/helper/multistep"
"github.com/hashicorp/packer/packer"
"log"
)
var _ multistep.Step = &StepCreateImage{}

View File

@ -3,11 +3,12 @@ package client
import (
"context"
"fmt"
"regexp"
"strings"
"github.com/Azure/azure-sdk-for-go/profiles/latest/compute/mgmt/compute"
"github.com/Azure/azure-sdk-for-go/profiles/latest/compute/mgmt/compute/computeapi"
"github.com/Azure/go-autorest/autorest/to"
"regexp"
"strings"
)
var platformImageRegex = regexp.MustCompile(`^[-_.a-zA-Z0-9]+:[-_.a-zA-Z0-9]+:[-_.a-zA-Z0-9]+:[-_.a-zA-Z0-9]+$`)

View File

@ -4,6 +4,7 @@ import (
"context"
"fmt"
"github.com/hashicorp/hcl/v2/hcldec"
"github.com/hashicorp/packer/common"
"github.com/hashicorp/packer/helper/communicator"
"github.com/hashicorp/packer/helper/multistep"
@ -15,18 +16,18 @@ const BuilderId = "packer.cloudstack"
// Builder represents the CloudStack builder.
type Builder struct {
config *Config
config Config
runner multistep.Runner
ui packer.Ui
}
// Prepare implements the packer.Builder interface.
func (b *Builder) ConfigSpec() hcldec.ObjectSpec { return b.config.FlatMapstructure().HCL2Spec() }
func (b *Builder) Prepare(raws ...interface{}) ([]string, error) {
config, errs := NewConfig(raws...)
errs := b.config.Prepare(raws...)
if errs != nil {
return nil, errs
}
b.config = config
return nil, nil
}
@ -109,7 +110,7 @@ func (b *Builder) Run(ctx context.Context, ui packer.Ui, hook packer.Hook) (pack
// Build the artifact and return it
artifact := &Artifact{
client: client,
config: b.config,
config: &b.config,
template: state.Get("template").(*cloudstack.CreateTemplateResponse),
}

View File

@ -40,10 +40,8 @@ func TestBuilder_Prepare(t *testing.T) {
},
}
b := &Builder{}
for desc, tc := range cases {
_, errs := b.Prepare(tc.Config)
_, errs := (&Builder{}).Prepare(tc.Config)
if tc.Err {
if errs == nil {

View File

@ -167,8 +167,7 @@ type Config struct {
}
// NewConfig parses and validates the given config.
func NewConfig(raws ...interface{}) (*Config, error) {
c := new(Config)
func (c *Config) Prepare(raws ...interface{}) error {
err := config.Decode(c, &config.DecodeOpts{
Interpolate: true,
InterpolateContext: &c.ctx,
@ -179,7 +178,7 @@ func NewConfig(raws ...interface{}) (*Config, error) {
},
}, raws...)
if err != nil {
return nil, err
return err
}
var errs *packer.MultiError
@ -309,8 +308,8 @@ func NewConfig(raws ...interface{}) (*Config, error) {
// Check for errors and return if we have any.
if errs != nil && len(errs.Errors) > 0 {
return nil, errs
return errs
}
return c, nil
return nil
}

View File

@ -49,8 +49,8 @@ type FlatConfig struct {
SSHReadWriteTimeout *string `mapstructure:"ssh_read_write_timeout" cty:"ssh_read_write_timeout"`
SSHRemoteTunnels []string `mapstructure:"ssh_remote_tunnels" cty:"ssh_remote_tunnels"`
SSHLocalTunnels []string `mapstructure:"ssh_local_tunnels" cty:"ssh_local_tunnels"`
SSHPublicKey []byte `cty:"ssh_public_key"`
SSHPrivateKey []byte `cty:"ssh_private_key"`
SSHPublicKey []byte `mapstructure:"ssh_public_key" cty:"ssh_public_key"`
SSHPrivateKey []byte `mapstructure:"ssh_private_key" cty:"ssh_private_key"`
WinRMUser *string `mapstructure:"winrm_username" cty:"winrm_username"`
WinRMPassword *string `mapstructure:"winrm_password" cty:"winrm_password"`
WinRMHost *string `mapstructure:"winrm_host" cty:"winrm_host"`
@ -104,10 +104,13 @@ type FlatConfig struct {
// FlatMapstructure returns a new FlatConfig.
// FlatConfig is an auto-generated flat version of Config.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*Config) FlatMapstructure() interface{} { return new(FlatConfig) }
func (*Config) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatConfig)
}
// HCL2Spec returns the hcldec.Spec of a FlatConfig.
// This spec is used by HCL to read the fields of FlatConfig.
// HCL2Spec returns the hcl spec of a Config.
// This spec is used by HCL to read the fields of Config.
// The decoded values from this spec will then be applied to a FlatConfig.
func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"packer_build_name": &hcldec.AttrSpec{Name: "packer_build_name", Type: cty.String, Required: false},

View File

@ -132,7 +132,8 @@ func TestNewConfig(t *testing.T) {
raw[tc.Nullify] = nil
}
_, errs := NewConfig(raw)
var c Config
errs := c.Prepare(raw)
if tc.Err {
if errs == nil {

View File

@ -10,6 +10,7 @@ import (
"net/url"
"github.com/digitalocean/godo"
"github.com/hashicorp/hcl/v2/hcldec"
"github.com/hashicorp/packer/common"
"github.com/hashicorp/packer/helper/communicator"
"github.com/hashicorp/packer/helper/multistep"
@ -25,12 +26,13 @@ type Builder struct {
runner multistep.Runner
}
func (b *Builder) ConfigSpec() hcldec.ObjectSpec { return b.config.FlatMapstructure().HCL2Spec() }
func (b *Builder) Prepare(raws ...interface{}) ([]string, error) {
c, warnings, errs := NewConfig(raws...)
warnings, errs := b.config.Prepare(raws...)
if errs != nil {
return warnings, errs
}
b.config = *c
return nil, nil
}

View File

@ -89,8 +89,7 @@ type Config struct {
ctx interpolate.Context
}
func NewConfig(raws ...interface{}) (*Config, []string, error) {
c := new(Config)
func (c *Config) Prepare(raws ...interface{}) ([]string, error) {
var md mapstructure.Metadata
err := config.Decode(c, &config.DecodeOpts{
@ -104,7 +103,7 @@ func NewConfig(raws ...interface{}) (*Config, []string, error) {
},
}, raws...)
if err != nil {
return nil, nil, err
return nil, err
}
// Defaults
@ -189,9 +188,9 @@ func NewConfig(raws ...interface{}) (*Config, []string, error) {
}
if errs != nil && len(errs.Errors) > 0 {
return nil, nil, errs
return nil, errs
}
packer.LogSecretFilter.Set(c.APIToken)
return c, nil, nil
return nil, nil
}

View File

@ -46,8 +46,8 @@ type FlatConfig struct {
SSHReadWriteTimeout *string `mapstructure:"ssh_read_write_timeout" cty:"ssh_read_write_timeout"`
SSHRemoteTunnels []string `mapstructure:"ssh_remote_tunnels" cty:"ssh_remote_tunnels"`
SSHLocalTunnels []string `mapstructure:"ssh_local_tunnels" cty:"ssh_local_tunnels"`
SSHPublicKey []byte `cty:"ssh_public_key"`
SSHPrivateKey []byte `cty:"ssh_private_key"`
SSHPublicKey []byte `mapstructure:"ssh_public_key" cty:"ssh_public_key"`
SSHPrivateKey []byte `mapstructure:"ssh_private_key" cty:"ssh_private_key"`
WinRMUser *string `mapstructure:"winrm_username" cty:"winrm_username"`
WinRMPassword *string `mapstructure:"winrm_password" cty:"winrm_password"`
WinRMHost *string `mapstructure:"winrm_host" cty:"winrm_host"`
@ -77,10 +77,13 @@ type FlatConfig struct {
// FlatMapstructure returns a new FlatConfig.
// FlatConfig is an auto-generated flat version of Config.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*Config) FlatMapstructure() interface{} { return new(FlatConfig) }
func (*Config) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatConfig)
}
// HCL2Spec returns the hcldec.Spec of a FlatConfig.
// This spec is used by HCL to read the fields of FlatConfig.
// HCL2Spec returns the hcl spec of a Config.
// This spec is used by HCL to read the fields of Config.
// The decoded values from this spec will then be applied to a FlatConfig.
func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"packer_build_name": &hcldec.AttrSpec{Name: "packer_build_name", Type: cty.String, Required: false},

View File

@ -4,6 +4,7 @@ import (
"context"
"log"
"github.com/hashicorp/hcl/v2/hcldec"
"github.com/hashicorp/packer/common"
"github.com/hashicorp/packer/helper/communicator"
"github.com/hashicorp/packer/helper/multistep"
@ -16,16 +17,17 @@ const (
)
type Builder struct {
config *Config
config Config
runner multistep.Runner
}
func (b *Builder) ConfigSpec() hcldec.ObjectSpec { return b.config.FlatMapstructure().HCL2Spec() }
func (b *Builder) Prepare(raws ...interface{}) ([]string, error) {
c, warnings, errs := NewConfig(raws...)
warnings, errs := b.config.Prepare(raws...)
if errs != nil {
return warnings, errs
}
b.config = c
return warnings, nil
}

View File

@ -107,8 +107,7 @@ type Config struct {
ctx interpolate.Context
}
func NewConfig(raws ...interface{}) (*Config, []string, error) {
c := new(Config)
func (c *Config) Prepare(raws ...interface{}) ([]string, error) {
c.FixUploadOwner = true
@ -124,7 +123,7 @@ func NewConfig(raws ...interface{}) (*Config, []string, error) {
},
}, raws...)
if err != nil {
return nil, nil, err
return nil, err
}
// Defaults
@ -191,8 +190,8 @@ func NewConfig(raws ...interface{}) (*Config, []string, error) {
}
if errs != nil && len(errs.Errors) > 0 {
return nil, nil, errs
return nil, errs
}
return c, nil, nil
return nil, nil
}

View File

@ -46,8 +46,8 @@ type FlatConfig struct {
SSHReadWriteTimeout *string `mapstructure:"ssh_read_write_timeout" cty:"ssh_read_write_timeout"`
SSHRemoteTunnels []string `mapstructure:"ssh_remote_tunnels" cty:"ssh_remote_tunnels"`
SSHLocalTunnels []string `mapstructure:"ssh_local_tunnels" cty:"ssh_local_tunnels"`
SSHPublicKey []byte `cty:"ssh_public_key"`
SSHPrivateKey []byte `cty:"ssh_private_key"`
SSHPublicKey []byte `mapstructure:"ssh_public_key" cty:"ssh_public_key"`
SSHPrivateKey []byte `mapstructure:"ssh_private_key" cty:"ssh_private_key"`
WinRMUser *string `mapstructure:"winrm_username" cty:"winrm_username"`
WinRMPassword *string `mapstructure:"winrm_password" cty:"winrm_password"`
WinRMHost *string `mapstructure:"winrm_host" cty:"winrm_host"`
@ -86,10 +86,13 @@ type FlatConfig struct {
// FlatMapstructure returns a new FlatConfig.
// FlatConfig is an auto-generated flat version of Config.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*Config) FlatMapstructure() interface{} { return new(FlatConfig) }
func (*Config) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatConfig)
}
// HCL2Spec returns the hcldec.Spec of a FlatConfig.
// This spec is used by HCL to read the fields of FlatConfig.
// HCL2Spec returns the hcl spec of a Config.
// This spec is used by HCL to read the fields of Config.
// The decoded values from this spec will then be applied to a FlatConfig.
func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"packer_build_name": &hcldec.AttrSpec{Name: "packer_build_name", Type: cty.String, Required: false},

View File

@ -14,7 +14,8 @@ func testConfig() map[string]interface{} {
}
func testConfigStruct(t *testing.T) *Config {
c, warns, errs := NewConfig(testConfig())
var c Config
warns, errs := c.Prepare(testConfig())
if len(warns) > 0 {
t.Fatalf("bad: %#v", len(warns))
}
@ -22,7 +23,7 @@ func testConfigStruct(t *testing.T) *Config {
t.Fatalf("bad: %#v", errs)
}
return c
return &c
}
func testConfigErr(t *testing.T, warns []string, err error) {
@ -55,17 +56,18 @@ func TestConfigPrepare_exportPath(t *testing.T) {
// No export path. This is invalid. Previously this would not error during
// validation and as a result the failure would happen at build time.
delete(raw, "export_path")
_, warns, errs := NewConfig(raw)
var c Config
warns, errs := c.Prepare(raw)
testConfigErr(t, warns, errs)
// Good export path
raw["export_path"] = "good"
_, warns, errs = NewConfig(raw)
warns, errs = c.Prepare(raw)
testConfigOk(t, warns, errs)
// Bad export path (directory)
raw["export_path"] = td
_, warns, errs = NewConfig(raw)
warns, errs = c.Prepare(raw)
testConfigErr(t, warns, errs)
}
@ -74,17 +76,17 @@ func TestConfigPrepare_exportPathAndCommit(t *testing.T) {
// Export but no commit (explicit default)
raw["commit"] = false
_, warns, errs := NewConfig(raw)
warns, errs := (&Config{}).Prepare(raw)
testConfigOk(t, warns, errs)
// Commit AND export specified (invalid)
raw["commit"] = true
_, warns, errs = NewConfig(raw)
warns, errs = (&Config{}).Prepare(raw)
testConfigErr(t, warns, errs)
// Commit but no export
delete(raw, "export_path")
_, warns, errs = NewConfig(raw)
warns, errs = (&Config{}).Prepare(raw)
testConfigOk(t, warns, errs)
}
@ -93,18 +95,18 @@ func TestConfigPrepare_exportDiscard(t *testing.T) {
// Export but no discard (explicit default)
raw["discard"] = false
_, warns, errs := NewConfig(raw)
warns, errs := (&Config{}).Prepare(raw)
testConfigOk(t, warns, errs)
// Discard AND export (invalid)
raw["discard"] = true
_, warns, errs = NewConfig(raw)
warns, errs = (&Config{}).Prepare(raw)
testConfigErr(t, warns, errs)
// Discard but no export
raw["discard"] = true
delete(raw, "export_path")
_, warns, errs = NewConfig(raw)
warns, errs = (&Config{}).Prepare(raw)
testConfigOk(t, warns, errs)
}
@ -113,12 +115,13 @@ func TestConfigPrepare_image(t *testing.T) {
// No image
delete(raw, "image")
_, warns, errs := NewConfig(raw)
var c Config
warns, errs := c.Prepare(raw)
testConfigErr(t, warns, errs)
// Good image
raw["image"] = "path"
_, warns, errs = NewConfig(raw)
warns, errs = c.Prepare(raw)
testConfigOk(t, warns, errs)
}
@ -127,7 +130,8 @@ func TestConfigPrepare_pull(t *testing.T) {
// No pull set
delete(raw, "pull")
c, warns, errs := NewConfig(raw)
var c Config
warns, errs := c.Prepare(raw)
testConfigOk(t, warns, errs)
if !c.Pull {
t.Fatal("should pull by default")
@ -135,7 +139,7 @@ func TestConfigPrepare_pull(t *testing.T) {
// Pull set
raw["pull"] = false
c, warns, errs = NewConfig(raw)
warns, errs = c.Prepare(raw)
testConfigOk(t, warns, errs)
if c.Pull {
t.Fatal("should not pull")

View File

@ -12,6 +12,7 @@ import (
"io/ioutil"
"os"
"github.com/hashicorp/hcl/v2/hcldec"
"github.com/hashicorp/packer/helper/multistep"
"github.com/hashicorp/packer/packer"
)
@ -19,16 +20,17 @@ import (
const BuilderId = "packer.file"
type Builder struct {
config *Config
config Config
runner multistep.Runner
}
func (b *Builder) ConfigSpec() hcldec.ObjectSpec { return b.config.FlatMapstructure().HCL2Spec() }
func (b *Builder) Prepare(raws ...interface{}) ([]string, error) {
c, warnings, errs := NewConfig(raws...)
warnings, errs := b.config.Prepare(raws...)
if errs != nil {
return warnings, errs
}
b.config = c
return warnings, nil
}

View File

@ -22,8 +22,7 @@ type Config struct {
Content string `mapstructure:"content"`
}
func NewConfig(raws ...interface{}) (*Config, []string, error) {
c := new(Config)
func (c *Config) Prepare(raws ...interface{}) ([]string, error) {
warnings := []string{}
err := config.Decode(c, &config.DecodeOpts{
@ -33,7 +32,7 @@ func NewConfig(raws ...interface{}) (*Config, []string, error) {
},
}, raws...)
if err != nil {
return nil, warnings, err
return warnings, err
}
var errs *packer.MultiError
@ -51,8 +50,8 @@ func NewConfig(raws ...interface{}) (*Config, []string, error) {
}
if errs != nil && len(errs.Errors) > 0 {
return nil, warnings, errs
return warnings, errs
}
return c, warnings, nil
return warnings, nil
}

View File

@ -24,10 +24,13 @@ type FlatConfig struct {
// FlatMapstructure returns a new FlatConfig.
// FlatConfig is an auto-generated flat version of Config.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*Config) FlatMapstructure() interface{} { return new(FlatConfig) }
func (*Config) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatConfig)
}
// HCL2Spec returns the hcldec.Spec of a FlatConfig.
// This spec is used by HCL to read the fields of FlatConfig.
// HCL2Spec returns the hcl spec of a Config.
// This spec is used by HCL to read the fields of Config.
// The decoded values from this spec will then be applied to a FlatConfig.
func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"packer_build_name": &hcldec.AttrSpec{Name: "packer_build_name", Type: cty.String, Required: false},

View File

@ -16,7 +16,8 @@ func testConfig() map[string]interface{} {
func TestContentSourceConflict(t *testing.T) {
raw := testConfig()
_, _, errs := NewConfig(raw)
var c Config
_, errs := c.Prepare(raw)
if !strings.Contains(errs.Error(), ErrContentSourceConflict.Error()) {
t.Errorf("Expected config error: %s", ErrContentSourceConflict.Error())
}
@ -26,7 +27,8 @@ func TestNoFilename(t *testing.T) {
raw := testConfig()
delete(raw, "filename")
_, _, errs := NewConfig(raw)
var c Config
_, errs := c.Prepare(raw)
if errs == nil {
t.Errorf("Expected config error: %s", ErrTargetRequired.Error())
}
@ -37,7 +39,8 @@ func TestNoContent(t *testing.T) {
delete(raw, "content")
delete(raw, "source")
_, warns, _ := NewConfig(raw)
var c Config
warns, _ := c.Prepare(raw)
if len(warns) == 0 {
t.Error("Expected config warning without any content")

View File

@ -7,6 +7,7 @@ import (
"fmt"
"log"
"github.com/hashicorp/hcl/v2/hcldec"
"github.com/hashicorp/packer/common"
"github.com/hashicorp/packer/helper/communicator"
"github.com/hashicorp/packer/helper/multistep"
@ -18,17 +19,17 @@ const BuilderId = "packer.googlecompute"
// Builder represents a Packer Builder.
type Builder struct {
config *Config
config Config
runner multistep.Runner
}
// Prepare processes the build configuration parameters.
func (b *Builder) ConfigSpec() hcldec.ObjectSpec { return b.config.FlatMapstructure().HCL2Spec() }
func (b *Builder) Prepare(raws ...interface{}) ([]string, error) {
c, warnings, errs := NewConfig(raws...)
warnings, errs := b.config.Prepare(raws...)
if errs != nil {
return warnings, errs
}
b.config = c
return warnings, nil
}
@ -43,7 +44,7 @@ func (b *Builder) Run(ctx context.Context, ui packer.Ui, hook packer.Hook) (pack
// Set up the state.
state := new(multistep.BasicStateBag)
state.Put("config", b.config)
state.Put("config", &b.config)
state.Put("driver", driver)
state.Put("hook", hook)
state.Put("ui", ui)
@ -97,7 +98,7 @@ func (b *Builder) Run(ctx context.Context, ui packer.Ui, hook packer.Hook) (pack
artifact := &Artifact{
image: state.Get("image").(*Image),
driver: driver,
config: b.config,
config: &b.config,
}
return artifact, nil
}

View File

@ -187,8 +187,7 @@ type Config struct {
ctx interpolate.Context
}
func NewConfig(raws ...interface{}) (*Config, []string, error) {
c := new(Config)
func (c *Config) Prepare(raws ...interface{}) ([]string, error) {
c.ctx.Funcs = TemplateFuncs
err := config.Decode(c, &config.DecodeOpts{
Interpolate: true,
@ -200,7 +199,7 @@ func NewConfig(raws ...interface{}) (*Config, []string, error) {
},
}, raws...)
if err != nil {
return nil, nil, err
return nil, err
}
var errs *packer.MultiError
@ -372,10 +371,10 @@ func NewConfig(raws ...interface{}) (*Config, []string, error) {
// Check for any errors.
if errs != nil && len(errs.Errors) > 0 {
return nil, nil, errs
return nil, errs
}
return c, nil, nil
return nil, nil
}
type CustomerEncryptionKey struct {

View File

@ -46,8 +46,8 @@ type FlatConfig struct {
SSHReadWriteTimeout *string `mapstructure:"ssh_read_write_timeout" cty:"ssh_read_write_timeout"`
SSHRemoteTunnels []string `mapstructure:"ssh_remote_tunnels" cty:"ssh_remote_tunnels"`
SSHLocalTunnels []string `mapstructure:"ssh_local_tunnels" cty:"ssh_local_tunnels"`
SSHPublicKey []byte `cty:"ssh_public_key"`
SSHPrivateKey []byte `cty:"ssh_private_key"`
SSHPublicKey []byte `mapstructure:"ssh_public_key" cty:"ssh_public_key"`
SSHPrivateKey []byte `mapstructure:"ssh_private_key" cty:"ssh_private_key"`
WinRMUser *string `mapstructure:"winrm_username" cty:"winrm_username"`
WinRMPassword *string `mapstructure:"winrm_password" cty:"winrm_password"`
WinRMHost *string `mapstructure:"winrm_host" cty:"winrm_host"`
@ -100,10 +100,13 @@ type FlatConfig struct {
// FlatMapstructure returns a new FlatConfig.
// FlatConfig is an auto-generated flat version of Config.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*Config) FlatMapstructure() interface{} { return new(FlatConfig) }
func (*Config) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatConfig)
}
// HCL2Spec returns the hcldec.Spec of a FlatConfig.
// This spec is used by HCL to read the fields of FlatConfig.
// HCL2Spec returns the hcl spec of a Config.
// This spec is used by HCL to read the fields of Config.
// The decoded values from this spec will then be applied to a FlatConfig.
func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"packer_build_name": &hcldec.AttrSpec{Name: "packer_build_name", Type: cty.String, Required: false},
@ -206,10 +209,13 @@ type FlatCustomerEncryptionKey struct {
// FlatMapstructure returns a new FlatCustomerEncryptionKey.
// FlatCustomerEncryptionKey is an auto-generated flat version of CustomerEncryptionKey.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*CustomerEncryptionKey) FlatMapstructure() interface{} { return new(FlatCustomerEncryptionKey) }
func (*CustomerEncryptionKey) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatCustomerEncryptionKey)
}
// HCL2Spec returns the hcldec.Spec of a FlatCustomerEncryptionKey.
// This spec is used by HCL to read the fields of FlatCustomerEncryptionKey.
// HCL2Spec returns the hcl spec of a CustomerEncryptionKey.
// This spec is used by HCL to read the fields of CustomerEncryptionKey.
// The decoded values from this spec will then be applied to a FlatCustomerEncryptionKey.
func (*FlatCustomerEncryptionKey) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"kms_key_name": &hcldec.AttrSpec{Name: "kms_key_name", Type: cty.String, Required: false},

View File

@ -242,7 +242,8 @@ func TestConfigPrepare(t *testing.T) {
raw[tc.Key] = tc.Value
}
_, warns, errs := NewConfig(raw)
var c Config
warns, errs := c.Prepare(raw)
if tc.Err {
testConfigErr(t, warns, errs, tc.Key)
@ -302,7 +303,8 @@ func TestConfigPrepareAccelerator(t *testing.T) {
}
}
_, warns, errs := NewConfig(raw)
var c Config
warns, errs := c.Prepare(raw)
if tc.Err {
testConfigErr(t, warns, errs, strings.TrimRight(errStr, ", "))
@ -352,7 +354,8 @@ func TestConfigPrepareServiceAccount(t *testing.T) {
}
}
_, warns, errs := NewConfig(raw)
var c Config
warns, errs := c.Prepare(raw)
if tc.Err {
testConfigErr(t, warns, errs, strings.TrimRight(errStr, ", "))
@ -371,7 +374,8 @@ func TestConfigPrepareStartupScriptFile(t *testing.T) {
"zone": "us-central1-a",
}
_, _, errs := NewConfig(config)
var c Config
_, errs := c.Prepare(config)
if errs == nil || !strings.Contains(errs.Error(), "startup_script_file") {
t.Fatalf("should error: startup_script_file")
@ -398,10 +402,11 @@ func TestConfigDefaults(t *testing.T) {
raw, tempfile := testConfig(t)
defer os.Remove(tempfile)
c, warns, errs := NewConfig(raw)
var c Config
warns, errs := c.Prepare(raw)
testConfigOk(t, warns, errs)
actual := tc.Read(c)
actual := tc.Read(&c)
if actual != tc.Value {
t.Fatalf("bad: %#v", actual)
}
@ -412,7 +417,8 @@ func TestImageName(t *testing.T) {
raw, tempfile := testConfig(t)
defer os.Remove(tempfile)
c, _, _ := NewConfig(raw)
var c Config
c.Prepare(raw)
if !strings.HasPrefix(c.ImageName, "packer-") {
t.Fatalf("ImageName should have 'packer-' prefix, found %s", c.ImageName)
}
@ -425,7 +431,8 @@ func TestRegion(t *testing.T) {
raw, tempfile := testConfig(t)
defer os.Remove(tempfile)
c, _, _ := NewConfig(raw)
var c Config
c.Prepare(raw)
if c.Region != "us-east1" {
t.Fatalf("Region should be 'us-east1' given Zone of 'us-east1-a', but is %s", c.Region)
}
@ -460,7 +467,8 @@ func testConfigStruct(t *testing.T) *Config {
raw, tempfile := testConfig(t)
defer os.Remove(tempfile)
c, warns, errs := NewConfig(raw)
var c Config
warns, errs := c.Prepare(raw)
if len(warns) > 0 {
t.Fatalf("bad: %#v", len(warns))
}
@ -468,7 +476,7 @@ func testConfigStruct(t *testing.T) *Config {
t.Fatalf("bad: %#v", errs)
}
return c
return &c
}
func testConfigErr(t *testing.T, warns []string, err error, extra string) {

View File

@ -4,6 +4,7 @@ import (
"context"
"fmt"
"github.com/hashicorp/hcl/v2/hcldec"
"github.com/hashicorp/packer/common"
"github.com/hashicorp/packer/helper/communicator"
"github.com/hashicorp/packer/helper/multistep"
@ -22,12 +23,13 @@ type Builder struct {
var pluginVersion = "1.0.0"
func (b *Builder) ConfigSpec() hcldec.ObjectSpec { return b.config.FlatMapstructure().HCL2Spec() }
func (b *Builder) Prepare(raws ...interface{}) ([]string, error) {
config, warnings, errs := NewConfig(raws...)
warnings, errs := b.config.Prepare(raws...)
if errs != nil {
return warnings, errs
}
b.config = *config
return nil, nil
}

View File

@ -50,9 +50,7 @@ type imageFilter struct {
MostRecent bool `mapstructure:"most_recent"`
}
func NewConfig(raws ...interface{}) (*Config, []string, error) {
c := new(Config)
func (c *Config) Prepare(raws ...interface{}) ([]string, error) {
var md mapstructure.Metadata
err := config.Decode(c, &config.DecodeOpts{
Metadata: &md,
@ -65,7 +63,7 @@ func NewConfig(raws ...interface{}) (*Config, []string, error) {
},
}, raws...)
if err != nil {
return nil, nil, err
return nil, err
}
// Defaults
@ -142,11 +140,11 @@ func NewConfig(raws ...interface{}) (*Config, []string, error) {
}
if errs != nil && len(errs.Errors) > 0 {
return nil, nil, errs
return nil, errs
}
packer.LogSecretFilter.Set(c.HCloudToken)
return c, nil, nil
return nil, nil
}
func getServerIP(state multistep.StateBag) (string, error) {

View File

@ -46,8 +46,8 @@ type FlatConfig struct {
SSHReadWriteTimeout *string `mapstructure:"ssh_read_write_timeout" cty:"ssh_read_write_timeout"`
SSHRemoteTunnels []string `mapstructure:"ssh_remote_tunnels" cty:"ssh_remote_tunnels"`
SSHLocalTunnels []string `mapstructure:"ssh_local_tunnels" cty:"ssh_local_tunnels"`
SSHPublicKey []byte `cty:"ssh_public_key"`
SSHPrivateKey []byte `cty:"ssh_private_key"`
SSHPublicKey []byte `mapstructure:"ssh_public_key" cty:"ssh_public_key"`
SSHPrivateKey []byte `mapstructure:"ssh_private_key" cty:"ssh_private_key"`
WinRMUser *string `mapstructure:"winrm_username" cty:"winrm_username"`
WinRMPassword *string `mapstructure:"winrm_password" cty:"winrm_password"`
WinRMHost *string `mapstructure:"winrm_host" cty:"winrm_host"`
@ -75,10 +75,13 @@ type FlatConfig struct {
// FlatMapstructure returns a new FlatConfig.
// FlatConfig is an auto-generated flat version of Config.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*Config) FlatMapstructure() interface{} { return new(FlatConfig) }
func (*Config) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatConfig)
}
// HCL2Spec returns the hcldec.Spec of a FlatConfig.
// This spec is used by HCL to read the fields of FlatConfig.
// HCL2Spec returns the hcl spec of a Config.
// This spec is used by HCL to read the fields of Config.
// The decoded values from this spec will then be applied to a FlatConfig.
func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"packer_build_name": &hcldec.AttrSpec{Name: "packer_build_name", Type: cty.String, Required: false},
@ -156,10 +159,13 @@ type FlatimageFilter struct {
// FlatMapstructure returns a new FlatimageFilter.
// FlatimageFilter is an auto-generated flat version of imageFilter.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*imageFilter) FlatMapstructure() interface{} { return new(FlatimageFilter) }
func (*imageFilter) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatimageFilter)
}
// HCL2Spec returns the hcldec.Spec of a FlatimageFilter.
// This spec is used by HCL to read the fields of FlatimageFilter.
// HCL2Spec returns the hcl spec of a imageFilter.
// This spec is used by HCL to read the fields of imageFilter.
// The decoded values from this spec will then be applied to a FlatimageFilter.
func (*FlatimageFilter) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"with_selector": &hcldec.AttrSpec{Name: "with_selector", Type: cty.List(cty.String), Required: false},

View File

@ -4,6 +4,7 @@ import (
"context"
"fmt"
"github.com/hashicorp/hcl/v2/hcldec"
"github.com/hashicorp/packer/common"
"github.com/hashicorp/packer/helper/communicator"
"github.com/hashicorp/packer/helper/multistep"
@ -20,14 +21,14 @@ type Builder struct {
client *openapi.APIClient
}
func (b *Builder) ConfigSpec() hcldec.ObjectSpec { return b.config.FlatMapstructure().HCL2Spec() }
func (b *Builder) Prepare(raws ...interface{}) ([]string, error) {
config, warnings, errs := NewConfig(raws...)
warnings, errs := b.config.Prepare(raws...)
if errs != nil {
return warnings, errs
}
b.config = *config
cfg := openapi.NewConfiguration()
cfg.AddDefaultHeader("x-auth-token", b.config.Token)
if b.config.Project != "" {

View File

@ -114,8 +114,7 @@ type Config struct {
ctx interpolate.Context
}
func NewConfig(raws ...interface{}) (*Config, []string, error) {
c := &Config{}
func (c *Config) Prepare(raws ...interface{}) ([]string, error) {
var md mapstructure.Metadata
err := config.Decode(c, &config.DecodeOpts{
@ -133,12 +132,12 @@ func NewConfig(raws ...interface{}) (*Config, []string, error) {
},
}, raws...)
if err != nil {
return nil, nil, err
return nil, err
}
cliConfig, err := loadCLIConfig()
if err != nil {
return nil, nil, err
return nil, err
}
// Defaults
@ -165,7 +164,7 @@ func NewConfig(raws ...interface{}) (*Config, []string, error) {
if c.TokenLogin != "" && c.APIURL == "" {
c.Token, err = fetchTokenBySSH(c.TokenLogin)
if err != nil {
return nil, nil, err
return nil, err
}
}
}
@ -181,7 +180,7 @@ func NewConfig(raws ...interface{}) (*Config, []string, error) {
if c.ImageName == "" {
name, err := interpolate.Render("packer-{{timestamp}}", nil)
if err != nil {
return nil, nil, err
return nil, err
}
c.ImageName = name
}
@ -217,7 +216,7 @@ func NewConfig(raws ...interface{}) (*Config, []string, error) {
if c.ChrootMountPath == "" {
path, err := interpolate.Render("/mnt/packer-hyperone-volumes/{{timestamp}}", nil)
if err != nil {
return nil, nil, err
return nil, err
}
c.ChrootMountPath = path
}
@ -281,12 +280,12 @@ func NewConfig(raws ...interface{}) (*Config, []string, error) {
}
if errs != nil && len(errs.Errors) > 0 {
return nil, nil, errs
return nil, errs
}
packer.LogSecretFilter.Set(c.Token)
return c, nil, nil
return nil, nil
}
type cliConfig struct {

View File

@ -46,8 +46,8 @@ type FlatConfig struct {
SSHReadWriteTimeout *string `mapstructure:"ssh_read_write_timeout" cty:"ssh_read_write_timeout"`
SSHRemoteTunnels []string `mapstructure:"ssh_remote_tunnels" cty:"ssh_remote_tunnels"`
SSHLocalTunnels []string `mapstructure:"ssh_local_tunnels" cty:"ssh_local_tunnels"`
SSHPublicKey []byte `cty:"ssh_public_key"`
SSHPrivateKey []byte `cty:"ssh_private_key"`
SSHPublicKey []byte `mapstructure:"ssh_public_key" cty:"ssh_public_key"`
SSHPrivateKey []byte `mapstructure:"ssh_private_key" cty:"ssh_private_key"`
WinRMUser *string `mapstructure:"winrm_username" cty:"winrm_username"`
WinRMPassword *string `mapstructure:"winrm_password" cty:"winrm_password"`
WinRMHost *string `mapstructure:"winrm_host" cty:"winrm_host"`
@ -94,10 +94,13 @@ type FlatConfig struct {
// FlatMapstructure returns a new FlatConfig.
// FlatConfig is an auto-generated flat version of Config.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*Config) FlatMapstructure() interface{} { return new(FlatConfig) }
func (*Config) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatConfig)
}
// HCL2Spec returns the hcldec.Spec of a FlatConfig.
// This spec is used by HCL to read the fields of FlatConfig.
// HCL2Spec returns the hcl spec of a Config.
// This spec is used by HCL to read the fields of Config.
// The decoded values from this spec will then be applied to a FlatConfig.
func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"packer_build_name": &hcldec.AttrSpec{Name: "packer_build_name", Type: cty.String, Required: false},

View File

@ -15,10 +15,13 @@ type FlatOutputConfig struct {
// FlatMapstructure returns a new FlatOutputConfig.
// FlatOutputConfig is an auto-generated flat version of OutputConfig.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*OutputConfig) FlatMapstructure() interface{} { return new(FlatOutputConfig) }
func (*OutputConfig) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatOutputConfig)
}
// HCL2Spec returns the hcldec.Spec of a FlatOutputConfig.
// This spec is used by HCL to read the fields of FlatOutputConfig.
// HCL2Spec returns the hcl spec of a OutputConfig.
// This spec is used by HCL to read the fields of OutputConfig.
// The decoded values from this spec will then be applied to a FlatOutputConfig.
func (*FlatOutputConfig) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"output_directory": &hcldec.AttrSpec{Name: "output_directory", Type: cty.String, Required: false},

View File

@ -11,6 +11,7 @@ import (
"path/filepath"
"strings"
"github.com/hashicorp/hcl/v2/hcldec"
hypervcommon "github.com/hashicorp/packer/builder/hyperv/common"
"github.com/hashicorp/packer/common"
"github.com/hashicorp/packer/common/bootcommand"
@ -84,7 +85,8 @@ type Config struct {
ctx interpolate.Context
}
// Prepare processes the build configuration parameters.
func (b *Builder) ConfigSpec() hcldec.ObjectSpec { return b.config.FlatMapstructure().HCL2Spec() }
func (b *Builder) Prepare(raws ...interface{}) ([]string, error) {
err := config.Decode(&b.config, &config.DecodeOpts{
Interpolate: true,

View File

@ -60,8 +60,8 @@ type FlatConfig struct {
SSHReadWriteTimeout *string `mapstructure:"ssh_read_write_timeout" cty:"ssh_read_write_timeout"`
SSHRemoteTunnels []string `mapstructure:"ssh_remote_tunnels" cty:"ssh_remote_tunnels"`
SSHLocalTunnels []string `mapstructure:"ssh_local_tunnels" cty:"ssh_local_tunnels"`
SSHPublicKey []byte `cty:"ssh_public_key"`
SSHPrivateKey []byte `cty:"ssh_private_key"`
SSHPublicKey []byte `mapstructure:"ssh_public_key" cty:"ssh_public_key"`
SSHPrivateKey []byte `mapstructure:"ssh_private_key" cty:"ssh_private_key"`
WinRMUser *string `mapstructure:"winrm_username" cty:"winrm_username"`
WinRMPassword *string `mapstructure:"winrm_password" cty:"winrm_password"`
WinRMHost *string `mapstructure:"winrm_host" cty:"winrm_host"`
@ -108,10 +108,13 @@ type FlatConfig struct {
// FlatMapstructure returns a new FlatConfig.
// FlatConfig is an auto-generated flat version of Config.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*Config) FlatMapstructure() interface{} { return new(FlatConfig) }
func (*Config) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatConfig)
}
// HCL2Spec returns the hcldec.Spec of a FlatConfig.
// This spec is used by HCL to read the fields of FlatConfig.
// HCL2Spec returns the hcl spec of a Config.
// This spec is used by HCL to read the fields of Config.
// The decoded values from this spec will then be applied to a FlatConfig.
func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"packer_build_name": &hcldec.AttrSpec{Name: "packer_build_name", Type: cty.String, Required: false},

View File

@ -10,6 +10,7 @@ import (
"os"
"strings"
"github.com/hashicorp/hcl/v2/hcldec"
hypervcommon "github.com/hashicorp/packer/builder/hyperv/common"
"github.com/hashicorp/packer/common"
"github.com/hashicorp/packer/common/bootcommand"
@ -77,7 +78,8 @@ type Config struct {
ctx interpolate.Context
}
// Prepare processes the build configuration parameters.
func (b *Builder) ConfigSpec() hcldec.ObjectSpec { return b.config.FlatMapstructure().HCL2Spec() }
func (b *Builder) Prepare(raws ...interface{}) ([]string, error) {
err := config.Decode(&b.config, &config.DecodeOpts{
Interpolate: true,

View File

@ -60,8 +60,8 @@ type FlatConfig struct {
SSHReadWriteTimeout *string `mapstructure:"ssh_read_write_timeout" cty:"ssh_read_write_timeout"`
SSHRemoteTunnels []string `mapstructure:"ssh_remote_tunnels" cty:"ssh_remote_tunnels"`
SSHLocalTunnels []string `mapstructure:"ssh_local_tunnels" cty:"ssh_local_tunnels"`
SSHPublicKey []byte `cty:"ssh_public_key"`
SSHPrivateKey []byte `cty:"ssh_private_key"`
SSHPublicKey []byte `mapstructure:"ssh_public_key" cty:"ssh_public_key"`
SSHPrivateKey []byte `mapstructure:"ssh_private_key" cty:"ssh_private_key"`
WinRMUser *string `mapstructure:"winrm_username" cty:"winrm_username"`
WinRMPassword *string `mapstructure:"winrm_password" cty:"winrm_password"`
WinRMHost *string `mapstructure:"winrm_host" cty:"winrm_host"`
@ -110,10 +110,13 @@ type FlatConfig struct {
// FlatMapstructure returns a new FlatConfig.
// FlatConfig is an auto-generated flat version of Config.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*Config) FlatMapstructure() interface{} { return new(FlatConfig) }
func (*Config) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatConfig)
}
// HCL2Spec returns the hcldec.Spec of a FlatConfig.
// This spec is used by HCL to read the fields of FlatConfig.
// HCL2Spec returns the hcl spec of a Config.
// This spec is used by HCL to read the fields of Config.
// The decoded values from this spec will then be applied to a FlatConfig.
func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"packer_build_name": &hcldec.AttrSpec{Name: "packer_build_name", Type: cty.String, Required: false},

View File

@ -3,6 +3,8 @@ package jdcloud
import (
"context"
"fmt"
"github.com/hashicorp/hcl/v2/hcldec"
"github.com/hashicorp/packer/common"
"github.com/hashicorp/packer/helper/communicator"
"github.com/hashicorp/packer/helper/config"
@ -11,6 +13,8 @@ import (
"github.com/hashicorp/packer/template/interpolate"
)
func (b *Builder) ConfigSpec() hcldec.ObjectSpec { return b.config.FlatMapstructure().HCL2Spec() }
func (b *Builder) Prepare(raws ...interface{}) ([]string, error) {
err := config.Decode(&b.config, &config.DecodeOpts{
Interpolate: true,

View File

@ -48,8 +48,8 @@ type FlatConfig struct {
SSHReadWriteTimeout *string `mapstructure:"ssh_read_write_timeout" cty:"ssh_read_write_timeout"`
SSHRemoteTunnels []string `mapstructure:"ssh_remote_tunnels" cty:"ssh_remote_tunnels"`
SSHLocalTunnels []string `mapstructure:"ssh_local_tunnels" cty:"ssh_local_tunnels"`
SSHPublicKey []byte `cty:"ssh_public_key"`
SSHPrivateKey []byte `cty:"ssh_private_key"`
SSHPublicKey []byte `mapstructure:"ssh_public_key" cty:"ssh_public_key"`
SSHPrivateKey []byte `mapstructure:"ssh_private_key" cty:"ssh_private_key"`
WinRMUser *string `mapstructure:"winrm_username" cty:"winrm_username"`
WinRMPassword *string `mapstructure:"winrm_password" cty:"winrm_password"`
WinRMHost *string `mapstructure:"winrm_host" cty:"winrm_host"`
@ -74,10 +74,13 @@ type FlatConfig struct {
// FlatMapstructure returns a new FlatConfig.
// FlatConfig is an auto-generated flat version of Config.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*Config) FlatMapstructure() interface{} { return new(FlatConfig) }
func (*Config) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatConfig)
}
// HCL2Spec returns the hcldec.Spec of a FlatConfig.
// This spec is used by HCL to read the fields of FlatConfig.
// HCL2Spec returns the hcl spec of a Config.
// This spec is used by HCL to read the fields of Config.
// The decoded values from this spec will then be applied to a FlatConfig.
func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"access_key": &hcldec.AttrSpec{Name: "access_key", Type: cty.String, Required: false},

View File

@ -3,10 +3,11 @@ package jdcloud
import (
"context"
"fmt"
"io/ioutil"
"github.com/hashicorp/packer/helper/multistep"
"github.com/hashicorp/packer/packer"
"github.com/jdcloud-api/jdcloud-sdk-go/services/vm/apis"
"io/ioutil"
)
type stepConfigCredentials struct {

View File

@ -3,10 +3,11 @@ package jdcloud
import (
"context"
"fmt"
"time"
"github.com/hashicorp/packer/helper/multistep"
"github.com/hashicorp/packer/packer"
"github.com/jdcloud-api/jdcloud-sdk-go/services/vm/apis"
"time"
)
type stepCreateJDCloudImage struct {

View File

@ -3,6 +3,9 @@ package jdcloud
import (
"context"
"fmt"
"regexp"
"time"
"github.com/hashicorp/packer/helper/multistep"
"github.com/hashicorp/packer/packer"
"github.com/jdcloud-api/jdcloud-sdk-go/core"
@ -11,8 +14,6 @@ import (
vpcApis "github.com/jdcloud-api/jdcloud-sdk-go/services/vpc/apis"
vpcClient "github.com/jdcloud-api/jdcloud-sdk-go/services/vpc/client"
vpc "github.com/jdcloud-api/jdcloud-sdk-go/services/vpc/models"
"regexp"
"time"
)
type stepCreateJDCloudInstance struct {

View File

@ -3,6 +3,7 @@ package jdcloud
import (
"context"
"fmt"
"github.com/hashicorp/packer/helper/multistep"
"github.com/hashicorp/packer/packer"
"github.com/jdcloud-api/jdcloud-sdk-go/services/vm/apis"

View File

@ -3,6 +3,7 @@ package jdcloud
import (
"context"
"fmt"
"github.com/hashicorp/packer/helper/multistep"
"github.com/hashicorp/packer/packer"
vm "github.com/jdcloud-api/jdcloud-sdk-go/services/vm/apis"

View File

@ -8,6 +8,7 @@ import (
"fmt"
"log"
"github.com/hashicorp/hcl/v2/hcldec"
"github.com/hashicorp/packer/common"
"github.com/linode/linodego"
@ -21,16 +22,17 @@ const BuilderID = "packer.linode"
// Builder represents a Packer Builder.
type Builder struct {
config *Config
config Config
runner multistep.Runner
}
func (b *Builder) ConfigSpec() hcldec.ObjectSpec { return b.config.FlatMapstructure().HCL2Spec() }
func (b *Builder) Prepare(raws ...interface{}) ([]string, error) {
c, warnings, errs := NewConfig(raws...)
warnings, errs := b.config.Prepare(raws...)
if errs != nil {
return warnings, errs
}
b.config = c
return nil, nil
}

View File

@ -48,8 +48,7 @@ func createRandomRootPassword() (string, error) {
return rootPass, nil
}
func NewConfig(raws ...interface{}) (*Config, []string, error) {
c := new(Config)
func (c *Config) Prepare(raws ...interface{}) ([]string, error) {
if err := config.Decode(c, &config.DecodeOpts{
Interpolate: true,
@ -60,7 +59,7 @@ func NewConfig(raws ...interface{}) (*Config, []string, error) {
},
},
}, raws...); err != nil {
return nil, nil, err
return nil, err
}
var errs *packer.MultiError
@ -136,9 +135,9 @@ func NewConfig(raws ...interface{}) (*Config, []string, error) {
}
if errs != nil && len(errs.Errors) > 0 {
return nil, nil, errs
return nil, errs
}
packer.LogSecretFilter.Set(c.PersonalAccessToken)
return c, nil, nil
return nil, nil
}

View File

@ -46,8 +46,8 @@ type FlatConfig struct {
SSHReadWriteTimeout *string `mapstructure:"ssh_read_write_timeout" cty:"ssh_read_write_timeout"`
SSHRemoteTunnels []string `mapstructure:"ssh_remote_tunnels" cty:"ssh_remote_tunnels"`
SSHLocalTunnels []string `mapstructure:"ssh_local_tunnels" cty:"ssh_local_tunnels"`
SSHPublicKey []byte `cty:"ssh_public_key"`
SSHPrivateKey []byte `cty:"ssh_private_key"`
SSHPublicKey []byte `mapstructure:"ssh_public_key" cty:"ssh_public_key"`
SSHPrivateKey []byte `mapstructure:"ssh_private_key" cty:"ssh_private_key"`
WinRMUser *string `mapstructure:"winrm_username" cty:"winrm_username"`
WinRMPassword *string `mapstructure:"winrm_password" cty:"winrm_password"`
WinRMHost *string `mapstructure:"winrm_host" cty:"winrm_host"`
@ -72,10 +72,13 @@ type FlatConfig struct {
// FlatMapstructure returns a new FlatConfig.
// FlatConfig is an auto-generated flat version of Config.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*Config) FlatMapstructure() interface{} { return new(FlatConfig) }
func (*Config) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatConfig)
}
// HCL2Spec returns the hcldec.Spec of a FlatConfig.
// This spec is used by HCL to read the fields of FlatConfig.
// HCL2Spec returns the hcl spec of a Config.
// This spec is used by HCL to read the fields of Config.
// The decoded values from this spec will then be applied to a FlatConfig.
func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"packer_build_name": &hcldec.AttrSpec{Name: "packer_build_name", Type: cty.String, Required: false},

View File

@ -5,6 +5,7 @@ import (
"os"
"path/filepath"
"github.com/hashicorp/hcl/v2/hcldec"
"github.com/hashicorp/packer/common"
"github.com/hashicorp/packer/helper/multistep"
"github.com/hashicorp/packer/packer"
@ -19,16 +20,17 @@ type wrappedCommandTemplate struct {
}
type Builder struct {
config *Config
config Config
runner multistep.Runner
}
func (b *Builder) ConfigSpec() hcldec.ObjectSpec { return b.config.FlatMapstructure().HCL2Spec() }
func (b *Builder) Prepare(raws ...interface{}) ([]string, error) {
c, errs := NewConfig(raws...)
errs := b.config.Prepare(raws...)
if errs != nil {
return nil, errs
}
b.config = c
return nil, nil
}

View File

@ -1,4 +1,5 @@
//go:generate struct-markdown
//go:generate mapstructure-to-hcl2 -type Config
package lxc
@ -67,16 +68,15 @@ type Config struct {
ctx interpolate.Context
}
func NewConfig(raws ...interface{}) (*Config, error) {
var c Config
func (c *Config) Prepare(raws ...interface{}) error {
var md mapstructure.Metadata
err := config.Decode(&c, &config.DecodeOpts{
err := config.Decode(c, &config.DecodeOpts{
Metadata: &md,
Interpolate: true,
}, raws...)
if err != nil {
return nil, err
return err
}
// Accumulate any errors
@ -107,8 +107,8 @@ func NewConfig(raws ...interface{}) (*Config, error) {
}
if errs != nil && len(errs.Errors) > 0 {
return nil, errs
return errs
}
return &c, nil
return nil
}

View File

@ -0,0 +1,66 @@
// Code generated by "mapstructure-to-hcl2 -type Config"; DO NOT EDIT.
package lxc
import (
"github.com/hashicorp/hcl/v2/hcldec"
"github.com/zclconf/go-cty/cty"
)
// FlatConfig is an auto-generated flat version of Config.
// Where the contents of a field with a `mapstructure:,squash` tag are bubbled up.
type FlatConfig struct {
PackerBuildName *string `mapstructure:"packer_build_name" cty:"packer_build_name"`
PackerBuilderType *string `mapstructure:"packer_builder_type" cty:"packer_builder_type"`
PackerDebug *bool `mapstructure:"packer_debug" cty:"packer_debug"`
PackerForce *bool `mapstructure:"packer_force" cty:"packer_force"`
PackerOnError *string `mapstructure:"packer_on_error" cty:"packer_on_error"`
PackerUserVars map[string]string `mapstructure:"packer_user_variables" cty:"packer_user_variables"`
PackerSensitiveVars []string `mapstructure:"packer_sensitive_variables" cty:"packer_sensitive_variables"`
ConfigFile *string `mapstructure:"config_file" required:"true" cty:"config_file"`
OutputDir *string `mapstructure:"output_directory" required:"false" cty:"output_directory"`
ContainerName *string `mapstructure:"container_name" required:"false" cty:"container_name"`
CommandWrapper *string `mapstructure:"command_wrapper" required:"false" cty:"command_wrapper"`
InitTimeout *string `mapstructure:"init_timeout" required:"false" cty:"init_timeout"`
CreateOptions []string `mapstructure:"create_options" required:"false" cty:"create_options"`
StartOptions []string `mapstructure:"start_options" required:"false" cty:"start_options"`
AttachOptions []string `mapstructure:"attach_options" required:"false" cty:"attach_options"`
Name *string `mapstructure:"template_name" required:"true" cty:"template_name"`
Parameters []string `mapstructure:"template_parameters" required:"false" cty:"template_parameters"`
EnvVars []string `mapstructure:"template_environment_vars" required:"true" cty:"template_environment_vars"`
TargetRunlevel *int `mapstructure:"target_runlevel" required:"false" cty:"target_runlevel"`
}
// FlatMapstructure returns a new FlatConfig.
// FlatConfig is an auto-generated flat version of Config.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*Config) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatConfig)
}
// HCL2Spec returns the hcl spec of a Config.
// This spec is used by HCL to read the fields of Config.
// The decoded values from this spec will then be applied to a FlatConfig.
func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"packer_build_name": &hcldec.AttrSpec{Name: "packer_build_name", Type: cty.String, Required: false},
"packer_builder_type": &hcldec.AttrSpec{Name: "packer_builder_type", Type: cty.String, Required: false},
"packer_debug": &hcldec.AttrSpec{Name: "packer_debug", Type: cty.Bool, Required: false},
"packer_force": &hcldec.AttrSpec{Name: "packer_force", Type: cty.Bool, Required: false},
"packer_on_error": &hcldec.AttrSpec{Name: "packer_on_error", Type: cty.String, Required: false},
"packer_user_variables": &hcldec.BlockAttrsSpec{TypeName: "packer_user_variables", ElementType: cty.String, Required: false},
"packer_sensitive_variables": &hcldec.AttrSpec{Name: "packer_sensitive_variables", Type: cty.List(cty.String), Required: false},
"config_file": &hcldec.AttrSpec{Name: "config_file", Type: cty.String, Required: false},
"output_directory": &hcldec.AttrSpec{Name: "output_directory", Type: cty.String, Required: false},
"container_name": &hcldec.AttrSpec{Name: "container_name", Type: cty.String, Required: false},
"command_wrapper": &hcldec.AttrSpec{Name: "command_wrapper", Type: cty.String, Required: false},
"init_timeout": &hcldec.AttrSpec{Name: "init_timeout", Type: cty.String, Required: false},
"create_options": &hcldec.AttrSpec{Name: "create_options", Type: cty.List(cty.String), Required: false},
"start_options": &hcldec.AttrSpec{Name: "start_options", Type: cty.List(cty.String), Required: false},
"attach_options": &hcldec.AttrSpec{Name: "attach_options", Type: cty.List(cty.String), Required: false},
"template_name": &hcldec.AttrSpec{Name: "template_name", Type: cty.String, Required: false},
"template_parameters": &hcldec.AttrSpec{Name: "template_parameters", Type: cty.List(cty.String), Required: false},
"template_environment_vars": &hcldec.AttrSpec{Name: "template_environment_vars", Type: cty.List(cty.String), Required: false},
"target_runlevel": &hcldec.AttrSpec{Name: "target_runlevel", Type: cty.Number, Required: false},
}
return s
}

View File

@ -3,6 +3,7 @@ package lxd
import (
"context"
"github.com/hashicorp/hcl/v2/hcldec"
"github.com/hashicorp/packer/common"
"github.com/hashicorp/packer/helper/multistep"
"github.com/hashicorp/packer/packer"
@ -17,16 +18,17 @@ type wrappedCommandTemplate struct {
}
type Builder struct {
config *Config
config Config
runner multistep.Runner
}
func (b *Builder) ConfigSpec() hcldec.ObjectSpec { return b.config.FlatMapstructure().HCL2Spec() }
func (b *Builder) Prepare(raws ...interface{}) ([]string, error) {
c, errs := NewConfig(raws...)
errs := b.config.Prepare(raws...)
if errs != nil {
return nil, errs
}
b.config = c
return nil, nil
}

View File

@ -43,16 +43,15 @@ type Config struct {
ctx interpolate.Context
}
func NewConfig(raws ...interface{}) (*Config, error) {
var c Config
func (c *Config) Prepare(raws ...interface{}) error {
var md mapstructure.Metadata
err := config.Decode(&c, &config.DecodeOpts{
err := config.Decode(c, &config.DecodeOpts{
Metadata: &md,
Interpolate: true,
}, raws...)
if err != nil {
return nil, err
return err
}
// Accumulate any errors
@ -85,8 +84,8 @@ func NewConfig(raws ...interface{}) (*Config, error) {
}
if errs != nil && len(errs.Errors) > 0 {
return nil, errs
return errs
}
return &c, nil
return nil
}

View File

@ -29,10 +29,13 @@ type FlatConfig struct {
// FlatMapstructure returns a new FlatConfig.
// FlatConfig is an auto-generated flat version of Config.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*Config) FlatMapstructure() interface{} { return new(FlatConfig) }
func (*Config) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatConfig)
}
// HCL2Spec returns the hcldec.Spec of a FlatConfig.
// This spec is used by HCL to read the fields of FlatConfig.
// HCL2Spec returns the hcl spec of a Config.
// This spec is used by HCL to read the fields of Config.
// The decoded values from this spec will then be applied to a FlatConfig.
func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"packer_build_name": &hcldec.AttrSpec{Name: "packer_build_name", Type: cty.String, Required: false},

View File

@ -4,6 +4,7 @@ import (
"context"
ncloud "github.com/NaverCloudPlatform/ncloud-sdk-go/sdk"
"github.com/hashicorp/hcl/v2/hcldec"
"github.com/hashicorp/packer/common"
"github.com/hashicorp/packer/helper/communicator"
"github.com/hashicorp/packer/helper/multistep"
@ -12,17 +13,18 @@ import (
// Builder assume this implements packer.Builder
type Builder struct {
config *Config
config Config
stateBag multistep.StateBag
runner multistep.Runner
}
func (b *Builder) ConfigSpec() hcldec.ObjectSpec { return b.config.FlatMapstructure().HCL2Spec() }
func (b *Builder) Prepare(raws ...interface{}) ([]string, error) {
c, warnings, errs := NewConfig(raws...)
warnings, errs := b.config.Prepare(raws...)
if errs != nil {
return warnings, errs
}
b.config = c
b.stateBag = new(multistep.BasicStateBag)
@ -42,12 +44,12 @@ func (b *Builder) Run(ctx context.Context, ui packer.Ui, hook packer.Hook) (pack
if b.config.Comm.Type == "ssh" {
steps = []multistep.Step{
NewStepValidateTemplate(conn, ui, b.config),
NewStepValidateTemplate(conn, ui, &b.config),
NewStepCreateLoginKey(conn, ui),
NewStepCreateServerInstance(conn, ui, b.config),
NewStepCreateBlockStorageInstance(conn, ui, b.config),
NewStepGetRootPassword(conn, ui, b.config),
NewStepCreatePublicIPInstance(conn, ui, b.config),
NewStepCreateServerInstance(conn, ui, &b.config),
NewStepCreateBlockStorageInstance(conn, ui, &b.config),
NewStepGetRootPassword(conn, ui, &b.config),
NewStepCreatePublicIPInstance(conn, ui, &b.config),
&communicator.StepConnectSSH{
Config: &b.config.Comm,
Host: func(stateBag multistep.StateBag) (string, error) {
@ -60,18 +62,18 @@ func (b *Builder) Run(ctx context.Context, ui packer.Ui, hook packer.Hook) (pack
Comm: &b.config.Comm,
},
NewStepStopServerInstance(conn, ui),
NewStepCreateServerImage(conn, ui, b.config),
NewStepDeleteBlockStorageInstance(conn, ui, b.config),
NewStepCreateServerImage(conn, ui, &b.config),
NewStepDeleteBlockStorageInstance(conn, ui, &b.config),
NewStepTerminateServerInstance(conn, ui),
}
} else if b.config.Comm.Type == "winrm" {
steps = []multistep.Step{
NewStepValidateTemplate(conn, ui, b.config),
NewStepValidateTemplate(conn, ui, &b.config),
NewStepCreateLoginKey(conn, ui),
NewStepCreateServerInstance(conn, ui, b.config),
NewStepCreateBlockStorageInstance(conn, ui, b.config),
NewStepGetRootPassword(conn, ui, b.config),
NewStepCreatePublicIPInstance(conn, ui, b.config),
NewStepCreateServerInstance(conn, ui, &b.config),
NewStepCreateBlockStorageInstance(conn, ui, &b.config),
NewStepGetRootPassword(conn, ui, &b.config),
NewStepCreatePublicIPInstance(conn, ui, &b.config),
&communicator.StepConnectWinRM{
Config: &b.config.Comm,
Host: func(stateBag multistep.StateBag) (string, error) {
@ -86,8 +88,8 @@ func (b *Builder) Run(ctx context.Context, ui packer.Ui, hook packer.Hook) (pack
},
&common.StepProvision{},
NewStepStopServerInstance(conn, ui),
NewStepCreateServerImage(conn, ui, b.config),
NewStepDeleteBlockStorageInstance(conn, ui, b.config),
NewStepCreateServerImage(conn, ui, &b.config),
NewStepDeleteBlockStorageInstance(conn, ui, &b.config),
NewStepTerminateServerInstance(conn, ui),
}
}

View File

@ -60,8 +60,7 @@ type Config struct {
}
// NewConfig checks parameters
func NewConfig(raws ...interface{}) (*Config, []string, error) {
c := new(Config)
func (c *Config) Prepare(raws ...interface{}) ([]string, error) {
warnings := []string{}
err := config.Decode(c, &config.DecodeOpts{
@ -71,7 +70,7 @@ func NewConfig(raws ...interface{}) (*Config, []string, error) {
},
}, raws...)
if err != nil {
return nil, warnings, err
return warnings, err
}
var errs *packer.MultiError
@ -115,7 +114,7 @@ func NewConfig(raws ...interface{}) (*Config, []string, error) {
if c.BlockStorageSize < 10 || c.BlockStorageSize > 2000 {
errs = packer.MultiErrorAppend(errs, errors.New("The size of BlockStorageSize is at least 10 GB and up to 2000GB"))
} else if int(c.BlockStorageSize/10)*10 != c.BlockStorageSize {
return nil, nil, errors.New("BlockStorageSize must be a multiple of 10 GB")
return nil, errors.New("BlockStorageSize must be a multiple of 10 GB")
}
}
@ -136,8 +135,8 @@ func NewConfig(raws ...interface{}) (*Config, []string, error) {
}
if errs != nil && len(errs.Errors) > 0 {
return nil, warnings, errs
return warnings, errs
}
return c, warnings, nil
return warnings, nil
}

View File

@ -58,8 +58,8 @@ type FlatConfig struct {
SSHReadWriteTimeout *string `mapstructure:"ssh_read_write_timeout" cty:"ssh_read_write_timeout"`
SSHRemoteTunnels []string `mapstructure:"ssh_remote_tunnels" cty:"ssh_remote_tunnels"`
SSHLocalTunnels []string `mapstructure:"ssh_local_tunnels" cty:"ssh_local_tunnels"`
SSHPublicKey []byte `cty:"ssh_public_key"`
SSHPrivateKey []byte `cty:"ssh_private_key"`
SSHPublicKey []byte `mapstructure:"ssh_public_key" cty:"ssh_public_key"`
SSHPrivateKey []byte `mapstructure:"ssh_private_key" cty:"ssh_private_key"`
WinRMUser *string `mapstructure:"winrm_username" cty:"winrm_username"`
WinRMPassword *string `mapstructure:"winrm_password" cty:"winrm_password"`
WinRMHost *string `mapstructure:"winrm_host" cty:"winrm_host"`
@ -73,10 +73,13 @@ type FlatConfig struct {
// FlatMapstructure returns a new FlatConfig.
// FlatConfig is an auto-generated flat version of Config.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*Config) FlatMapstructure() interface{} { return new(FlatConfig) }
func (*Config) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatConfig)
}
// HCL2Spec returns the hcldec.Spec of a FlatConfig.
// This spec is used by HCL to read the fields of FlatConfig.
// HCL2Spec returns the hcl spec of a Config.
// This spec is used by HCL to read the fields of Config.
// The decoded values from this spec will then be applied to a FlatConfig.
func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"packer_build_name": &hcldec.AttrSpec{Name: "packer_build_name", Type: cty.String, Required: false},

View File

@ -42,7 +42,8 @@ func testConfigForMemberServerImage() map[string]interface{} {
func TestConfigWithServerImageProductCode(t *testing.T) {
raw := testConfig()
c, _, _ := NewConfig(raw)
var c Config
c.Prepare(raw)
if c.AccessKey != "access_key" {
t.Errorf("Expected 'access_key' to be set to '%s', but got '%s'.", raw["access_key"], c.AccessKey)
@ -76,7 +77,8 @@ func TestConfigWithServerImageProductCode(t *testing.T) {
func TestConfigWithMemberServerImageCode(t *testing.T) {
raw := testConfigForMemberServerImage()
c, _, _ := NewConfig(raw)
var c Config
c.Prepare(raw)
if c.AccessKey != "access_key" {
t.Errorf("Expected 'access_key' to be set to '%s', but got '%s'.", raw["access_key"], c.AccessKey)
@ -110,7 +112,8 @@ func TestConfigWithMemberServerImageCode(t *testing.T) {
func TestEmptyConfig(t *testing.T) {
raw := new(map[string]interface{})
_, _, err := NewConfig(raw)
var c Config
_, err := c.Prepare(raw)
if err == nil {
t.Error("Expected Config to require 'access_key', 'secret_key' and some mandatory fields, but it did not")
@ -138,7 +141,8 @@ func TestExistsBothServerImageProductCodeAndMemberServerImageNoConfig(t *testing
"member_server_image_no": "2440",
}
_, _, err := NewConfig(raw)
var c Config
_, err := c.Prepare(raw)
if !strings.Contains(err.Error(), "Only one of server_image_product_code and member_server_image_no can be set") {
t.Error("Expected Config to require Only one of 'server_image_product_code' and 'member_server_image_no' can be set, but it did not")

View File

@ -3,6 +3,7 @@ package null
import (
"context"
"github.com/hashicorp/hcl/v2/hcldec"
"github.com/hashicorp/packer/common"
"github.com/hashicorp/packer/helper/communicator"
"github.com/hashicorp/packer/helper/multistep"
@ -12,16 +13,17 @@ import (
const BuilderId = "fnoeding.null"
type Builder struct {
config *Config
config Config
runner multistep.Runner
}
func (b *Builder) ConfigSpec() hcldec.ObjectSpec { return b.config.FlatMapstructure().HCL2Spec() }
func (b *Builder) Prepare(raws ...interface{}) ([]string, error) {
c, warnings, errs := NewConfig(raws...)
warnings, errs := b.config.Prepare(raws...)
if errs != nil {
return warnings, errs
}
b.config = c
return warnings, nil
}

View File

@ -18,15 +18,14 @@ type Config struct {
CommConfig communicator.Config `mapstructure:",squash"`
}
func NewConfig(raws ...interface{}) (*Config, []string, error) {
var c Config
func (c *Config) Prepare(raws ...interface{}) ([]string, error) {
err := config.Decode(&c, &config.DecodeOpts{
Interpolate: true,
InterpolateFilter: &interpolate.RenderFilter{},
}, raws...)
if err != nil {
return nil, nil, err
return nil, err
}
var errs *packer.MultiError
@ -60,8 +59,8 @@ func NewConfig(raws ...interface{}) (*Config, []string, error) {
}
if errs != nil && len(errs.Errors) > 0 {
return nil, nil, errs
return nil, errs
}
return &c, nil, nil
return nil, nil
}

View File

@ -46,8 +46,8 @@ type FlatConfig struct {
SSHReadWriteTimeout *string `mapstructure:"ssh_read_write_timeout" cty:"ssh_read_write_timeout"`
SSHRemoteTunnels []string `mapstructure:"ssh_remote_tunnels" cty:"ssh_remote_tunnels"`
SSHLocalTunnels []string `mapstructure:"ssh_local_tunnels" cty:"ssh_local_tunnels"`
SSHPublicKey []byte `cty:"ssh_public_key"`
SSHPrivateKey []byte `cty:"ssh_private_key"`
SSHPublicKey []byte `mapstructure:"ssh_public_key" cty:"ssh_public_key"`
SSHPrivateKey []byte `mapstructure:"ssh_private_key" cty:"ssh_private_key"`
WinRMUser *string `mapstructure:"winrm_username" cty:"winrm_username"`
WinRMPassword *string `mapstructure:"winrm_password" cty:"winrm_password"`
WinRMHost *string `mapstructure:"winrm_host" cty:"winrm_host"`
@ -61,10 +61,13 @@ type FlatConfig struct {
// FlatMapstructure returns a new FlatConfig.
// FlatConfig is an auto-generated flat version of Config.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*Config) FlatMapstructure() interface{} { return new(FlatConfig) }
func (*Config) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatConfig)
}
// HCL2Spec returns the hcldec.Spec of a FlatConfig.
// This spec is used by HCL to read the fields of FlatConfig.
// HCL2Spec returns the hcl spec of a Config.
// This spec is used by HCL to read the fields of Config.
// The decoded values from this spec will then be applied to a FlatConfig.
func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"packer_build_name": &hcldec.AttrSpec{Name: "packer_build_name", Type: cty.String, Required: false},

View File

@ -16,7 +16,8 @@ func testConfig() map[string]interface{} {
}
func testConfigStruct(t *testing.T) *Config {
c, warns, errs := NewConfig(testConfig())
var c Config
warns, errs := c.Prepare(testConfig())
if len(warns) > 0 {
t.Fatalf("bad: %#v", len(warns))
}
@ -24,7 +25,7 @@ func testConfigStruct(t *testing.T) *Config {
t.Fatalf("bad: %#v", errs)
}
return c
return &c
}
func testConfigErr(t *testing.T, warns []string, err error) {
@ -50,7 +51,8 @@ func TestConfigPrepare_port(t *testing.T) {
// default port should be 22
delete(raw, "port")
c, warns, errs := NewConfig(raw)
var c Config
warns, errs := c.Prepare(raw)
if c.CommConfig.SSHPort != 22 {
t.Fatalf("bad: port should default to 22, not %d", c.CommConfig.SSHPort)
}
@ -62,12 +64,13 @@ func TestConfigPrepare_host(t *testing.T) {
// No host
delete(raw, "ssh_host")
_, warns, errs := NewConfig(raw)
var c Config
warns, errs := c.Prepare(raw)
testConfigErr(t, warns, errs)
// Good host
raw["ssh_host"] = "good"
_, warns, errs = NewConfig(raw)
warns, errs = c.Prepare(raw)
testConfigOk(t, warns, errs)
}
@ -77,12 +80,12 @@ func TestConfigPrepare_sshCredential(t *testing.T) {
// no ssh_password and no ssh_private_key_file
delete(raw, "ssh_password")
delete(raw, "ssh_private_key_file")
_, warns, errs := NewConfig(raw)
warns, errs := (&Config{}).Prepare(raw)
testConfigErr(t, warns, errs)
// only ssh_password
raw["ssh_password"] = "good"
_, warns, errs = NewConfig(raw)
warns, errs = (&Config{}).Prepare(raw)
testConfigOk(t, warns, errs)
// only ssh_private_key_file
@ -90,11 +93,11 @@ func TestConfigPrepare_sshCredential(t *testing.T) {
defer os.Remove(testFile)
raw["ssh_private_key_file"] = testFile
delete(raw, "ssh_password")
_, warns, errs = NewConfig(raw)
warns, errs = (&Config{}).Prepare(raw)
testConfigOk(t, warns, errs)
// both ssh_password and ssh_private_key_file set
raw["ssh_password"] = "bad"
_, warns, errs = NewConfig(raw)
warns, errs = (&Config{}).Prepare(raw)
testConfigErr(t, warns, errs)
}

View File

@ -5,6 +5,7 @@ import (
"errors"
"fmt"
"github.com/hashicorp/hcl/v2/hcldec"
"github.com/hashicorp/packer/common"
"github.com/hashicorp/packer/helper/communicator"
"github.com/hashicorp/packer/helper/multistep"
@ -14,16 +15,17 @@ import (
const BuilderId = "packer.oneandone"
type Builder struct {
config *Config
config Config
runner multistep.Runner
}
func (b *Builder) ConfigSpec() hcldec.ObjectSpec { return b.config.FlatMapstructure().HCL2Spec() }
func (b *Builder) Prepare(raws ...interface{}) ([]string, error) {
c, warnings, errs := NewConfig(raws...)
warnings, errs := b.config.Prepare(raws...)
if errs != nil {
return warnings, errs
}
b.config = c
return warnings, nil
}

View File

@ -31,11 +31,10 @@ type Config struct {
ctx interpolate.Context
}
func NewConfig(raws ...interface{}) (*Config, []string, error) {
var c Config
func (c *Config) Prepare(raws ...interface{}) ([]string, error) {
var md mapstructure.Metadata
err := config.Decode(&c, &config.DecodeOpts{
err := config.Decode(c, &config.DecodeOpts{
Metadata: &md,
Interpolate: true,
InterpolateContext: &c.ctx,
@ -46,7 +45,7 @@ func NewConfig(raws ...interface{}) (*Config, []string, error) {
},
}, raws...)
if err != nil {
return nil, nil, err
return nil, err
}
var errs *packer.MultiError
@ -107,8 +106,8 @@ func NewConfig(raws ...interface{}) (*Config, []string, error) {
}
if errs != nil && len(errs.Errors) > 0 {
return nil, nil, errs
return nil, errs
}
packer.LogSecretFilter.Set(c.Token)
return &c, nil, nil
return nil, nil
}

View File

@ -46,8 +46,8 @@ type FlatConfig struct {
SSHReadWriteTimeout *string `mapstructure:"ssh_read_write_timeout" cty:"ssh_read_write_timeout"`
SSHRemoteTunnels []string `mapstructure:"ssh_remote_tunnels" cty:"ssh_remote_tunnels"`
SSHLocalTunnels []string `mapstructure:"ssh_local_tunnels" cty:"ssh_local_tunnels"`
SSHPublicKey []byte `cty:"ssh_public_key"`
SSHPrivateKey []byte `cty:"ssh_private_key"`
SSHPublicKey []byte `mapstructure:"ssh_public_key" cty:"ssh_public_key"`
SSHPrivateKey []byte `mapstructure:"ssh_private_key" cty:"ssh_private_key"`
WinRMUser *string `mapstructure:"winrm_username" cty:"winrm_username"`
WinRMPassword *string `mapstructure:"winrm_password" cty:"winrm_password"`
WinRMHost *string `mapstructure:"winrm_host" cty:"winrm_host"`
@ -69,10 +69,13 @@ type FlatConfig struct {
// FlatMapstructure returns a new FlatConfig.
// FlatConfig is an auto-generated flat version of Config.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*Config) FlatMapstructure() interface{} { return new(FlatConfig) }
func (*Config) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatConfig)
}
// HCL2Spec returns the hcldec.Spec of a FlatConfig.
// This spec is used by HCL to read the fields of FlatConfig.
// HCL2Spec returns the hcl spec of a Config.
// This spec is used by HCL to read the fields of Config.
// The decoded values from this spec will then be applied to a FlatConfig.
func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"packer_build_name": &hcldec.AttrSpec{Name: "packer_build_name", Type: cty.String, Required: false},

View File

@ -9,6 +9,7 @@ import (
"context"
"fmt"
"github.com/hashicorp/hcl/v2/hcldec"
"github.com/hashicorp/packer/common"
"github.com/hashicorp/packer/helper/communicator"
"github.com/hashicorp/packer/helper/config"
@ -35,6 +36,8 @@ type Builder struct {
runner multistep.Runner
}
func (b *Builder) ConfigSpec() hcldec.ObjectSpec { return b.config.FlatMapstructure().HCL2Spec() }
func (b *Builder) Prepare(raws ...interface{}) ([]string, error) {
err := config.Decode(&b.config, &config.DecodeOpts{
Interpolate: true,

View File

@ -73,8 +73,8 @@ type FlatConfig struct {
SSHReadWriteTimeout *string `mapstructure:"ssh_read_write_timeout" cty:"ssh_read_write_timeout"`
SSHRemoteTunnels []string `mapstructure:"ssh_remote_tunnels" cty:"ssh_remote_tunnels"`
SSHLocalTunnels []string `mapstructure:"ssh_local_tunnels" cty:"ssh_local_tunnels"`
SSHPublicKey []byte `cty:"ssh_public_key"`
SSHPrivateKey []byte `cty:"ssh_private_key"`
SSHPublicKey []byte `mapstructure:"ssh_public_key" cty:"ssh_public_key"`
SSHPrivateKey []byte `mapstructure:"ssh_private_key" cty:"ssh_private_key"`
WinRMUser *string `mapstructure:"winrm_username" cty:"winrm_username"`
WinRMPassword *string `mapstructure:"winrm_password" cty:"winrm_password"`
WinRMHost *string `mapstructure:"winrm_host" cty:"winrm_host"`
@ -118,10 +118,13 @@ type FlatConfig struct {
// FlatMapstructure returns a new FlatConfig.
// FlatConfig is an auto-generated flat version of Config.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*Config) FlatMapstructure() interface{} { return new(FlatConfig) }
func (*Config) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatConfig)
}
// HCL2Spec returns the hcldec.Spec of a FlatConfig.
// This spec is used by HCL to read the fields of FlatConfig.
// HCL2Spec returns the hcl spec of a Config.
// This spec is used by HCL to read the fields of Config.
// The decoded values from this spec will then be applied to a FlatConfig.
func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"packer_build_name": &hcldec.AttrSpec{Name: "packer_build_name", Type: cty.String, Required: false},
@ -241,10 +244,13 @@ type FlatImageFilter struct {
// FlatMapstructure returns a new FlatImageFilter.
// FlatImageFilter is an auto-generated flat version of ImageFilter.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*ImageFilter) FlatMapstructure() interface{} { return new(FlatImageFilter) }
func (*ImageFilter) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatImageFilter)
}
// HCL2Spec returns the hcldec.Spec of a FlatImageFilter.
// This spec is used by HCL to read the fields of FlatImageFilter.
// HCL2Spec returns the hcl spec of a ImageFilter.
// This spec is used by HCL to read the fields of ImageFilter.
// The decoded values from this spec will then be applied to a FlatImageFilter.
func (*FlatImageFilter) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"filters": &hcldec.BlockSpec{TypeName: "filters", Nested: hcldec.ObjectSpec((*FlatImageFilterOptions)(nil).HCL2Spec())},
@ -266,10 +272,13 @@ type FlatImageFilterOptions struct {
// FlatMapstructure returns a new FlatImageFilterOptions.
// FlatImageFilterOptions is an auto-generated flat version of ImageFilterOptions.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*ImageFilterOptions) FlatMapstructure() interface{} { return new(FlatImageFilterOptions) }
func (*ImageFilterOptions) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatImageFilterOptions)
}
// HCL2Spec returns the hcldec.Spec of a FlatImageFilterOptions.
// This spec is used by HCL to read the fields of FlatImageFilterOptions.
// HCL2Spec returns the hcl spec of a ImageFilterOptions.
// This spec is used by HCL to read the fields of ImageFilterOptions.
// The decoded values from this spec will then be applied to a FlatImageFilterOptions.
func (*FlatImageFilterOptions) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"name": &hcldec.AttrSpec{Name: "name", Type: cty.String, Required: false},

View File

@ -1,3 +1,5 @@
//go:generate mapstructure-to-hcl2 -type Config
package classic
import (
@ -8,6 +10,7 @@ import (
"github.com/hashicorp/go-cleanhttp"
"github.com/hashicorp/go-oracle-terraform/compute"
"github.com/hashicorp/go-oracle-terraform/opc"
"github.com/hashicorp/hcl/v2/hcldec"
ocommon "github.com/hashicorp/packer/builder/oracle/common"
"github.com/hashicorp/packer/common"
"github.com/hashicorp/packer/helper/communicator"
@ -20,16 +23,17 @@ const BuilderId = "packer.oracle.classic"
// Builder is a builder implementation that creates Oracle OCI custom images.
type Builder struct {
config *Config
config Config
runner multistep.Runner
}
func (b *Builder) Prepare(rawConfig ...interface{}) ([]string, error) {
config, err := NewConfig(rawConfig...)
func (b *Builder) ConfigSpec() hcldec.ObjectSpec { return b.config.FlatMapstructure().HCL2Spec() }
func (b *Builder) Prepare(raws ...interface{}) ([]string, error) {
err := b.config.Prepare(raws...)
if err != nil {
return nil, err
}
b.config = config
var errs *packer.MultiError

View File

@ -53,8 +53,8 @@ type FlatConfig struct {
SSHReadWriteTimeout *string `mapstructure:"ssh_read_write_timeout" cty:"ssh_read_write_timeout"`
SSHRemoteTunnels []string `mapstructure:"ssh_remote_tunnels" cty:"ssh_remote_tunnels"`
SSHLocalTunnels []string `mapstructure:"ssh_local_tunnels" cty:"ssh_local_tunnels"`
SSHPublicKey []byte `cty:"ssh_public_key"`
SSHPrivateKey []byte `cty:"ssh_private_key"`
SSHPublicKey []byte `mapstructure:"ssh_public_key" cty:"ssh_public_key"`
SSHPrivateKey []byte `mapstructure:"ssh_private_key" cty:"ssh_private_key"`
WinRMUser *string `mapstructure:"winrm_username" cty:"winrm_username"`
WinRMPassword *string `mapstructure:"winrm_password" cty:"winrm_password"`
WinRMHost *string `mapstructure:"winrm_host" cty:"winrm_host"`
@ -82,10 +82,13 @@ type FlatConfig struct {
// FlatMapstructure returns a new FlatConfig.
// FlatConfig is an auto-generated flat version of Config.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*Config) FlatMapstructure() interface{} { return new(FlatConfig) }
func (*Config) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatConfig)
}
// HCL2Spec returns the hcldec.Spec of a FlatConfig.
// This spec is used by HCL to read the fields of FlatConfig.
// HCL2Spec returns the hcl spec of a Config.
// This spec is used by HCL to read the fields of Config.
// The decoded values from this spec will then be applied to a FlatConfig.
func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"packer_build_name": &hcldec.AttrSpec{Name: "packer_build_name", Type: cty.String, Required: false},

View File

@ -1,5 +1,3 @@
//go:generate mapstructure-to-hcl2 -type Config
package classic
import (
@ -57,8 +55,7 @@ func (c *Config) Identifier(s string) string {
return fmt.Sprintf("/Compute-%s/%s/%s", c.IdentityDomain, c.Username, s)
}
func NewConfig(raws ...interface{}) (*Config, error) {
c := &Config{}
func (c *Config) Prepare(raws ...interface{}) error {
// Decode from template
err := config.Decode(c, &config.DecodeOpts{
@ -66,12 +63,12 @@ func NewConfig(raws ...interface{}) (*Config, error) {
InterpolateContext: &c.ctx,
}, raws...)
if err != nil {
return nil, fmt.Errorf("Failed to mapstructure Config: %+v", err)
return fmt.Errorf("Failed to mapstructure Config: %+v", err)
}
c.apiEndpointURL, err = url.Parse(c.APIEndpoint)
if err != nil {
return nil, fmt.Errorf("Error parsing API Endpoint: %s", err)
return fmt.Errorf("Error parsing API Endpoint: %s", err)
}
// Set default source list
if c.SSHSourceList == "" {
@ -127,7 +124,7 @@ func NewConfig(raws ...interface{}) (*Config, error) {
}
if errs != nil && len(errs.Errors) > 0 {
return nil, errs
return errs
}
// unpack attributes from json into config
@ -155,5 +152,5 @@ func NewConfig(raws ...interface{}) (*Config, error) {
c.attribs = data
}
return c, nil
return nil
}

View File

@ -22,7 +22,8 @@ func testConfig() map[string]interface{} {
func TestConfigAutoFillsSourceList(t *testing.T) {
tc := testConfig()
conf, err := NewConfig(tc)
var conf Config
err := conf.Prepare(tc)
if err != nil {
t.Fatalf("Should not have error: %s", err.Error())
}
@ -47,7 +48,8 @@ func TestConfigValidationCatchesMissing(t *testing.T) {
for _, key := range required {
tc := testConfig()
delete(tc, key)
_, err := NewConfig(tc)
var c Config
err := c.Prepare(tc)
if err == nil {
t.Fatalf("Test should have failed when config lacked %s!", key)
}
@ -68,7 +70,8 @@ func TestConfigValidatesObjects(t *testing.T) {
for _, tt := range objectTests {
tc := testConfig()
tc[s] = tt.object
_, err := NewConfig(tc)
var c Config
err := c.Prepare(tc)
if tt.valid {
assert.NoError(t, err, tt.object)
} else {

View File

@ -6,6 +6,7 @@ import (
"context"
"fmt"
"github.com/hashicorp/hcl/v2/hcldec"
ocommon "github.com/hashicorp/packer/builder/oracle/common"
"github.com/hashicorp/packer/common"
"github.com/hashicorp/packer/helper/communicator"
@ -22,22 +23,23 @@ const ociAPIVersion = "20160918"
// Builder is a builder implementation that creates Oracle OCI custom images.
type Builder struct {
config *Config
config Config
runner multistep.Runner
}
func (b *Builder) Prepare(rawConfig ...interface{}) ([]string, error) {
config, err := NewConfig(rawConfig...)
func (b *Builder) ConfigSpec() hcldec.ObjectSpec { return b.config.FlatMapstructure().HCL2Spec() }
func (b *Builder) Prepare(raws ...interface{}) ([]string, error) {
err := b.config.Prepare(raws...)
if err != nil {
return nil, err
}
b.config = config
return nil, nil
}
func (b *Builder) Run(ctx context.Context, ui packer.Ui, hook packer.Hook) (packer.Artifact, error) {
driver, err := NewDriverOCI(b.config)
driver, err := NewDriverOCI(&b.config)
if err != nil {
return nil, err
}

View File

@ -75,8 +75,7 @@ func (c *Config) ConfigProvider() ocicommon.ConfigurationProvider {
return c.configProvider
}
func NewConfig(raws ...interface{}) (*Config, error) {
c := &Config{}
func (c *Config) Prepare(raws ...interface{}) error {
// Decode from template
err := config.Decode(c, &config.DecodeOpts{
@ -84,7 +83,7 @@ func NewConfig(raws ...interface{}) (*Config, error) {
InterpolateContext: &c.ctx,
}, raws...)
if err != nil {
return nil, fmt.Errorf("Failed to mapstructure Config: %+v", err)
return fmt.Errorf("Failed to mapstructure Config: %+v", err)
}
// Determine where the SDK config is located
@ -103,13 +102,13 @@ func NewConfig(raws ...interface{}) (*Config, error) {
if c.KeyFile != "" {
path, err := packer.ExpandUser(c.KeyFile)
if err != nil {
return nil, err
return err
}
// Read API signing key
keyContent, err = ioutil.ReadFile(path)
if err != nil {
return nil, err
return err
}
}
@ -135,7 +134,7 @@ func NewConfig(raws ...interface{}) (*Config, error) {
// Load API access configuration from SDK
configProvider, err := ocicommon.ComposingConfigurationProvider(providers)
if err != nil {
return nil, err
return err
}
var errs *packer.MultiError
@ -249,10 +248,10 @@ func NewConfig(raws ...interface{}) (*Config, error) {
}
if errs != nil && len(errs.Errors) > 0 {
return nil, errs
return errs
}
return c, nil
return nil
}
// getDefaultOCISettingsPath uses os/user to compute the default

View File

@ -46,8 +46,8 @@ type FlatConfig struct {
SSHReadWriteTimeout *string `mapstructure:"ssh_read_write_timeout" cty:"ssh_read_write_timeout"`
SSHRemoteTunnels []string `mapstructure:"ssh_remote_tunnels" cty:"ssh_remote_tunnels"`
SSHLocalTunnels []string `mapstructure:"ssh_local_tunnels" cty:"ssh_local_tunnels"`
SSHPublicKey []byte `cty:"ssh_public_key"`
SSHPrivateKey []byte `cty:"ssh_private_key"`
SSHPublicKey []byte `mapstructure:"ssh_public_key" cty:"ssh_public_key"`
SSHPrivateKey []byte `mapstructure:"ssh_private_key" cty:"ssh_private_key"`
WinRMUser *string `mapstructure:"winrm_username" cty:"winrm_username"`
WinRMPassword *string `mapstructure:"winrm_password" cty:"winrm_password"`
WinRMHost *string `mapstructure:"winrm_host" cty:"winrm_host"`
@ -82,10 +82,13 @@ type FlatConfig struct {
// FlatMapstructure returns a new FlatConfig.
// FlatConfig is an auto-generated flat version of Config.
// Where the contents a fields with a `mapstructure:,squash` tag are bubbled up.
func (*Config) FlatMapstructure() interface{} { return new(FlatConfig) }
func (*Config) FlatMapstructure() interface{ HCL2Spec() map[string]hcldec.Spec } {
return new(FlatConfig)
}
// HCL2Spec returns the hcldec.Spec of a FlatConfig.
// This spec is used by HCL to read the fields of FlatConfig.
// HCL2Spec returns the hcl spec of a Config.
// This spec is used by HCL to read the fields of Config.
// The decoded values from this spec will then be applied to a FlatConfig.
func (*FlatConfig) HCL2Spec() map[string]hcldec.Spec {
s := map[string]hcldec.Spec{
"packer_build_name": &hcldec.AttrSpec{Name: "packer_build_name", Type: cty.String, Required: false},

View File

@ -69,7 +69,8 @@ func TestConfig(t *testing.T) {
// Config tests
t.Run("BaseConfig", func(t *testing.T) {
raw := testConfig(cfgFile)
_, errs := NewConfig(raw)
var c Config
errs := c.Prepare(raw)
if errs != nil {
t.Fatalf("Unexpected error in configuration %+v", errs)
@ -80,7 +81,8 @@ func TestConfig(t *testing.T) {
raw := testConfig(cfgFile)
delete(raw, "access_cfg_file")
_, errs := NewConfig(raw)
var c Config
errs := c.Prepare(raw)
expectedErrors := []string{
"'user_ocid'", "'tenancy_ocid'", "'fingerprint'", "'key_file'",
@ -102,7 +104,8 @@ func TestConfig(t *testing.T) {
raw["fingerprint"] = "00:00..."
raw["key_file"] = keyFile.Name()
_, errs := NewConfig(raw)
var c Config
errs := c.Prepare(raw)
if errs != nil {
t.Fatalf("err: %+v", errs)
@ -112,7 +115,8 @@ func TestConfig(t *testing.T) {
t.Run("TenancyReadFromAccessCfgFile", func(t *testing.T) {
raw := testConfig(cfgFile)
c, errs := NewConfig(raw)
var c Config
errs := c.Prepare(raw)
if errs != nil {
t.Fatalf("Unexpected error in configuration %+v", errs)
}
@ -131,7 +135,8 @@ func TestConfig(t *testing.T) {
t.Run("RegionNotDefaultedToPHXWhenSetInOCISettings", func(t *testing.T) {
raw := testConfig(cfgFile)
c, errs := NewConfig(raw)
var c Config
errs := c.Prepare(raw)
if errs != nil {
t.Fatalf("Unexpected error in configuration %+v", errs)
}
@ -156,7 +161,8 @@ func TestConfig(t *testing.T) {
raw := testConfig(cfgFile)
delete(raw, k)
_, errs := NewConfig(raw)
var c Config
errs := c.Prepare(raw)
if !strings.Contains(errs.Error(), k) {
t.Errorf("Expected '%s' to contain '%s'", errs.Error(), k)
@ -168,7 +174,8 @@ func TestConfig(t *testing.T) {
raw := testConfig(cfgFile)
delete(raw, "image_name")
c, errs := NewConfig(raw)
var c Config
errs := c.Prepare(raw)
if errs != nil {
t.Fatalf("Unexpected error in configuration %+v", errs)
}
@ -183,7 +190,8 @@ func TestConfig(t *testing.T) {
raw := testConfig(cfgFile)
raw["user_ocid"] = expected
c, errs := NewConfig(raw)
var c Config
errs := c.Prepare(raw)
if errs != nil {
t.Fatalf("Unexpected error in configuration %+v", errs)
}
@ -199,7 +207,8 @@ func TestConfig(t *testing.T) {
raw := testConfig(cfgFile)
raw["tenancy_ocid"] = expected
c, errs := NewConfig(raw)
var c Config
errs := c.Prepare(raw)
if errs != nil {
t.Fatalf("Unexpected error in configuration %+v", errs)
}
@ -215,7 +224,8 @@ func TestConfig(t *testing.T) {
raw := testConfig(cfgFile)
raw["region"] = expected
c, errs := NewConfig(raw)
var c Config
errs := c.Prepare(raw)
if errs != nil {
t.Fatalf("Unexpected error in configuration %+v", errs)
}
@ -231,7 +241,8 @@ func TestConfig(t *testing.T) {
raw := testConfig(cfgFile)
raw["fingerprint"] = expected
c, errs := NewConfig(raw)
var c Config
errs := c.Prepare(raw)
if errs != nil {
t.Fatalf("Unexpected error in configuration: %+v", errs)
}

View File

@ -16,7 +16,8 @@ func baseTestConfig() *Config {
panic(err)
}
cfg, err := NewConfig(map[string]interface{}{
var c Config
err = c.Prepare(map[string]interface{}{
"availability_domain": "aaaa:US-ASHBURN-AD-1",
// Image
@ -46,7 +47,7 @@ func baseTestConfig() *Config {
if err != nil {
panic(err)
}
return cfg
return &c
}
func testState() multistep.StateBag {

Some files were not shown because too many files have changed in this diff Show More