diff --git a/digitalocean/resource_digitalocean_project.go b/digitalocean/resource_digitalocean_project.go index 934db282e..5c273a376 100644 --- a/digitalocean/resource_digitalocean_project.go +++ b/digitalocean/resource_digitalocean_project.go @@ -66,8 +66,10 @@ func resourceDigitalOceanProject() *schema.Resource { Description: "the id of the project owner.", }, "is_default": { - Type: schema.TypeBool, - Computed: true, + Type: schema.TypeBool, + Optional: true, + Default: false, + Description: "determine if the project is the default or not.", }, "created_at": { Type: schema.TypeString, @@ -123,6 +125,21 @@ func resourceDigitalOceanProjectCreate(ctx context.Context, d *schema.ResourceDa d.Set("resources", resources) } + if v, ok := d.GetOk("is_default"); ok { + updateReq := &godo.UpdateProjectRequest{ + Name: project.Name, + Description: project.Description, + Purpose: project.Purpose, + Environment: project.Environment, + IsDefault: v.(bool), + } + + _, _, err := client.Projects.Update(context.Background(), project.ID, updateReq) + if err != nil { + return diag.Errorf("Error setting project as default: %s", err) + } + } + d.SetId(project.ID) log.Printf("[INFO] Project created, ID: %s", d.Id()) diff --git a/digitalocean/resource_digitalocean_project_test.go b/digitalocean/resource_digitalocean_project_test.go index 4b74552d5..b5de65a41 100644 --- a/digitalocean/resource_digitalocean_project_test.go +++ b/digitalocean/resource_digitalocean_project_test.go @@ -5,6 +5,7 @@ import ( "fmt" "testing" + "github.com/digitalocean/godo" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/acctest" "github.com/hashicorp/terraform-plugin-sdk/v2/helper/resource" "github.com/hashicorp/terraform-plugin-sdk/v2/terraform" @@ -43,6 +44,75 @@ func TestAccDigitalOceanProject_CreateWithDefaults(t *testing.T) { }) } +func TestAccDigitalOceanProject_CreateWithIsDefault(t *testing.T) { + expectedName := generateProjectName() + expectedIsDefault := "true" + createConfig := fixtureCreateWithIsDefault(expectedName, expectedIsDefault) + + var ( + originalDefaultProject = &godo.Project{} + client = &godo.Client{} + ) + + resource.ParallelTest(t, resource.TestCase{ + PreCheck: func() { + testAccPreCheck(t) + + // Get an store original default project ID + client = testAccProvider.Meta().(*CombinedConfig).godoClient() + defaultProject, _, defaultProjErr := client.Projects.GetDefault(context.Background()) + if defaultProjErr != nil { + t.Errorf("Error locating default project %s", defaultProjErr) + } + originalDefaultProject = defaultProject + }, + ProviderFactories: testAccProviderFactories, + CheckDestroy: testAccCheckDigitalOceanProjectDestroy, + Steps: []resource.TestStep{ + { + Config: createConfig, + ExpectNonEmptyPlan: true, + Check: resource.ComposeTestCheckFunc( + testAccCheckDigitalOceanProjectExists("digitalocean_project.myproj"), + // Restore original default project. This must happen here + // to ensure it runs even if the tests fails. + func(*terraform.State) error { + t.Logf("Restoring original default project: %s (%s)", originalDefaultProject.Name, originalDefaultProject.ID) + originalDefaultProject.IsDefault = true + updateReq := &godo.UpdateProjectRequest{ + Name: originalDefaultProject.Name, + Description: originalDefaultProject.Description, + Purpose: originalDefaultProject.Purpose, + Environment: originalDefaultProject.Environment, + IsDefault: true, + } + _, _, err := client.Projects.Update(context.Background(), originalDefaultProject.ID, updateReq) + if err != nil { + return fmt.Errorf("Error restoring default project %s", err) + } + return nil + }, + resource.TestCheckResourceAttr( + "digitalocean_project.myproj", "name", expectedName), + resource.TestCheckResourceAttr( + "digitalocean_project.myproj", "description", ""), + resource.TestCheckResourceAttr( + "digitalocean_project.myproj", "purpose", "Web Application"), + resource.TestCheckResourceAttr( + "digitalocean_project.myproj", "environment", ""), + resource.TestCheckResourceAttr( + "digitalocean_project.myproj", "is_default", expectedIsDefault), + resource.TestCheckResourceAttrSet("digitalocean_project.myproj", "id"), + resource.TestCheckResourceAttrSet("digitalocean_project.myproj", "owner_uuid"), + resource.TestCheckResourceAttrSet("digitalocean_project.myproj", "owner_id"), + resource.TestCheckResourceAttrSet("digitalocean_project.myproj", "created_at"), + resource.TestCheckResourceAttrSet("digitalocean_project.myproj", "updated_at"), + ), + }, + }, + }) +} + func TestAccDigitalOceanProject_CreateWithInitialValues(t *testing.T) { expectedName := generateProjectName() @@ -441,3 +511,11 @@ func fixtureWithManyResources(domainBase string, name string) string { resources = digitalocean_domain.foobar[*].urn }`, domainBase, name) } + +func fixtureCreateWithIsDefault(name string, is_default string) string { + return fmt.Sprintf(` + resource "digitalocean_project" "myproj" { + name = "%s" + is_default = "%s" + }`, name, is_default) +} diff --git a/docs/resources/project.md b/docs/resources/project.md index 150c184d0..1cf31efe8 100644 --- a/docs/resources/project.md +++ b/docs/resources/project.md @@ -64,6 +64,7 @@ The following arguments are supported: * `purpose` - (Optional) the purpose of the project, (Default: "Web Application") * `environment` - (Optional) the environment of the project's resources. The possible values are: `Development`, `Staging`, `Production`) * `resources` - a list of uniform resource names (URNs) for the resources associated with the project +* `is_default` - (Optional) a boolean indicating whether or not the project is the default project. (Default: "false") ## Attributes Reference