The standalone configuration to emit when the user has no existing Terraform project. When they do,
take only the resources below the provider blocks and add them to what they already have.
Placeholders to replace before writing the file:
Placeholder
Source
<USER_SUBSCRIPTION_IDS>
Phase 1 - a complete HCL list, e.g. ["sub-a", "sub-b"]. Never a bare comma-separated fragment: the placeholder replaces the whole expression, brackets included
<USER_MANAGEMENT_GROUP_NAMES>
Phase 1 - a complete HCL list, e.g. ["mg-root"], or [] when none
<TENANT_ID>
Phase 1 - the Entra tenant ID. Both providers are pinned to it so a guest/multi-tenant login cannot create the app in a different tenant than the one you checked for duplicates
<DD_SITE>
Phase 0 (DD_SITE)
hcl
# No root variables hold the Datadog keys. The provider reads them from DD_API_KEY and DD_APP_KEY in the# environment, so there is nothing for Terraform to record: no variable value in state, none in a saved# plan, and no `-var=` on any command line. This also means an existing project needs no variable changes.locals { tenant_id = "<TENANT_ID>" azure_subscription_ids = <USER_SUBSCRIPTION_IDS> management_group_names = <USER_MANAGEMENT_GROUP_NAMES> # The full set Datadog requires; do not trim it. Source of truth: # https://docs.datadoghq.com/integrations/guide/azure-graph-api-permissions/ graph_api_permissions = [ "AdministrativeUnit.Read.All", "Application.Read.All", "AuditLog.Read.All",
Subscriptions only (no management groups). Set management_group_names = [] and delete the
azurerm_role_assignment.monitoring_reader_management_group resource and its depends_on entry.
Management groups only. Keep azure_subscription_ids populated with at least one subscription
from inside one of those groups - the azurerm provider requires a subscription ID even when every
role assignment is at group scope. Datadog discovers the rest of the group’s subscriptions itself.
Cloud Security posture. Set cspm_enabled = true to add security posture scanning. It needs the
Security Reader role in addition to Monitoring Reader; add a second azurerm_role_assignment
per scope if the user wants it.
Host filters.host_filters takes a comma-separated tag list (e.g. "env:prod,team:core") to
restrict which VMs are monitored. Leave "" to monitor everything.
Secretless auth (Preview) - the direction to prefer, but not shippable from this template yet.
This is Azure’s equivalent of the keyless models AWS and GCP use (role assumption and service-account
impersonation): with it, no secret is minted at all, so nothing secret reaches state.
As written today it cannot be used here.
datadog_integration_azure accepts secretless_auth_enabled = true, where Datadog authenticates with
federated workload identity instead of a client secret, and nothing secret reaches state. The catch: the
federated credential must exist on the app registration being registered, and this template creates a
brand-new azuread_application that has none - so flipping the flag alone yields an integration that
cannot authenticate. Making it work means either provisioning
azuread_application_federated_identity_credential with Datadog’s issuer and subject values (this skill
does not carry them), or replacing the new application and service-principal resources with references to
an existing app that already holds the credential. Both are beyond this template: tell the user secretless
exists and is the better end state, point at
the provider docs (opens in a new tab),
and do not half-apply it. The specific gap is the federated credential’s issuer, subject, and audience:
those are not published in the provider docs, the Azure integration docs, or the Azure portal setup guide
as of this writing, so they have to come from Datadog. If the user already has secretless enabled on an
existing app registration, prefer that app over creating a new one - that is the one case where this path
works today.