-
Notifications
You must be signed in to change notification settings - Fork 4.6k
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
Implement DigitalOcean Droplet FI Task #3707
Conversation
CI not happy |
Name: subnetName, | ||
// region and zone are the same for DO | ||
Region: region, | ||
Zone: 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.
Hmm... we should be able to cope without a Zone being set, but I'm guessing something breaks ?
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.
Yes, the FindZonesForInstanceGroup function only inserts to list if Zone is set, and so this check fails. Any objections to add a region check there?
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.
No objections, particularly if we can scope it to DO. The root issue there is that EBS volumes on AWS / PDs on GCE are single zone, and thus we need to figure out the zone. But it looks like DO volumes are regional (wow!) so it's fine to relax that check. I would want to see the existing checks for AWS & GCE continue to work (likely by a switch statement on the cloudproviderid).
} | ||
cluster.Spec.Subnets = append(cluster.Spec.Subnets, *subnet) | ||
} | ||
zoneToSubnetMap[region] = subnet |
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'd be in favor of a region
flag in future, but we can run with this...
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.
Agreed!
@@ -80,9 +80,6 @@ func ValidateCluster(c *kops.Cluster, strict bool) *field.Error { | |||
switch kops.CloudProviderID(c.Spec.CloudProvider) { | |||
case kops.CloudProviderBareMetal: | |||
requiresSubnets = false | |||
if c.Spec.NetworkCIDR != "" { | |||
return field.Invalid(fieldSpec.Child("NetworkCIDR"), c.Spec.NetworkCIDR, "NetworkCIDR should not be set on bare metal") |
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!
var _ fi.ModelBuilder = &DropletBuilder{} | ||
|
||
func (d *DropletBuilder) Build(c *fi.ModelBuilderContext) error { | ||
sshKeyName, err := d.SSHKeyName() |
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.
We could tweak SSHKeyName to return something you don't have to parse if that would help...
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.
Noted! Didn't want to creep too much into other packages but this seems like a good future optimization!
splitSSHKeyName := strings.Split(sshKeyName, "-") | ||
sshKeyFingerPrint := splitSSHKeyName[len(splitSSHKeyName)-1] | ||
|
||
// replace "." with "-" since DO API does not accept "." |
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.
GCE has a similar issue, and has SafeClusterName
- you might want to create a similar function for DO, depending on how often you end up using it!
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.
ahh, that's useful noted!
droplet.Name = fi.String(name) | ||
// during alpha support we only allow 1 region | ||
// validation for only 1 region is done at this point | ||
droplet.Region = fi.String(d.Cluster.Spec.Subnets[0].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.
FYI, single-region is actually pretty deep in the k8s design today
return nil | ||
} | ||
|
||
func handleResponse(resp *godo.Response) error { |
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 take it that godo now handles this for you?
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.
Yes! That was actually always the case, just only recently found out :)
var _ fi.CompareWithID = &Droplet{} | ||
|
||
func (d *Droplet) CompareWithID() *string { | ||
return d.ID |
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.
CompareWithID is used to identify two objects that are the same thing, in particular when an object refers to another object. e.g. If Image was actually an object here, we might have two Droplet objects that both set a stub Image, and we might define a task for that Image, and we want to match all 3. CompareWithID is what is matched to match them.
The reason we care about reconciling the duplicates is primarily for dependency analysis, so we can know to run the Image task before the Droplet task in this example.
So in this case, you probably want to compare by Name, because that is what you would set in a stub Droplet I would guess - in particular you're unlikely to know the ID. But in practice, it probably doesn't matter anyway, unless you're actually creating stub Droplets in another task.
|
||
func (_ *Droplet) RenderDO(t *do.DOAPITarget, a, e, changes *Droplet) error { | ||
if a != nil { | ||
return nil |
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.
It can be a good idea to do something like this:
if a != nil && changes != nil {
empty := &Disk{}
if !reflect.DeepEqual(empty, changes) {
return fmt.Errorf("Cannot apply changes to Disk: %v", changes)
}
}
Or at least warn that you're not updating e.g. the Image, even if it isn't an error. But this is the hardest bit (e.g. if someone changes the image, what do you want to do), so I think it's fine to build this up relatively incrementally as well..
if changes.Size != nil { | ||
return fi.CannotChangeField("Size") | ||
} | ||
if changes.Image != nil { |
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 - well there we go - they can't change the image 👍
Looks like you added a package so you need to run Code LGTM - I added some comments primarily to try to explain what some of the things are used for, but I think we should get this in and iterate (once CI is happy!) /lgtm |
/lgtm cancel //PR changed after LGTM, removing LGTM. @andrewsykim @justinsb |
/lgtm Thanks @andrewsykim ! |
[APPROVALNOTIFIER] This PR is APPROVED This pull-request has been approved by: justinsb The full list of commands accepted by this bot can be found here.
Needs approval from an approver in each of these OWNERS Files:
You can indicate your approval by writing |
/test all [submit-queue is verifying that this PR is safe to merge] |
I'll have a follow up PR soon with the improvements you suggested! |
Automatic merge from submit-queue. |
ref: #2150 |
Implements cloudup fi tasks for DigitalOcean droplets. It makes a few assumptions to reduce the size of this PR, those will be addressed in future PRs.
Also does some cleanup in the DigitalOcean
dns
package.