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

Make billing budget filter credit_types and subaccounts updatable #13466

Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions .changelog/7035.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
```release-note:enhancement
billingbudget: Make fields `credit_types` and `subaccounts` updatable for `google_billing_budget`
```
12 changes: 9 additions & 3 deletions google/resource_billing_budget.go
Original file line number Diff line number Diff line change
Expand Up @@ -203,7 +203,9 @@ Exactly one of 'calendar_period', 'custom_period' must be provided. Possible val
Optional: true,
Description: `Optional. If creditTypesTreatment is INCLUDE_SPECIFIED_CREDITS,
this is a list of credit types to be subtracted from gross cost to determine the spend for threshold calculations. See a list of acceptable credit type values.
If creditTypesTreatment is not INCLUDE_SPECIFIED_CREDITS, this field must be empty.`,
If creditTypesTreatment is not INCLUDE_SPECIFIED_CREDITS, this field must be empty.

**Note:** If the field has a value in the config and needs to be removed, the field has to be an emtpy array in the config.`,
Elem: &schema.Schema{
Type: schema.TypeString,
},
Expand Down Expand Up @@ -336,7 +338,9 @@ specifying that usage from only this set of subaccounts should
be included in the budget. If a subaccount is set to the name of
the parent account, usage from the parent account will be included.
If the field is omitted, the report will include usage from the parent
account and all subaccounts, if they exist.`,
account and all subaccounts, if they exist.

**Note:** If the field has a value in the config and needs to be removed, the field has to be an emtpy array in the config.`,
Elem: &schema.Schema{
Type: schema.TypeString,
},
Expand Down Expand Up @@ -564,7 +568,9 @@ func resourceBillingBudgetUpdate(d *schema.ResourceData, meta interface{}) error
"budgetFilter.calendarPeriod",
"budgetFilter.customPeriod",
"budgetFilter.services",
"budgetFilter.creditTypesTreatment")
"budgetFilter.creditTypesTreatment",
"budgetFilter.creditTypes",
"budgetFilter.subaccounts")
}

if d.HasChange("amount") {
Expand Down
7 changes: 4 additions & 3 deletions google/resource_billing_budget_generated_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -168,9 +168,10 @@ resource "google_billing_budget" "budget" {
display_name = "Example Billing Budget%{random_suffix}"

budget_filter {
projects = ["projects/${data.google_project.project.number}"]
credit_types_treatment = "EXCLUDE_ALL_CREDITS"
services = ["services/24E6-581D-38E5"] # Bigquery
projects = ["projects/${data.google_project.project.number}"]
credit_types_treatment = "INCLUDE_SPECIFIED_CREDITS"
services = ["services/24E6-581D-38E5"] # Bigquery
credit_types = ["PROMOTION", "FREE_TIER"]
}

amount {
Expand Down
123 changes: 120 additions & 3 deletions google/resource_billing_budget_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -122,6 +122,121 @@ func TestAccBillingBudget_billingBudgetUpdate(t *testing.T) {
})
}

func TestAccBillingBudget_billingFilterSubaccounts(t *testing.T) {
t.Parallel()

context := map[string]interface{}{
"master_billing_acct": getTestMasterBillingAccountFromEnv(t),
"random_suffix": randString(t, 10),
}

vcrTest(t, resource.TestCase{
PreCheck: func() { testAccPreCheck(t) },
Providers: testAccProviders,
CheckDestroy: testAccCheckBillingBudgetDestroyProducer(t),
Steps: []resource.TestStep{
{
Config: testAccBillingBudget_billingFilterSubaccounts(context),
},
{
ResourceName: "google_billing_budget.budget",
ImportState: true,
ImportStateVerify: true,
},
{
Config: testAccBillingBudget_billingFilterRemoveSubaccounts(context),
},
{
ResourceName: "google_billing_budget.budget",
ImportState: true,
ImportStateVerify: true,
},
},
})
}

func testAccBillingBudget_billingFilterSubaccounts(context map[string]interface{}) string {
return Nprintf(`
data "google_billing_account" "account" {
billing_account = "%{master_billing_acct}"
}

