diff --git a/terraform/azure_billing/.terraform.lock.hcl b/terraform/azure_billing/.terraform.lock.hcl new file mode 100644 index 00000000..ee5d1dcc --- /dev/null +++ b/terraform/azure_billing/.terraform.lock.hcl @@ -0,0 +1,41 @@ +# This file is maintained automatically by "terraform init". +# Manual edits may be lost in future updates. + +provider "registry.terraform.io/azure/azapi" { + version = "2.8.0" + hashes = [ + "h1:gJpLLWwcTgHPyyqDNaXZkCfFCAywGMAgVlqg7QHRRBk=", + "zh:048fa67ba123c6da65a7af12453328e36e1783cac1dbecc905d44ee7a1daa41c", + "zh:08dfb8c493a99aa54ea0c00f5d2e2389aac55d70b31bfc50a38e4ab61800aca8", + "zh:0d5bf53f356864567bf0855eb90b0b9aa4619b60fd1469210461ad88c0508a6f", + "zh:221cc52181d81bd741e8624ba9619ae20438f7a13828b72aa138a51b57bc1483", + "zh:51e7485e4f502cbbefe9b4ea991961eb9b19f41862593150905197bbb37cc6fb", + "zh:6e2d0986176bbeabdfa7dc3d1bf37d0a24549ebff29a3c9e8c5082e03cc38247", + "zh:87e46ceddcd3a4b7ed16f6b853c286840753d8af8ae8df0618ab5f29e950976b", + "zh:894998419943fadb3b85d1469665e9b7cdf492e6dc30907a77e32043e1d52b6a", + "zh:9f1efae3ad37510d947e7a27118a84bae55e35681b047d939781da96dd6ab6c7", + "zh:a201371f6c4c65b6976a8a360223c188ea91b7a33078fdd3a5f5f0ac7b438d35", + "zh:af3cc16bdfc545e61ce66449b9daaebfaa0c5e495777241c9414671a31e37ffa", + "zh:dbbb263a5f4c40624823fd3e68dc046b1f00325548393557384f0914a4694278", + ] +} + +provider "registry.terraform.io/hashicorp/azurerm" { + version = "4.58.0" + constraints = "~> 4.0" + hashes = [ + "h1:k0a/JkkhIEGrJ/oR7MZWbTZsUXHQ18JIPcVWBdW+V58=", + "zh:041c2a778ab4dd5a9af174b1d6f75409e5aabfc359cb386dfea3fb09e3f32709", + "zh:0a302531a61e7383acf99a6202d7984b2ea559306f45021381665c827a830d46", + "zh:0c69f132c7609683d907e87b89210a298d84c5b0121b62278949931bc54ca952", + "zh:0cadf48e9d2d9daed43212a3c9d886d7faaf68787b6e955456cbe4f43e4a17ec", + "zh:35ef4293d7731f6ff1f8bcba2c4529f987b7fac243c1ac1c154bbc02c9703c25", + "zh:3cb2679e1d56865e0ee0cf4c5d1404dbad0db42d11425e7bf0580a026cc64287", + "zh:4e56411f5119042d4962acff5c6d64224a49a69154ba80e6df63fa57b1e6d284", + "zh:78d5eefdd9e494defcb3c68d282b8f96630502cac21d1ea161f53cfe9bb483b3", + "zh:ca4626411a111720c220f9849c7d2e1fcd5d380f56459e096d835a9dbf9e6e13", + "zh:d31c4e65dcb096974479b2d548fffb86fc9a5262aff1b01fe62ef442ce536c6b", + "zh:d9631602999c1853e53ee2c5aef7476e23c7787beddc3599c10dbaa4891ba166", + "zh:f31ba7c9341037ceb7d49467946c01b2b0930404ed1d5643c1451f734a613a03", + ] +} diff --git a/terraform/azure_billing/azure-provider.tf b/terraform/azure_billing/azure-provider.tf new file mode 100644 index 00000000..08f33381 --- /dev/null +++ b/terraform/azure_billing/azure-provider.tf @@ -0,0 +1,14 @@ +# Provider configuration for billing-scoped resources +# Billing APIs are tenant-scoped; subscription_id is only needed for authentication +provider "azurerm" { + features {} + + # Using FXCI subscription for authentication + subscription_id = "108d46d5-fe9b-4850-9a7d-8c914aa6c1f0" + tenant_id = "c0dc8bb0-b616-427e-8217-9513964a145b" +} + +provider "azapi" { + subscription_id = "108d46d5-fe9b-4850-9a7d-8c914aa6c1f0" + tenant_id = "c0dc8bb0-b616-427e-8217-9513964a145b" +} diff --git a/terraform/azure_billing/backend.tf b/terraform/azure_billing/backend.tf new file mode 100644 index 00000000..ab88f16c --- /dev/null +++ b/terraform/azure_billing/backend.tf @@ -0,0 +1,8 @@ +terraform { + backend "s3" { + bucket = "relops-tf-states" + key = "azure_billing.tfstate" + use_lockfile = true + region = "us-west-2" + } +} diff --git a/terraform/azure_billing/finops.tf b/terraform/azure_billing/finops.tf new file mode 100644 index 00000000..a5e533b3 --- /dev/null +++ b/terraform/azure_billing/finops.tf @@ -0,0 +1,123 @@ +# Cost exports for billing-scoped resources (invoice sections, billing profiles) +# These are not tied to a specific subscription + +locals { + # Billing hierarchy + billing_account_id = "05ef9068-c74c-54a9-5b8f-82f7fb8b32cd:6e104178-9e3c-470c-9787-8ef53f372665_2019-05-31" + mozilla_billing_profile_id = "GRUW-TLBL-BG7-PGB" + + # Invoice sections under mozilla billing profile + anonym_invoice_section_id = "RUDC-GV4R-PJA-PGB" +} + +# Storage account for cost exports (managed in azure_fxci) +data "azurerm_storage_account" "finops" { + name = "safinopsdata" + resource_group_name = "rg-azure-cost-mgmt" +} + +import { + to = azapi_resource.anonym_cost_export_actual + id = "/providers/Microsoft.Billing/billingAccounts/${local.billing_account_id}/billingProfiles/${local.mozilla_billing_profile_id}/invoiceSections/${local.anonym_invoice_section_id}/providers/Microsoft.CostManagement/exports/anonym_daily-actual-cost" +} + +import { + to = azapi_resource.anonym_cost_export_amortized + id = "/providers/Microsoft.Billing/billingAccounts/${local.billing_account_id}/billingProfiles/${local.mozilla_billing_profile_id}/invoiceSections/${local.anonym_invoice_section_id}/providers/Microsoft.CostManagement/exports/anonym-amortized-cost" +} + +# Anonym invoice section - Actual Cost export +resource "azapi_resource" "anonym_cost_export_actual" { + type = "Microsoft.CostManagement/exports@2025-03-01" + name = "anonym_daily-actual-cost" + parent_id = "/providers/Microsoft.Billing/billingAccounts/${local.billing_account_id}/billingProfiles/${local.mozilla_billing_profile_id}/invoiceSections/${local.anonym_invoice_section_id}" + + identity { + type = "SystemAssigned" + } + + body = { + properties = { + schedule = { + status = "Active" + recurrence = "Daily" + recurrencePeriod = { + from = "2024-10-01T00:00:00Z" + to = "2050-02-01T00:00:00Z" + } + } + format = "Csv" + compressionMode = "None" + dataOverwriteBehavior = "CreateNewReport" + deliveryInfo = { + destination = { + type = "AzureBlob" + resourceId = data.azurerm_storage_account.finops.id + container = "cost-management" + rootFolderPath = "anon_daily" + } + } + partitionData = true + definition = { + type = "ActualCost" + timeframe = "MonthToDate" + dataSet = { + granularity = "Daily" + configuration = { + columns = [] + dataVersion = "2021-10-01" + filters = [] + } + } + } + } + } +} + +# Anonym invoice section - Amortized Cost export +resource "azapi_resource" "anonym_cost_export_amortized" { + type = "Microsoft.CostManagement/exports@2025-03-01" + name = "anonym-amortized-cost" + parent_id = "/providers/Microsoft.Billing/billingAccounts/${local.billing_account_id}/billingProfiles/${local.mozilla_billing_profile_id}/invoiceSections/${local.anonym_invoice_section_id}" + + identity { + type = "SystemAssigned" + } + + body = { + properties = { + schedule = { + status = "Active" + recurrence = "Daily" + recurrencePeriod = { + from = "2024-10-01T00:00:00Z" + to = "2050-02-01T00:00:00Z" + } + } + format = "Csv" + compressionMode = "None" + dataOverwriteBehavior = "CreateNewReport" + deliveryInfo = { + destination = { + type = "AzureBlob" + resourceId = data.azurerm_storage_account.finops.id + container = "cost-management" + rootFolderPath = "anon_daily_amortized" + } + } + partitionData = true + definition = { + type = "AmortizedCost" + timeframe = "MonthToDate" + dataSet = { + granularity = "Daily" + configuration = { + columns = [] + dataVersion = "2021-10-01" + filters = [] + } + } + } + } + } +} diff --git a/terraform/azure_billing/versions.tf b/terraform/azure_billing/versions.tf new file mode 100644 index 00000000..75a5075c --- /dev/null +++ b/terraform/azure_billing/versions.tf @@ -0,0 +1,12 @@ +terraform { + required_version = ">= 0.15" + required_providers { + azurerm = { + source = "hashicorp/azurerm" + version = "~> 4" + } + azapi = { + source = "azure/azapi" + } + } +}