From 07733e13ba9b107db4338b2f256ef921767ae16c Mon Sep 17 00:00:00 2001 From: peay Date: Mon, 27 Mar 2017 08:28:26 -0400 Subject: [PATCH 1/2] vSphere disks: read disk capacity instead of file size --- .../vsphere/resource_vsphere_virtual_disk.go | 64 ++++++++++++++++--- .../resource_vsphere_virtual_disk_test.go | 2 + 2 files changed, 58 insertions(+), 8 deletions(-) diff --git a/builtin/providers/vsphere/resource_vsphere_virtual_disk.go b/builtin/providers/vsphere/resource_vsphere_virtual_disk.go index 7b0eedccb..a17d43d5c 100644 --- a/builtin/providers/vsphere/resource_vsphere_virtual_disk.go +++ b/builtin/providers/vsphere/resource_vsphere_virtual_disk.go @@ -4,12 +4,14 @@ import ( "fmt" "log" + "errors" "github.com/hashicorp/terraform/helper/schema" "github.com/vmware/govmomi" "github.com/vmware/govmomi/find" "github.com/vmware/govmomi/object" "github.com/vmware/govmomi/vim25/types" "golang.org/x/net/context" + "path" ) type virtualDisk struct { @@ -180,20 +182,66 @@ func resourceVSphereVirtualDiskRead(d *schema.ResourceData, meta interface{}) er return err } - fileInfo, err := ds.Stat(context.TODO(), vDisk.vmdkPath) + ctx := context.TODO() + b, err := ds.Browser(ctx) if err != nil { - log.Printf("[DEBUG] resourceVSphereVirtualDiskRead - stat failed on: %v", vDisk.vmdkPath) - d.SetId("") + return err + } - _, ok := err.(object.DatastoreNoSuchFileError) - if !ok { - return err + // `Datastore.Stat` does not allow to query `VmDiskFileQuery`. Instead, we + // search the datastore manually. + spec := types.HostDatastoreBrowserSearchSpec{ + Query: []types.BaseFileQuery{&types.VmDiskFileQuery{Details: &types.VmDiskFileQueryFlags{ + CapacityKb: true, + DiskType: true, + }}}, + Details: &types.FileQueryFlags{ + FileSize: true, + FileType: true, + Modification: true, + FileOwner: types.NewBool(true), + }, + MatchPattern: []string{path.Base(vDisk.vmdkPath)}, + } + + dsPath := ds.Path(path.Dir(vDisk.vmdkPath)) + task, err := b.SearchDatastore(context.TODO(), dsPath, &spec) + + if err != nil { + log.Printf("[DEBUG] resourceVSphereVirtualDiskRead - could not search datastore for: %v", vDisk.vmdkPath) + return err + } + + info, err := task.WaitForResult(context.TODO(), nil) + if err != nil { + if info == nil || info.Error != nil { + _, ok := info.Error.Fault.(*types.FileNotFound) + if ok { + log.Printf("[DEBUG] resourceVSphereVirtualDiskRead - could not find: %v", vDisk.vmdkPath) + d.SetId("") + return nil + } } + + log.Printf("[DEBUG] resourceVSphereVirtualDiskRead - could not search datastore for: %v", vDisk.vmdkPath) + return err + } + + res := info.Result.(types.HostDatastoreBrowserSearchResults) + log.Printf("[DEBUG] num results: %d", len(res.File)) + if len(res.File) == 0 { + d.SetId("") + log.Printf("[DEBUG] resourceVSphereVirtualDiskRead - could not find: %v", vDisk.vmdkPath) return nil } - fileInfo = fileInfo.GetFileInfo() + + if len(res.File) != 1 { + return errors.New("Datastore search did not return exactly one result") + } + + fileInfo := res.File[0] log.Printf("[DEBUG] resourceVSphereVirtualDiskRead - fileinfo: %#v", fileInfo) - size := fileInfo.(*types.FileInfo).FileSize / 1024 / 1024 / 1024 + size := fileInfo.(*types.VmDiskFileInfo).CapacityKb / 1024 / 1024 d.SetId(vDisk.vmdkPath) diff --git a/builtin/providers/vsphere/resource_vsphere_virtual_disk_test.go b/builtin/providers/vsphere/resource_vsphere_virtual_disk_test.go index c27426ad7..a24ea597e 100644 --- a/builtin/providers/vsphere/resource_vsphere_virtual_disk_test.go +++ b/builtin/providers/vsphere/resource_vsphere_virtual_disk_test.go @@ -27,6 +27,8 @@ func TestAccVSphereVirtualDisk_basic(t *testing.T) { } if v := os.Getenv("VSPHERE_INIT_TYPE"); v != "" { initTypeOpt += fmt.Sprintf(" type = \"%s\"\n", v) + } else { + initTypeOpt += fmt.Sprintf(" type = \"%s\"\n", "thin") } if v := os.Getenv("VSPHERE_ADAPTER_TYPE"); v != "" { adapterTypeOpt += fmt.Sprintf(" adapter_type = \"%s\"\n", v) From 066eea4b352c79c315e221307acc7a232a35811e Mon Sep 17 00:00:00 2001 From: stack72 Date: Mon, 27 Mar 2017 18:09:12 +0300 Subject: [PATCH 2/2] provider/vsphere: Randomize the vsphere_virtual_disk acceptance test ``` % make testacc TEST=./builtin/providers/vsphere TESTARGS='-run=TestAccVSphereVirtualDisk_' ==> Checking that code complies with gofmt requirements... go generate $(go list ./... | grep -v /terraform/vendor/) 2017/03/27 18:08:08 Generated command/internal_plugin_list.go TF_ACC=1 go test ./builtin/providers/vsphere -v -run=TestAccVSphereVirtualDisk_ -timeout 120m === RUN TestAccVSphereVirtualDisk_basic --- PASS: TestAccVSphereVirtualDisk_basic (8.57s) PASS ok github.com/hashicorp/terraform/builtin/providers/vsphere 8.591s ``` --- .../resource_vsphere_virtual_disk_test.go | 21 +++++++++---------- 1 file changed, 10 insertions(+), 11 deletions(-) diff --git a/builtin/providers/vsphere/resource_vsphere_virtual_disk_test.go b/builtin/providers/vsphere/resource_vsphere_virtual_disk_test.go index a24ea597e..d3fef92d0 100644 --- a/builtin/providers/vsphere/resource_vsphere_virtual_disk_test.go +++ b/builtin/providers/vsphere/resource_vsphere_virtual_disk_test.go @@ -6,6 +6,7 @@ import ( "os" "testing" + "github.com/hashicorp/terraform/helper/acctest" "github.com/hashicorp/terraform/helper/resource" "github.com/hashicorp/terraform/terraform" "github.com/vmware/govmomi" @@ -19,6 +20,8 @@ func TestAccVSphereVirtualDisk_basic(t *testing.T) { var initTypeOpt string var adapterTypeOpt string + rString := acctest.RandString(5) + if v := os.Getenv("VSPHERE_DATACENTER"); v != "" { datacenterOpt = v } @@ -39,14 +42,8 @@ func TestAccVSphereVirtualDisk_basic(t *testing.T) { Providers: testAccProviders, CheckDestroy: testAccCheckVSphereVirtualDiskDestroy, Steps: []resource.TestStep{ - resource.TestStep{ - Config: fmt.Sprintf( - testAccCheckVSphereVirtuaDiskConfig_basic, - initTypeOpt, - adapterTypeOpt, - datacenterOpt, - datastoreOpt, - ), + { + Config: testAccCheckVSphereVirtuaDiskConfig_basic(rString, initTypeOpt, adapterTypeOpt, datacenterOpt, datastoreOpt), Check: resource.ComposeTestCheckFunc( testAccVSphereVirtualDiskExists("vsphere_virtual_disk.foo"), ), @@ -119,13 +116,15 @@ func testAccCheckVSphereVirtualDiskDestroy(s *terraform.State) error { return nil } -const testAccCheckVSphereVirtuaDiskConfig_basic = ` +func testAccCheckVSphereVirtuaDiskConfig_basic(rName, initTypeOpt, adapterTypeOpt, datacenterOpt, datastoreOpt string) string { + return fmt.Sprintf(` resource "vsphere_virtual_disk" "foo" { size = 1 - vmdk_path = "tfTestDisk.vmdk" + vmdk_path = "tfTestDisk-%s.vmdk" %s %s datacenter = "%s" datastore = "%s" } -` +`, rName, initTypeOpt, adapterTypeOpt, datacenterOpt, datastoreOpt) +}