data "google_project" "project" {
}

resource "google_billing_subaccount" "subaccount" {
display_name = "My Billing Account"
master_billing_account = data.google_billing_account.account.id
}

resource "google_billing_budget" "budget" {
billing_account = data.google_billing_account.account.id
display_name = "Example Billing Budget%{random_suffix}"

budget_filter {
projects = ["projects/${data.google_project.project.number}"]
labels = {
label = "bar"
}

subaccounts = ["billingAccounts/${google_billing_subaccount.subaccount.billing_account_id}"]
}

amount {
specified_amount {
units = "100000"
}
}

threshold_rules {
threshold_percent = 1.0
}
threshold_rules {
threshold_percent = 1.0
spend_basis = "FORECASTED_SPEND"
}
}
`, context)
}

func testAccBillingBudget_billingFilterRemoveSubaccounts(context map[string]interface{}) string {
return Nprintf(`
data "google_billing_account" "account" {
billing_account = "%{master_billing_acct}"
}

data "google_project" "project" {
}

resource "google_billing_budget" "budget" {
billing_account = data.google_billing_account.account.id
display_name = "Example Billing Budget%{random_suffix}"

budget_filter {
projects = ["projects/${data.google_project.project.number}"]
labels = {
label = "bar"
}
subaccounts = []
}

amount {
specified_amount {
units = "100000"
}
}

threshold_rules {
threshold_percent = 1.0
}
threshold_rules {
threshold_percent = 1.0
spend_basis = "FORECASTED_SPEND"
}
}
`, context)
}

func testAccBillingBudget_billingBudgetUpdateStart(context map[string]interface{}) string {
return Nprintf(`
resource "google_pubsub_topic" "topic1" {
Expand Down Expand Up @@ -242,8 +357,9 @@ resource "google_billing_budget" "budget" {
labels = {
label1 = "bar2"
}
credit_types_treatment = "INCLUDE_ALL_CREDITS"
services = ["services/24E6-581D-38E5"] # Bigquery
credit_types_treatment = "INCLUDE_SPECIFIED_CREDITS"
services = ["services/24E6-581D-38E5"] # Bigquery
credit_types = ["PROMOTION", "FREE_TIER"]
}

amount {
Expand Down Expand Up @@ -350,8 +466,9 @@ resource "google_billing_budget" "budget" {
year = 2023
month = 12
day = 31
}
}
}
credit_types = []
}

amount {
Expand Down
9 changes: 6 additions & 3 deletions website/docs/r/billing_budget.html.markdown
Original file line number Diff line number Diff line change
Expand Up @@ -104,9 +104,10 @@ resource "google_billing_budget" "budget" {
display_name = "Example Billing Budget"

budget_filter {
projects = ["projects/${data.google_project.project.number}"]
credit_types_treatment = "EXCLUDE_ALL_CREDITS"
services = ["services/24E6-581D-38E5"] # Bigquery
projects = ["projects/${data.google_project.project.number}"]
credit_types_treatment = "INCLUDE_SPECIFIED_CREDITS"
services = ["services/24E6-581D-38E5"] # Bigquery
credit_types = ["PROMOTION", "FREE_TIER"]
}

amount {
Expand Down Expand Up @@ -338,6 +339,7 @@ The following arguments are supported:
Optional. If creditTypesTreatment is INCLUDE_SPECIFIED_CREDITS,
this is a list of credit types to be subtracted from gross cost to determine the spend for threshold calculations. See a list of acceptable credit type values.
If creditTypesTreatment is not INCLUDE_SPECIFIED_CREDITS, this field must be empty.
**Note:** If the field has a value in the config and needs to be removed, the field has to be an emtpy array in the config.

* `subaccounts` -
(Optional)
Expand All @@ -347,6 +349,7 @@ The following arguments are supported:
the parent account, usage from the parent account will be included.
If the field is omitted, the report will include usage from the parent
account and all subaccounts, if they exist.
**Note:** If the field has a value in the config and needs to be removed, the field has to be an emtpy array in the config.

* `labels` -
(Optional)
Expand Down