How to accept a list of objects in Waypoint configuration?

Hello there,

I would like users to be able to pass a list of objects as a parameter in waypoint.hcl for a plugin I am building.

The configuration should look something like this:

deploy {
    use "appengine" {
      # ...other parameters
      # How to make handlers work ?
      handlers = [
        {
          url = "/.*"
          script = "auto"
          secure = "always"
        }
      ]
    }
  }

The DeployConfig struct in Go looks like this:

type DeployConfig struct {
        // Other config fields...
	Handlers                  []Handler         `hcl:"handlers,optional"`
}

type Handler struct {
	URL    string `hcl:"url"`
	Script string `hcl:"script"`
	Secure string `hcl:"secure"`
}

This generates the following error:
Validating required plugins...panic: unsuitable DecodeExpression target: no cty.Type for struct { URL string "hcl:\"url\""; Script string "hcl:\"script\""; Secure string "hcl:\"secure\"" } (no cty field tags)

Anyone knows how to make this work ?

I found this issue on GitHub but I doesn’t have any answers: https://github.com/hashicorp/hcl/issues/396

Thanks,

Hey @sharkyze,

The way I would tend to handle this in HCL is to use block, you could then write your config like so:

deploy {
    use "appengine" {
      # ...other parameters
      # How to make handlers work ?
      handler {
          url = "/.*"
          script = "auto"
          secure = "always"
        }

        handler {
          url = "/another"
          script = "auto"
          secure = "always"
        }
    }
  }

In your code you would write:

type DeployConfig struct {
        // Other config fields...
	Handlers  []Handler `hcl:"handler,block"`
}

type Handler struct {
	URL    string `hcl:"url"`
	Script string `hcl:"script"`
	Secure string `hcl:"secure"`
}

When HCL parses the config it will automatically read each of the handler blocks and process it into your array.

block would also work with your original syntax:

handlers = [
        {
          url = "/.*"
          script = "auto"
          secure = "always"
        }
      ]

Note: When you use block HCL will not validate that there are elements in the array, or that no handlers were defined. You would need to validate this yourself.

1 Like

Hey @nic,

Great thank you so much, I was able to make the syntax with the repeated blocks work with your suggestion. Unfortunately, the following syntax triggers the error below.

handlers = [
        {
          url = "/.*"
          script = "auto"
          secure = "always"
        }
]

Triggers the following error:
waypoint.hcl:106,7-15: Unsupported argument; An argument named "handlers" is not expected here. Did you mean to define a block of type "handlers"?

Is this expected ?

Did you use the singular handler when defining the hcl tag, if so you will have to use that in the array form too.

No I am using plural handlers in the tag as well as in my configuration file.

Here is the source code: https://github.com/sharkyze/waypoint-plugin-appengine/blob/e9b264611d4f0b7470f0da5209f0ea3b3bb36747/platform/deploy.go#L29

EDIT: Do you mean I have to define the handler singular in the struct tag and then use handlers plural for the array :upside_down_face: ?