mirror of
https://github.com/letic/terraform-provider-google.git
synced 2024-06-29 06:42:36 +00:00
Add 'google_billing_account' data source (#889)
* Add 'google_billing_account' data source. * Use 'GetResourceNameFromSelfLink'. * Use 'ConflictsWith' in schema. * Use pagination for List() API call. * Add ability to filter by 'open' attribute. * Don't use 'ForceNew' for data sources. * Add 'billing_account' argument and make 'name' an output-only attribute. * Correct error message.
This commit is contained in:
parent
5498a33d1b
commit
a086e70e79
131
google/data_source_google_billing_account.go
Normal file
131
google/data_source_google_billing_account.go
Normal file
|
@ -0,0 +1,131 @@
|
|||
package google
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"net/http"
|
||||
"strings"
|
||||
|
||||
"github.com/hashicorp/terraform/helper/schema"
|
||||
|
||||
"google.golang.org/api/cloudbilling/v1"
|
||||
"google.golang.org/api/googleapi"
|
||||
)
|
||||
|
||||
func dataSourceGoogleBillingAccount() *schema.Resource {
|
||||
return &schema.Resource{
|
||||
Read: dataSourceBillingAccountRead,
|
||||
Schema: map[string]*schema.Schema{
|
||||
"billing_account": {
|
||||
Type: schema.TypeString,
|
||||
Optional: true,
|
||||
ConflictsWith: []string{"display_name"},
|
||||
},
|
||||
"display_name": {
|
||||
Type: schema.TypeString,
|
||||
Optional: true,
|
||||
Computed: true,
|
||||
ConflictsWith: []string{"billing_account"},
|
||||
},
|
||||
"open": {
|
||||
Type: schema.TypeBool,
|
||||
Optional: true,
|
||||
Computed: true,
|
||||
},
|
||||
"name": {
|
||||
Type: schema.TypeString,
|
||||
Computed: true,
|
||||
},
|
||||
"project_ids": {
|
||||
Type: schema.TypeSet,
|
||||
Computed: true,
|
||||
Elem: &schema.Schema{
|
||||
Type: schema.TypeString,
|
||||
},
|
||||
},
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
func dataSourceBillingAccountRead(d *schema.ResourceData, meta interface{}) error {
|
||||
config := meta.(*Config)
|
||||
|
||||
open, openOk := d.GetOkExists("open")
|
||||
|
||||
var billingAccount *cloudbilling.BillingAccount
|
||||
if v, ok := d.GetOk("billing_account"); ok {
|
||||
resp, err := config.clientBilling.BillingAccounts.Get(canonicalBillingAccountName(v.(string))).Do()
|
||||
if err != nil {
|
||||
if gerr, ok := err.(*googleapi.Error); ok && gerr.Code == http.StatusNotFound {
|
||||
return fmt.Errorf("Billing account not found: %s", v)
|
||||
}
|
||||
|
||||
return fmt.Errorf("Error reading billing account: %s", err)
|
||||
}
|
||||
|
||||
if openOk && resp.Open != open.(bool) {
|
||||
return fmt.Errorf("Billing account not found: %s", v)
|
||||
}
|
||||
|
||||
billingAccount = resp
|
||||
} else if v, ok := d.GetOk("display_name"); ok {
|
||||
token := ""
|
||||
for paginate := true; paginate; {
|
||||
resp, err := config.clientBilling.BillingAccounts.List().PageToken(token).Do()
|
||||
if err != nil {
|
||||
return fmt.Errorf("Error reading billing accounts: %s", err)
|
||||
}
|
||||
|
||||
for _, ba := range resp.BillingAccounts {
|
||||
if ba.DisplayName == v.(string) {
|
||||
if openOk && ba.Open != open.(bool) {
|
||||
continue
|
||||
}
|
||||
if billingAccount != nil {
|
||||
return fmt.Errorf("More than one matching billing account found")
|
||||
}
|
||||
billingAccount = ba
|
||||
}
|
||||
}
|
||||
|
||||
token = resp.NextPageToken
|
||||
paginate = token != ""
|
||||
}
|
||||
|
||||
if billingAccount == nil {
|
||||
return fmt.Errorf("Billing account not found: %s", v)
|
||||
}
|
||||
} else {
|
||||
return fmt.Errorf("one of billing_account or display_name must be set")
|
||||
}
|
||||
|
||||
resp, err := config.clientBilling.BillingAccounts.Projects.List(billingAccount.Name).Do()
|
||||
if err != nil {
|
||||
return fmt.Errorf("Error reading billing account projects: %s", err)
|
||||
}
|
||||
projectIds := flattenBillingProjects(resp.ProjectBillingInfo)
|
||||
|
||||
d.SetId(GetResourceNameFromSelfLink(billingAccount.Name))
|
||||
d.Set("name", billingAccount.Name)
|
||||
d.Set("display_name", billingAccount.DisplayName)
|
||||
d.Set("open", billingAccount.Open)
|
||||
d.Set("project_ids", projectIds)
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func canonicalBillingAccountName(ba string) string {
|
||||
if strings.HasPrefix(ba, "billingAccounts/") {
|
||||
return ba
|
||||
}
|
||||
|
||||
return "billingAccounts/" + ba
|
||||
}
|
||||
|
||||
func flattenBillingProjects(billingProjects []*cloudbilling.ProjectBillingInfo) []string {
|
||||
projectIds := make([]string, len(billingProjects))
|
||||
for i, billingProject := range billingProjects {
|
||||
projectIds[i] = billingProject.ProjectId
|
||||
}
|
||||
|
||||
return projectIds
|
||||
}
|
104
google/data_source_google_billing_account_test.go
Normal file
104
google/data_source_google_billing_account_test.go
Normal file
|
@ -0,0 +1,104 @@
|
|||
package google
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"regexp"
|
||||
"testing"
|
||||
|
||||
"github.com/hashicorp/terraform/helper/acctest"
|
||||
|
||||
"github.com/hashicorp/terraform/helper/resource"
|
||||
)
|
||||
|
||||
func TestAccDataSourceGoogleBillingAccount_byFullName(t *testing.T) {
|
||||
billingId := getTestBillingAccountFromEnv(t)
|
||||
name := "billingAccounts/" + billingId
|
||||
|
||||
resource.Test(t, resource.TestCase{
|
||||
PreCheck: func() { testAccPreCheck(t) },
|
||||
Providers: testAccProviders,
|
||||
Steps: []resource.TestStep{
|
||||
{
|
||||
Config: testAccCheckGoogleBillingAccount_byName(name),
|
||||
Check: resource.ComposeTestCheckFunc(
|
||||
resource.TestCheckResourceAttr("data.google_billing_account.acct", "id", billingId),
|
||||
resource.TestCheckResourceAttr("data.google_billing_account.acct", "name", name),
|
||||
resource.TestCheckResourceAttr("data.google_billing_account.acct", "open", "true"),
|
||||
),
|
||||
},
|
||||
},
|
||||
})
|
||||
}
|
||||
|
||||
func TestAccDataSourceGoogleBillingAccount_byShortName(t *testing.T) {
|
||||
billingId := getTestBillingAccountFromEnv(t)
|
||||
name := "billingAccounts/" + billingId
|
||||
|
||||
resource.Test(t, resource.TestCase{
|
||||
PreCheck: func() { testAccPreCheck(t) },
|
||||
Providers: testAccProviders,
|
||||
Steps: []resource.TestStep{
|
||||
{
|
||||
Config: testAccCheckGoogleBillingAccount_byName(billingId),
|
||||
Check: resource.ComposeTestCheckFunc(
|
||||
resource.TestCheckResourceAttr("data.google_billing_account.acct", "id", billingId),
|
||||
resource.TestCheckResourceAttr("data.google_billing_account.acct", "name", name),
|
||||
resource.TestCheckResourceAttr("data.google_billing_account.acct", "open", "true"),
|
||||
),
|
||||
},
|
||||
},
|
||||
})
|
||||
}
|
||||
|
||||
func TestAccDataSourceGoogleBillingAccount_byFullNameClosed(t *testing.T) {
|
||||
billingId := getTestBillingAccountFromEnv(t)
|
||||
name := "billingAccounts/" + billingId
|
||||
|
||||
resource.Test(t, resource.TestCase{
|
||||
PreCheck: func() { testAccPreCheck(t) },
|
||||
Providers: testAccProviders,
|
||||
Steps: []resource.TestStep{
|
||||
{
|
||||
Config: testAccCheckGoogleBillingAccount_byNameClosed(name),
|
||||
ExpectError: regexp.MustCompile("Billing account not found: " + name),
|
||||
},
|
||||
},
|
||||
})
|
||||
}
|
||||
|
||||
func TestAccDataSourceGoogleBillingAccount_byDisplayName(t *testing.T) {
|
||||
name := acctest.RandString(16)
|
||||
|
||||
resource.Test(t, resource.TestCase{
|
||||
PreCheck: func() { testAccPreCheck(t) },
|
||||
Providers: testAccProviders,
|
||||
Steps: []resource.TestStep{
|
||||
{
|
||||
Config: testAccCheckGoogleBillingAccount_byDisplayName(name),
|
||||
ExpectError: regexp.MustCompile("Billing account not found: " + name),
|
||||
},
|
||||
},
|
||||
})
|
||||
}
|
||||
|
||||
func testAccCheckGoogleBillingAccount_byName(name string) string {
|
||||
return fmt.Sprintf(`
|
||||
data "google_billing_account" "acct" {
|
||||
billing_account = "%s"
|
||||
}`, name)
|
||||
}
|
||||
|
||||
func testAccCheckGoogleBillingAccount_byNameClosed(name string) string {
|
||||
return fmt.Sprintf(`
|
||||
data "google_billing_account" "acct" {
|
||||
billing_account = "%s"
|
||||
open = false
|
||||
}`, name)
|
||||
}
|
||||
|
||||
func testAccCheckGoogleBillingAccount_byDisplayName(name string) string {
|
||||
return fmt.Sprintf(`
|
||||
data "google_billing_account" "acct" {
|
||||
display_name = "%s"
|
||||
}`, name)
|
||||
}
|
|
@ -60,6 +60,7 @@ func Provider() terraform.ResourceProvider {
|
|||
},
|
||||
|
||||
DataSourcesMap: map[string]*schema.Resource{
|
||||
"google_billing_account": dataSourceGoogleBillingAccount(),
|
||||
"google_dns_managed_zone": dataSourceDnsManagedZone(),
|
||||
"google_client_config": dataSourceGoogleClientConfig(),
|
||||
"google_compute_address": dataSourceGoogleComputeAddress(),
|
||||
|
|
46
website/docs/d/google_billing_account.html.markdown
Normal file
46
website/docs/d/google_billing_account.html.markdown
Normal file
|
@ -0,0 +1,46 @@
|
|||
---
|
||||
layout: "google"
|
||||
page_title: "Google: google_billing_account"
|
||||
sidebar_current: "docs-google-datasource-billing-account"
|
||||
description: |-
|
||||
Get information about a Google Billing Account.
|
||||
---
|
||||
|
||||
# google\_billing\_account
|
||||
|
||||
Use this data source to get information about a Google Billing Account.
|
||||
|
||||
```hcl
|
||||
data "google_billing_account" "acct" {
|
||||
display_name = "My Billing Account"
|
||||
open = true
|
||||
}
|
||||
|
||||
resource "google_project" "my_project" {
|
||||
name = "My Project"
|
||||
project_id = "your-project-id"
|
||||
org_id = "1234567"
|
||||
|
||||
billing_account = "${data.google_billing_account.acct.id}"
|
||||
}
|
||||
```
|
||||
|
||||
## Argument Reference
|
||||
|
||||
The arguments of this data source act as filters for querying the available billing accounts.
|
||||
The given filters must match exactly one billing account whose data will be exported as attributes.
|
||||
The following arguments are supported:
|
||||
|
||||
* `billing_account` (Optional) - The name of the billing account in the form `{billing_account_id}` or `billingAccounts/{billing_account_id}`.
|
||||
* `display_name` (Optional) - The display name of the billing account.
|
||||
* `open` (Optional) - `true` if the billing account is open, `false` if the billing account is closed.
|
||||
|
||||
~> **NOTE:** One of `billing_account` or `display_name` must be specified.
|
||||
|
||||
## Attributes Reference
|
||||
|
||||
The following additional attributes are exported:
|
||||
|
||||
* `id` - The billing account ID.
|
||||
* `name` - The resource name of the billing account in the form `billingAccounts/{billing_account_id}`.
|
||||
* `project_ids` - The IDs of any projects associated with the billing account.
|
|
@ -13,6 +13,9 @@
|
|||
<li<%= sidebar_current("docs-google-datasource") %>>
|
||||
<a href="#">Google Cloud Platform Data Sources</a>
|
||||
<ul class="nav nav-visible">
|
||||
<li<%= sidebar_current("docs-google-datasource-billing-account") %>>
|
||||
<a href="/docs/providers/google/d/google_billing_account.html">google_billing_account</a>
|
||||
</li>
|
||||
<li<%= sidebar_current("docs-google-datasource-client-config") %>>
|
||||
<a href="/docs/providers/google/d/datasource_client_config.html">google_client_config</a>
|
||||
</li>
|
||||
|
@ -136,7 +139,7 @@
|
|||
</li>
|
||||
<li<%= sidebar_current("docs-google-service-account") %>>
|
||||
<a href="/docs/providers/google/r/google_service_account.html">google_service_account</a>
|
||||
</li>
|
||||
</li>
|
||||
<li<%= sidebar_current("docs-google-service-account-iam") %>>
|
||||
<a href="/docs/providers/google/r/google_service_account_iam.html">google_service_account_iam_binding</a>
|
||||
</li>
|
||||
|
|
Loading…
Reference in New Issue
Block a user