From d583b936b2a0db4a449af32de679f0115cc3a35c Mon Sep 17 00:00:00 2001 From: Martin Atkins Date: Wed, 26 Aug 2015 17:37:09 -0700 Subject: [PATCH] chef_data_bag resource. --- builtin/providers/chef/provider.go | 2 +- builtin/providers/chef/resource_data_bag.go | 77 +++++++++++++++++++ .../providers/chef/resource_data_bag_test.go | 70 +++++++++++++++++ 3 files changed, 148 insertions(+), 1 deletion(-) create mode 100644 builtin/providers/chef/resource_data_bag.go create mode 100644 builtin/providers/chef/resource_data_bag_test.go diff --git a/builtin/providers/chef/provider.go b/builtin/providers/chef/provider.go index 2319d7639..9f3e41255 100644 --- a/builtin/providers/chef/provider.go +++ b/builtin/providers/chef/provider.go @@ -43,7 +43,7 @@ func Provider() terraform.ResourceProvider { //"chef_acl": resourceChefAcl(), //"chef_client": resourceChefClient(), //"chef_cookbook": resourceChefCookbook(), - //"chef_data_bag": resourceChefDataBag(), + "chef_data_bag": resourceChefDataBag(), //"chef_data_bag_item": resourceChefDataBagItem(), //"chef_environment": resourceChefEnvironment(), //"chef_node": resourceChefNode(), diff --git a/builtin/providers/chef/resource_data_bag.go b/builtin/providers/chef/resource_data_bag.go new file mode 100644 index 000000000..a9c08748c --- /dev/null +++ b/builtin/providers/chef/resource_data_bag.go @@ -0,0 +1,77 @@ +package chef + +import ( + "github.com/hashicorp/terraform/helper/schema" + + chefc "github.com/go-chef/chef" +) + +func resourceChefDataBag() *schema.Resource { + return &schema.Resource{ + Create: CreateDataBag, + Read: ReadDataBag, + Delete: DeleteDataBag, + + Schema: map[string]*schema.Schema{ + "name": &schema.Schema{ + Type: schema.TypeString, + Required: true, + ForceNew: true, + }, + "api_uri": &schema.Schema{ + Type: schema.TypeString, + Computed: true, + }, + }, + } +} + +func CreateDataBag(d *schema.ResourceData, meta interface{}) error { + client := meta.(*chefc.Client) + + dataBag := &chefc.DataBag{ + Name: d.Get("name").(string), + } + + result, err := client.DataBags.Create(dataBag) + if err != nil { + return err + } + + d.SetId(dataBag.Name) + d.Set("api_uri", result.URI) + return nil +} + +func ReadDataBag(d *schema.ResourceData, meta interface{}) error { + client := meta.(*chefc.Client) + + // The Chef API provides no API to read a data bag's metadata, + // but we can try to read its items and use that as a proxy for + // whether it still exists. + + name := d.Id() + + _, err := client.DataBags.ListItems(name) + if err != nil { + if errRes, ok := err.(*chefc.ErrorResponse); ok { + if errRes.Response.StatusCode == 404 { + d.SetId("") + return nil + } + } + } + return err +} + +func DeleteDataBag(d *schema.ResourceData, meta interface{}) error { + client := meta.(*chefc.Client) + + name := d.Id() + + _, err := client.DataBags.Delete(name) + if err == nil { + d.SetId("") + } + return err +} diff --git a/builtin/providers/chef/resource_data_bag_test.go b/builtin/providers/chef/resource_data_bag_test.go new file mode 100644 index 000000000..92b74e5df --- /dev/null +++ b/builtin/providers/chef/resource_data_bag_test.go @@ -0,0 +1,70 @@ +package chef + +import ( + "fmt" + "testing" + + chefc "github.com/go-chef/chef" + + "github.com/hashicorp/terraform/helper/resource" + "github.com/hashicorp/terraform/terraform" +) + +func TestAccDataBag_basic(t *testing.T) { + var dataBagName string + resource.Test(t, resource.TestCase{ + PreCheck: func() { testAccPreCheck(t) }, + Providers: testAccProviders, + CheckDestroy: testAccDataBagCheckDestroy(dataBagName), + Steps: []resource.TestStep{ + resource.TestStep{ + Config: testAccDataBagConfig_basic, + Check: testAccDataBagCheckExists("chef_data_bag.test", &dataBagName), + }, + }, + }) +} + +func testAccDataBagCheckExists(rn string, name *string) resource.TestCheckFunc { + return func(s *terraform.State) error { + rs, ok := s.RootModule().Resources[rn] + if !ok { + return fmt.Errorf("resource not found: %s", rn) + } + + if rs.Primary.ID == "" { + return fmt.Errorf("data bag id not set") + } + + client := testAccProvider.Meta().(*chefc.Client) + _, err := client.DataBags.ListItems(rs.Primary.ID) + if err != nil { + return fmt.Errorf("error getting data bag: %s", err) + } + + *name = rs.Primary.ID + + return nil + } +} + +func testAccDataBagCheckDestroy(name string) resource.TestCheckFunc { + return func(s *terraform.State) error { + client := testAccProvider.Meta().(*chefc.Client) + result, err := client.DataBags.ListItems(name) + if err == nil && len(*result) != 0 { + return fmt.Errorf("data bag still exists") + } + if _, ok := err.(*chefc.ErrorResponse); err != nil && !ok { + return fmt.Errorf("got something other than an HTTP error (%v) when getting data bag", err) + } + + return nil + } +} + +const testAccDataBagConfig_basic = ` +resource "chef_data_bag" "test" { + name = "terraform-acc-test-basic" +} +`