Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

List parameters should be flattened if MaxItems == 1 #37

Closed
mmdriley opened this issue Oct 2, 2017 · 11 comments
Closed

List parameters should be flattened if MaxItems == 1 #37

mmdriley opened this issue Oct 2, 2017 · 11 comments
Assignees
Labels
area/providers impact/breaking Fixing this issue will require a breaking change kind/bug Some behavior is incorrect or out of spec
Milestone

Comments

@mmdriley
Copy link
Contributor

mmdriley commented Oct 2, 2017

Terraform's Schema doesn't have an explicit way to indicate "a named group of parameters". To approximate this, providers use a schema.TypeList of schema.Resource with MaxItems: 1. This is pretty common in the AWS provider.

As a concrete example, the aws_alb_target_group resource (doc, src) has an optional group named health_check with MaxItems set to 1. This matches reality, since a target group has exactly one health check.

The bridge brings this field in as an array -- originally as healthCheck, though we explicitly pluralized it so its name matched its type. In this case, though, the type should match the name -- this parameter should be an optional object.

A quick spot check through other instances where MaxItems == 1 suggests this is true generally. We should be projecting lists of length <= 1 as maybe-optional objects.

@lukehoban
Copy link
Member

Interesting - I had noticed a couple other examples of this and thought is was just odd design decision in the Terraform providers, but given the way these get exposed to users in Terraform, it actually makes sense to use lists with max one item as a way of nesting properties.

As you note though - projecting this as an array make far less sense in Pulumi.

@joeduffy joeduffy added customer/lm/m2 kind/bug Some behavior is incorrect or out of spec area/providers labels Oct 3, 2017
@joeduffy joeduffy self-assigned this Oct 10, 2017
@joeduffy joeduffy added this to the 0.8 milestone Oct 10, 2017
@joeduffy joeduffy assigned mmdriley and unassigned joeduffy Oct 10, 2017
@mmdriley mmdriley modified the milestones: 0.8, 0.9 Oct 30, 2017
@joeduffy joeduffy assigned pgavlin and unassigned mmdriley Nov 13, 2017
pgavlin added a commit that referenced this issue Nov 14, 2017
A single-item lists/sets is a Terraform idiom for a set of named
optional parameters. We currently project these as lists; these changes
instead project them as their element type.

Fixes #37.
@joeduffy joeduffy modified the milestones: 0.9, 0.10 Dec 1, 2017
@pgavlin
Copy link
Member

pgavlin commented Jan 22, 2018

@joeduffy @lukehoban are we comfortable moving this to 0.11?

@joeduffy
Copy link
Member

I guess ... this is a breaking change, though, right?

@pgavlin
Copy link
Member

pgavlin commented Jan 22, 2018

Yep, and that's why I ask.

@lukehoban
Copy link
Member

I've generally been moving big breaking changes in libraries to 0.11, with the assumption that https://github.com/pulumi/pulumi-service/issues/15 will be addressed in 0.10 giving us a way to make breaking changes in our libraries without forcing users to take those breaking changes immediately. This will provide a much better answer for how we deploy breaking changes to customers.

@pgavlin pgavlin modified the milestones: 0.10, 0.11 Jan 22, 2018
@lukehoban
Copy link
Member

Note - this is very visible for Kubernetes - see https://github.com/pulumi/pulumi-kubernetes/pull/2/files#diff-2f88940fd609897ac656a04d3cb7c464.

 let nginxvolume = new kubernetes.PersistentVolume("redis", {
         metadata: [{
                 name: "nginxvolume"
         }],
         spec: [{
                 capacity: {
                         storage: "10Gi"
                 },
                 accessModes: ["ReadWriteMany"],
                 persistentVolumeSource: [{
                         gcePersistentDisk: [{
                                 pdName: "test-123"
                         }]
                 }]
         }]
 });

@pgavlin
Copy link
Member

pgavlin commented Feb 16, 2018

I assume we still believe that this is important to address in 0.11, especially given the impact on k8s?

@lukehoban
Copy link
Member

Yes - would love to get this done sooner rather than later - it will be a meaningful breaking change.

One thing I noted to @joeduffy in person yesterday - if we make this change to projection then some things which are not breaking changes for Terraform (increasing MaxItems from 1 to 2), will be breaking changes for us (changing type from scalar to array).

I'm not sure if there is any good alternative to that. And I think generally we'll have to treat adopting new versions of the Terraform provider as (likely) breaking changes (version bumps) in our provider.

But if anyone has ideas on how we could enable this sort of thing to not be a breaking change - that would be even better.

@pgavlin
Copy link
Member

pgavlin commented Feb 16, 2018

But if anyone has ideas on how we could enable this sort of thing to not be a breaking change - that would be even better.

We could always type these as foo | foo[], right?

@lukehoban
Copy link
Member

We could always type these as foo | foo[], right?

Would we do this on the input side for all arrays?

If we only do it for MaxItems=1 then it's still a breaking change when TF changes it to 2.

I assume we would on the output side always make it an array - even in the MaxItems=1 case.

There's a little bit of subtlety there, but I could see that working okay in practice.

@pgavlin
Copy link
Member

pgavlin commented Feb 17, 2018

If we only do it for MaxItems=1 then it's still a breaking change when TF changes it to 2.

Yes, that's a fair point. Would it be too odd to do this for all arrays?

@lukehoban lukehoban assigned lukehoban and unassigned pgavlin Feb 21, 2018
lukehoban added a commit that referenced this issue Feb 22, 2018
This aligns better with the practical usage of TypeList with MaxItems=1 as a way to do nested structs in Terraform providers.

We do this projection and translation for both inputs and outputs.

Fixes #37.
@lukehoban lukehoban added the impact/breaking Fixing this issue will require a breaking change label Feb 23, 2018
lukehoban added a commit that referenced this issue Feb 24, 2018
This aligns better with the practical usage of TypeList with MaxItems=1 as a way to do nested structs in Terraform providers.

We do this projection and translation for both inputs and outputs.

Fixes #37.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
area/providers impact/breaking Fixing this issue will require a breaking change kind/bug Some behavior is incorrect or out of spec
Projects
None yet
Development

No branches or pull requests

5 participants