-
Notifications
You must be signed in to change notification settings - Fork 1.8k
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
Add support for regional GKE clusters in google_container_cluster #1181
Add support for regional GKE clusters in google_container_cluster #1181
Conversation
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks @ashish-amarnath for taking on this feature! Here are some initial comments.
google/resource_container_cluster.go
Outdated
@@ -393,7 +412,13 @@ func resourceContainerCluster() *schema.Resource { | |||
} | |||
|
|||
func resourceContainerClusterCreate(d *schema.ResourceData, meta interface{}) error { | |||
containerApiVersion := getContainerApiVersion(d, ContainerClusterBaseApiVersion, ContainerClusterVersionedFeatures) | |||
_, isRegionalCluster := d.GetOk("region") | |||
if isRegionalCluster { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This block isn't necessary- you can just add the feature to the var as defined at the top of the file. The name of it should be the name of the field in the schema, so "region"
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Got it! Thanks.
google/resource_container_cluster.go
Outdated
@@ -447,19 +472,35 @@ func resourceContainerClusterCreate(d *schema.ResourceData, meta interface{}) er | |||
} | |||
|
|||
if v, ok := d.GetOk("additional_zones"); ok { | |||
if isRegionalCluster { | |||
return fmt.Errorf("'additional_zones' is incompatible with regional clusters") |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This should be doable with ConflictsWith
in the schema
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thank you. That should simplify this.
google/resource_container_cluster.go
Outdated
Elem: &schema.Schema{Type: schema.TypeString}, | ||
}, | ||
|
||
"num_nodes": { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This doesn't seem to get used anywhere
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I see that this is not a new field added to support regional clusters. So this is not relevant to this PR. Removing this. But we'll have to add this later.
google/resource_container_cluster.go
Outdated
} | ||
} | ||
locations = append(locations, zoneName) | ||
cluster.Locations = locations | ||
} | ||
|
||
if isRegionalCluster { | ||
locations := []string{} | ||
locations = append(locations, d.Get("region").(string)) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think the locations field is still supposed to be just a list of zones- this will likely still work without this entire block (and the node_locations
field)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I see that this is not a new field added to support regional clusters. So this is not relevant to this PR. Removing this. But we'll have to add this later. As additional_zones
is getting deprecated.
google/resource_dataproc_cluster.go
Outdated
@@ -797,7 +797,7 @@ func flattenPreemptibleInstanceGroupConfig(d *schema.ResourceData, icg *dataproc | |||
func flattenInstanceGroupConfig(d *schema.ResourceData, icg *dataproc.InstanceGroupConfig) []map[string]interface{} { | |||
disk := map[string]interface{}{} | |||
data := map[string]interface{}{ | |||
//"instance_names": []string{}, | |||
//"instance_names": []string{}, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
this can be reverted, it's not really relevant here
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Reverted.
@danawillow I took another stab at this and I need some help to update the |
The API as it is in the vendor directory should work. Instead of |
Thanks for those pointers. I should be able to make more progress with this. |
fc3d5d8
to
d7734e6
Compare
The test is now able to create regional GKE clusters. This is most likely because the support is only implemented to create regional clusters but not to update, read or destroy. Next step: Make this work! |
@ashish-amarnath I just wanted to say thanks for your efforts with this, I don't know enough golang to help out with the implementation but if i (we - people on my team) can help with testing in any way just ask |
@Stono Thanks for offering to help! I will surely ask for help validating this change. Right now I am trying to a checkpoint where this is can spin-up and teardown regional clusters. This is not the top priority for us right now so I am trying to backfill my time working on this. For that reason, and my unfamiliarity with this codebase are the reasons for the slow progress. I am not blocked. @danawillow has been super helpful in unblocking me :) |
Made more progress on this. I now have code and unit test to successfully create and destroy regional GKE clusters. Next, I need to work on the Update operation and then there are merge conflicts that I have to resolve, of course. |
47050ab
to
6d1bc50
Compare
@danawillow this PR is ready for more feedback. I need to add some more tests. Suggestions are welcome :) |
google/resource_container_cluster.go
Outdated
if err != nil { | ||
return err | ||
|
||
if isRegionalCluster { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Since the location could also be the zone, I don't think we actually need this conditional- it should be fine to just always do the Projects.Locations
call
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
That made sense. But didn't what that change to have unknown side-effects. I will give that a try.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Fixed.
google/resource_container_cluster.go
Outdated
} | ||
|
||
cluster := &containerBeta.Cluster{} | ||
var clust interface{} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Did this work for you when you tested it? I've tried this approach (just doing the Convert
from an interface at the end) in the past and it failed for me because Convert needed the parameter passed to be a struct of a certain type (so it can recurse through the fields).
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Well.. It compiled right and the tests passed. From that, I figured it works. Any other tests I can run to be doubly sure?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@danawillow What did you to break this? I'd like to make sure this will not break later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Looks like it works! I must have done something slightly differently when I tried doing it this way in the past.
google/resource_container_cluster.go
Outdated
switch containerAPIVersion { | ||
case v1: | ||
op, err = config.clientContainer.Projects.Zones.Clusters.Update( | ||
project, zoneName, clusterName, req).Do() |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This change makes me nervous- it feels a bit brittle to me to have this depending on what the value of req is at the time this function gets called. If you'd like to refactor it out, I think wrapping it in another function that takes in req as a parameter and returns this func would be a safer choice.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I agree. For that exact reason, I tried going the function route but quickly realised that that number of args to that function became too many and that made me a little uncomfortable. That function would need config, project, zone, region, isRegionalCluster, request, clusterName, timeout, apiVersion
.
Total of 9 args. But, collapsing zone and region into location
that number could go down to 8.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ah yeah, I was more just thinking that only req
would be the parameter since it's the only thing that would change between requests.
@@ -1001,15 +1031,33 @@ func resourceContainerClusterUpdate(d *schema.ResourceData, meta interface{}) er | |||
} | |||
|
|||
updateF := func() error { | |||
log.Println("[DEBUG] emilyye updating enable_legacy_abac") | |||
op, err := config.clientContainer.Projects.Zones.Clusters.LegacyAbac(project, zoneName, clusterName, req).Do() | |||
log.Println("[DEBUG] updating enable_legacy_abac") |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
thanks :)
Steps: []resource.TestStep{ | ||
{ | ||
Config: testAccContainerCluster_regional(clusterName), | ||
}, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can you add another test step that does an import? There are a bunch of examples elsewhere in this file.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Will do.
google/resource_container_cluster.go
Outdated
var zoneName string | ||
locations := []string{} | ||
regionName, isRegionalCluster := d.GetOk("region") | ||
if !isRegionalCluster { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Here's an idea- what if instead of separate "region" and "zone" fields, we just had a "location" field? Then once regional clusters have gone GA we can deprecate zone. I'm not totally set on this, but it does seem like it would simplify the logic. What do you think?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thought about that. But because that would increase the surface area of this change I decided against it. I'll do this if that is not too bad. If that makes sense :)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yup, that's fair. I do think that having it as two separate fields probably makes it a bit clearer to users what to put, so I'm fine with that.
8e4f9c7
to
fc27105
Compare
I've had other things taking up my time and haven't had a chance to work on this for a while. Just so you don't think I've vanished off the face of the Earth! |
Hey, |
@ashish-amarnath @danawillow Thanks for all the hard work on this. I am very interested in this PR but since there is no upgrade path from zone-based clusters to regional ones and I have to set up a few clusters in the near future, I am curious what might be the best approach to take in terms of getting them into terraform after? I see 2 options.
Any recommendations or even timelines? Even if this was merged how often does the provider get released? Or do you need any help testing this? |
@ashish-amarnath, I think there were just a few small changes that were remaining, right? I don't mind making them and pushing them to your branch if you're all right with that. Seems like people are pretty eager for this :) @drubin, we usually aim to release every 2 weeks or so, with one aimed for the next few days. So if this gets in today it'll be in the next release, if not probably not. Even though I think the schema for this is set, I'm also pretty hesitant about solution 1. If this doesn't make it into the next release, then I think solution 3 will be totally fine. |
* implement operation wait for v1beta1 api * implement container clusters get for regional clusters * implement container clusters delete for regional cluster * implement container clusters update for regional cluster * simplify logic by using generic 'location' instead of 'zone' and 'region' * implement a method to generate the update function and refactor * rebase and fix
fc27105
to
1e1ace0
Compare
I haven't had the time to pick-up where I left off on this. |
hey @rosbo, since the changes I made are non-trivial I wouldn't mind having you look at this as well if you don't mind |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Only one small comment.
google/resource_container_cluster.go
Outdated
locations = append(locations, location) | ||
if location == zoneName { | ||
return fmt.Errorf("additional_zones should not contain the original 'zone'.") | ||
loc := v.(string) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Consider simplifying this by using convertStringSet and schema.Set#Contains.
Also I am not sure why we have this block below:
if isZone(location) {
locations = append(locations, location)
}
Why are we adding the "main" zone to the list of additional zones... Consider adding a comment to clarify this.
…shicorp#1181) * Add support for regional GKE clusters in google_container_cluster: * implement operation wait for v1beta1 api * implement container clusters get for regional clusters * implement container clusters delete for regional cluster * implement container clusters update for regional cluster * simplify logic by using generic 'location' instead of 'zone' and 'region' * implement a method to generate the update function and refactor * rebase and fix * reorder container_operation fns * cleanup * add import support and docs * additional locations cleanup
I'm going to lock this issue because it has been closed for 30 days ⏳. This helps our maintainers find and focus on the active issues. If you feel this issue should be reopened, we encourage creating a new issue linking back to this one for added context. If you feel I made an error 🤖 🙉 , please reach out to my human friends 👉 [email protected]. Thanks! |
This is a work in progress PR.
An initial set of changes to share and get feedback on the approach.