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

Add boot_disk property to google_compute_instance #122

Merged
merged 5 commits into from
Jun 28, 2017

Conversation

danawillow
Copy link
Contributor

This is change 1 in a series of changes to provide a better experience for attaching/detaching disks to/from instances. The end goal is to have a separate resource for attached disks, in order to have some attached disks that are managed by terraform side-by-side with disks that are managed some other way (such as by k8s), and to allow users to attach/detach disks (see #33)

The order of the changes will look roughly like:

  1. (this) Add boot_disk property
  2. Add scratch_disk property and deprecate disk
  3. Remove disk property, make boot_disk Required
  4. Add google_compute_attached_disk resource and deprecate the attached_disk property

@danawillow
Copy link
Contributor Author

Also note that tests are currently failing, but will be fixed in #1.

@@ -394,12 +469,23 @@ func resourceComputeInstanceCreate(d *schema.ResourceData, meta interface{}) err
}

// Build up the list of disks

disks := []*compute.AttachedDisk{}
var bootDisk *compute.AttachedDisk
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We keep the bootdisk object in scope for the entire function but only use it to perform nil checks outside of the if block below. What if we moved it inside the if block, and pulled up the ok result of d.GetOk("boot_disk");, giving it a name like hasBootDisk?

That way, we know that code later in the function can only interact with the bootDisk as part of disks, and we can make lines like

disk.Boot = i == 0 && bootDisk == nil

look like:

disk.Boot = i == 0 && !hasBootDisk

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done.

@@ -1142,3 +1235,79 @@ func resourceInstanceTags(d *schema.ResourceData) *compute.Tags {

return tags
}

func expandBootDisk(d *schema.ResourceData, config *Config, zone *compute.Zone, project string) (*compute.AttachedDisk, error) {
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It looks like we only use schema elements that are properties of boot_disk.0; we can reduce the information this function needs by passing in a limited set of data, like BackendService's expandBackends()

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The problem with that approach is that it auto-populates all the map keys, and sets them to default values. So if you want to check the existence of something, you have to check against "", 0, false, and nil, rather than being able to use a consistent d.GetOk("whatever"); ok. It seems like you should be able to just do v, ok := data["whatever"]; ok, but that will return true for elements not set in the config, which is a problem when you're then trying to use that value in another call, like in line 1274. This way feels less bug-prone.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That makes sense, thanks!

return disk, nil
}

func flattenBootDisk(d *schema.ResourceData, disk *compute.AttachedDisk) []map[string]interface{} {
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Same as expandBootDisk - do we need access to all of schema.ResourceData here? Or just a subset?

@@ -1187,6 +1248,49 @@ func testAccComputeInstance_attachedDisk(disk, instance string) string {
}`, disk, instance)
}

func testAccComputeInstance_bootDisk(instance string) string {
return fmt.Sprintf(`
resource "google_compute_instance" "foobar" {
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nit: Can you de-indent both of these configs so that the top level is against the left side of the file? That way, they are easier to copy out and modify/test interactively, or for users who browse the source to pull out pre-tested .tf configurations.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'll do it in a separate PR so it's the same for all of them since there are a lot of tests in this file.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Separate PR is submitted, updated here (and other comment as well)

network_interface {
network = "default"
}
}`, instance)
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nit: can the ` be moved to the next line? This would also make using these tests in .tf configs easier.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

likewise

@rileykarson
Copy link
Collaborator

LGTM 👍

Copy link
Contributor

@paddycarver paddycarver left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Only a couple minor comments. This looks great.

"device_name": &schema.Schema{
Type: schema.TypeString,
Optional: true,
Computed: true,
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Does this need to be ForceNew?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yup. Fixed.

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The Forcenew:true would cause the current resource such as a db instance to be recreated. is this desired? maybe I am asking a terraform basic question instead of a google provider one here. thanks.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It means that if the field in question changes in value then it would, yes.


disks := []*compute.AttachedDisk{}
var hasBootDisk bool
if _, hasBootDisk = d.GetOk("boot_disk"); hasBootDisk {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nit: if _, hasBootDisk := means you don't need var hasBootDisk bool.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I need it so I can refer to it outside of the if statement

"device_name": disk.DeviceName,
"source": sourceUrl[len(sourceUrl)-1],
// disk_encryption_key_raw is not returned from the API, so don't store it in state.
// If necessary in the future, this can be copied from what the user originally specified.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think in other places we do the fingerprint of the key. Is that returned from the API?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yup, added

@paddycarver
Copy link
Contributor

Rebase and LGTM. 👍

@danawillow danawillow merged commit 549e131 into hashicorp:master Jun 28, 2017
@danawillow danawillow deleted the boot-disk branch June 28, 2017 22:36
negz pushed a commit to negz/terraform-provider-google that referenced this pull request Oct 17, 2017
* Add boot_disk property to google_compute_instance

* docs for boot_disk

* limit scope of bootDisk, use bool instead

* test formatting

* make device_name forcenew, add sha256 encryption key
chrisst pushed a commit to chrisst/terraform-provider-google that referenced this pull request Nov 9, 2018
* Add boot_disk property to google_compute_instance

* docs for boot_disk

* limit scope of bootDisk, use bool instead

* test formatting

* make device_name forcenew, add sha256 encryption key
@johnmehler
Copy link

This seems like the best place to ask without opening a new ticket-- why does resizing the boot disk force creation of a new resource? Example code below:

boot_disk {
    initialize_params {
      image = "${var.machine_image_id}"
      type  = "${var.boot_disk_type}"
      size  = "${var.boot_disk_size_gb}"
    }
  }
allow_stopping_for_update = true

If the size param is changed and terraform apply is run again, the build plan will include something like

boot_disk.0.initialize_params.0.size: "10" => "200" (forces new resource)

In the console, you can resize (or at least increase the size of) a the boot disk without destroying and recreating it. Is it possible to do so in Terraform?

@danawillow
Copy link
Contributor Author

Hey @johnmehler, that's because the size there is in the initialize_params block, which is specific to creating the disk for the first time. If you want to be able to make changes later, you should use a google_compute_disk resource and use the source property of the boot_disk to reference that disk.

@ghost
Copy link

ghost commented Nov 16, 2018

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!

@ghost ghost locked and limited conversation to collaborators Nov 16, 2018
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

5 participants