<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom"><channel><title>Grafana Terraform provider on Grafana Labs</title><link>https://grafana.com/docs/grafana/v12.4/as-code/infrastructure-as-code/terraform/</link><description>Recent content in Grafana Terraform provider on Grafana Labs</description><generator>Hugo -- gohugo.io</generator><language>en</language><atom:link href="/docs/grafana/v12.4/as-code/infrastructure-as-code/terraform/index.xml" rel="self" type="application/rss+xml"/><item><title>Create and manage a Grafana Cloud stack using Terraform</title><link>https://grafana.com/docs/grafana/v12.4/as-code/infrastructure-as-code/terraform/terraform-cloud-stack/</link><pubDate>Fri, 03 Apr 2026 12:35:46 -0500</pubDate><guid>https://grafana.com/docs/grafana/v12.4/as-code/infrastructure-as-code/terraform/terraform-cloud-stack/</guid><content><![CDATA[&lt;h1 id=&#34;create-and-manage-a-grafana-cloud-stack-using-terraform&#34;&gt;Create and manage a Grafana Cloud stack using Terraform&lt;/h1&gt;
&lt;p&gt;Learn how to add a data source, a dashboard, and a folder to a Grafana Cloud stack using Terraform.&lt;/p&gt;
&lt;h2 id=&#34;prerequisites&#34;&gt;Prerequisites&lt;/h2&gt;
&lt;p&gt;Before you begin, ensure you have the following:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;A Grafana Cloud account, as shown in &lt;a href=&#34;/docs/grafana-cloud/get-started/&#34;&gt;Get started&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://www.terraform.io/downloads&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;Terraform&lt;/a&gt; installed on your machine&lt;/li&gt;
&lt;/ul&gt;


&lt;div class=&#34;admonition admonition-note&#34;&gt;&lt;blockquote&gt;&lt;p class=&#34;title text-uppercase&#34;&gt;Note&lt;/p&gt;&lt;p&gt;All of the following Terraform configuration files should be saved in the same directory.&lt;/p&gt;&lt;/blockquote&gt;&lt;/div&gt;

&lt;h2 id=&#34;create-a-cloud-stack&#34;&gt;Create a Cloud stack&lt;/h2&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;Create a Terraform configuration file.&lt;/p&gt;
&lt;p&gt;This Terraform configuration will create a Grafana Cloud stack and a second token needed for your Grafana instance.&lt;/p&gt;
&lt;p&gt;Create a file named &lt;code&gt;cloud-stack.tf&lt;/code&gt; and add the following:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;terraform&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-terraform&#34;&gt;terraform {
  required_providers {
    grafana = {
      source  = &amp;#34;grafana/grafana&amp;#34;
      version = &amp;#34;&amp;gt;= 2.9.0&amp;#34;
    }
  }
}
// Step 1: Create a stack
provider &amp;#34;grafana&amp;#34; {
  alias = &amp;#34;cloud&amp;#34;
  cloud_access_policy_token = &amp;#34;&amp;lt;cloud-access-token&amp;gt;&amp;#34;
}


resource &amp;#34;grafana_cloud_stack&amp;#34; &amp;#34;my_stack&amp;#34; {
  provider = grafana.cloud

  name               = &amp;#34;&amp;lt;stack-name&amp;gt;&amp;#34;
  slug               = &amp;#34;&amp;lt;stack-name&amp;gt;&amp;#34;
  region_slug        = &amp;#34;&amp;lt;region&amp;gt;&amp;#34; # Example &amp;#34;us&amp;#34;,&amp;#34;eu&amp;#34; etc
  delete_protection  = true
}

// Step 2: Create a service account and key for the stack
resource &amp;#34;grafana_cloud_stack_service_account&amp;#34; &amp;#34;cloud_sa&amp;#34; {
  provider   = grafana.cloud
  stack_slug = grafana_cloud_stack.my_stack.slug

  name        = &amp;#34;&amp;lt;service-account-name&amp;gt;&amp;#34;
  role        = &amp;#34;Admin&amp;#34;
  is_disabled = false
}

resource &amp;#34;grafana_cloud_stack_service_account_token&amp;#34; &amp;#34;cloud_sa&amp;#34; {
  provider   = grafana.cloud
  stack_slug = grafana_cloud_stack.my_stack.slug

  name               = &amp;#34;terraform serviceaccount key&amp;#34;
  service_account_id = grafana_cloud_stack_service_account.cloud_sa.id
}

// Step 3: Create resources within the stack
provider &amp;#34;grafana&amp;#34; {
  alias = &amp;#34;my_stack&amp;#34;

  url  = grafana_cloud_stack.my_stack.url
  auth = grafana_cloud_stack_service_account_token.cloud_sa.key
}
resource &amp;#34;grafana_folder&amp;#34; &amp;#34;my_folder&amp;#34; {
  provider = grafana.my_stack

  title = &amp;#34;Test Folder&amp;#34;
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Replace the following field values:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;&amp;lt;cloud-access-token&amp;gt;&lt;/code&gt; with your Grafana Cloud Access Policy Token.
To create a new one, refer to &lt;a href=&#34;/docs/grafana-cloud/account-management/authentication-and-permissions/access-policies/&#34;&gt;Grafana Cloud Access Policies&lt;/a&gt;.
Add all stacks to the realms list.
The scopes needed for the example are:
&lt;ul&gt;
&lt;li&gt;dashboards:read&lt;/li&gt;
&lt;li&gt;orgs:read&lt;/li&gt;
&lt;li&gt;stack-dashboards:read&lt;/li&gt;
&lt;li&gt;stacks:read&lt;/li&gt;
&lt;li&gt;dashboards:write&lt;/li&gt;
&lt;li&gt;orgs:write&lt;/li&gt;
&lt;li&gt;stack-dashboards:write&lt;/li&gt;
&lt;li&gt;stacks:write&lt;/li&gt;
&lt;li&gt;stack-service-accounts:write&lt;/li&gt;
&lt;li&gt;dashboards:delete&lt;/li&gt;
&lt;li&gt;stack-dashboards:delete&lt;/li&gt;
&lt;li&gt;stacks:delete&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;&lt;code&gt;&amp;lt;stack-name&amp;gt;&lt;/code&gt; with the name of your stack.&lt;/li&gt;
&lt;li&gt;&lt;code&gt;&amp;lt;region&amp;gt;&lt;/code&gt; with the region in which you want to create the stack. For example &lt;code&gt;us&lt;/code&gt;, &lt;code&gt;eu&lt;/code&gt;.&lt;/li&gt;
&lt;li&gt;&lt;code&gt;&amp;lt;service-account-name&amp;gt;&lt;/code&gt; with a name for the serviceaccount that will be created to use for operations within the stack/instance.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;The first provider block, &lt;code&gt;grafana.cloud&lt;/code&gt;, uses the Cloud Access Policy Token from the Cloud Portal and is referenced as a parameter when creating the Cloud stack and the token in the Grafana instance to provide the necessary authentication.&lt;/p&gt;
&lt;p&gt;The second provider block, &lt;code&gt;grafana.my_stack&lt;/code&gt;, is referenced as a parameter when creating resources inside the Grafana instance.&lt;/p&gt;
&lt;h2 id=&#34;add-a-data-source&#34;&gt;Add a data source&lt;/h2&gt;
&lt;p&gt;This guide uses the InfluxDB data source. The required arguments for &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs/resources/data_source&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;grafana_data_source (Resource)&lt;/a&gt; vary depending on the type of data source you select.&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;Create a file named &lt;code&gt;datasource.tf&lt;/code&gt; and add the following:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;terraform&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-terraform&#34;&gt;resource &amp;#34;grafana_data_source&amp;#34; &amp;#34;&amp;lt;data-source-name&amp;gt;&amp;#34; {
  provider = grafana.my_stack

  type          = &amp;#34;influxdb&amp;#34;
  name          = &amp;#34;&amp;lt;data-source-name&amp;gt;&amp;#34;
  url           = &amp;#34;&amp;lt;data-source-url&amp;gt;&amp;#34;
  username      = &amp;#34;&amp;lt;username&amp;gt;&amp;#34;
  password      = &amp;#34;&amp;lt;password&amp;gt;&amp;#34;
  database_name = &amp;#34;&amp;lt;db-name&amp;gt;&amp;#34;
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Replace the following field values:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;&amp;lt;data-source-name&amp;gt;&lt;/code&gt; with the name of the data source to be added in Grafana.&lt;/li&gt;
&lt;li&gt;&lt;code&gt;&amp;lt;data-source-url&amp;gt;&lt;/code&gt; with URL of your data source.&lt;/li&gt;
&lt;li&gt;&lt;code&gt;&amp;lt;username&amp;gt;&lt;/code&gt; with the username for authenticating with your data source.&lt;/li&gt;
&lt;li&gt;&lt;code&gt;&amp;lt;password&amp;gt;&lt;/code&gt; with password for authenticating with your data source.&lt;/li&gt;
&lt;li&gt;&lt;code&gt;&amp;lt;db-name&amp;gt;&lt;/code&gt; with name of your database.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;h2 id=&#34;add-a-folder&#34;&gt;Add a folder&lt;/h2&gt;
&lt;p&gt;This Terraform configuration creates a folder in your Grafana instance using &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs/resources/folder&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;grafana_folder (Resource)&lt;/a&gt;.&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;Create a file named &lt;code&gt;folder.tf&lt;/code&gt; and add the following:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;terraform&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-terraform&#34;&gt;resource &amp;#34;grafana_folder&amp;#34; &amp;#34;&amp;lt;folder-name&amp;gt;&amp;#34; {
  provider = grafana.my_stack

  title = &amp;#34;&amp;lt;folder-name&amp;gt;&amp;#34;
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Replace the following field value:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;&amp;lt;folder-name&amp;gt;&lt;/code&gt; with a name for the folder.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;h2 id=&#34;add-a-dashboard-to-the-folder&#34;&gt;Add a dashboard to the folder&lt;/h2&gt;
&lt;p&gt;This Terraform configuration creates a dashboard inside the folder created above in your Grafana instance using &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs/resources/dashboard&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;grafana_dashboard (Resource)&lt;/a&gt;.&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;Create a file named &lt;code&gt;dashboard.tf&lt;/code&gt; and add the following:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;terraform&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-terraform&#34;&gt;# Using a JSON file
resource &amp;#34;grafana_dashboard&amp;#34; &amp;#34;dashboard&amp;#34; {
  provider = grafana.my_stack

  config_json = file(&amp;#34;&amp;lt;file-name&amp;gt;.json&amp;#34;)
  folder = grafana_folder.&amp;lt;folder-name&amp;gt;.id
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Replace the following field value:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;&amp;lt;file-name&amp;gt;&lt;/code&gt; with the name of the JSON file that has the source code for the dashboard.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;The dashboard is represented by its JSON source code and referenced in the &lt;code&gt;config_json&lt;/code&gt; parameter.&lt;/p&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;h2 id=&#34;apply-the-terraform-configuration&#34;&gt;Apply the Terraform configuration&lt;/h2&gt;
&lt;p&gt;In a terminal, run the following commands from the directory where all of the configuration files are located.&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;Initialize a working directory containing Terraform configuration files.&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;shell&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-shell&#34;&gt;terraform init&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Preview the changes that Terraform will make.&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;shell&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-shell&#34;&gt;terraform plan&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Apply the configuration files.&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;shell&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-shell&#34;&gt;terraform apply&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;h2 id=&#34;validation&#34;&gt;Validation&lt;/h2&gt;
&lt;p&gt;Once you apply the changes in the Terraform configurations, you should be able to verify the following:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;The new Grafana stack is created and visible in the Cloud Portal&lt;/p&gt;
&lt;p&gt;&lt;img
  class=&#34;lazyload d-inline-block&#34;
  data-src=&#34;/static/img/docs/grafana-cloud/terraform/cloud_portal_tf.png&#34;
  alt=&#34;Cloud Portal&#34; width=&#34;1376&#34;
     height=&#34;816&#34;/&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;A service account key token is added in your Grafana instance. In the following image, the service account key token named &amp;ldquo;terraform serviceaccount key&amp;rdquo; was added by the &lt;a href=&#34;#create-a-cloud-stack&#34;&gt;grafana_cloud_stack_service_account_token (Resource)&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;&lt;img
  class=&#34;lazyload d-inline-block&#34;
  data-src=&#34;/media/docs/grafana-cloud/screenshot-api_key_tf.png&#34;
  alt=&#34;API Key&#34; width=&#34;2444&#34;
     height=&#34;916&#34;/&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;A new data source (InfluxDB in this example) is visible in the grafana instance.&lt;/p&gt;
&lt;p&gt;&lt;img
  class=&#34;lazyload d-inline-block&#34;
  data-src=&#34;/media/docs/grafana-cloud/screenshot-influxdb_datasource_tf.png&#34;
  alt=&#34;InfluxDB data source&#34; width=&#34;1440&#34;
     height=&#34;764&#34;/&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;A new folder in Grafana. In the following image, a folder named &amp;ldquo;Demos&amp;rdquo; was added by the &lt;a href=&#34;./#add-a-folder&#34;&gt;grafana_folder (Resource)&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;&lt;img
  class=&#34;lazyload d-inline-block&#34;
  data-src=&#34;/media/docs/grafana-cloud/screenshot-folder_tf.png&#34;
  alt=&#34;Folder&#34; width=&#34;2436&#34;
     height=&#34;694&#34;/&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;A new dashboard in the Grafana instance. In the following image a dashboard named &amp;ldquo;InfluxDB Cloud Demos&amp;rdquo; was created inside the &amp;ldquo;Demos&amp;rdquo; folder.&lt;/p&gt;
&lt;p&gt;&lt;img
  class=&#34;lazyload d-inline-block&#34;
  data-src=&#34;/static/img/docs/grafana-cloud/terraform/influxdb_dashboard_tf.png&#34;
  alt=&#34;InfluxDB dashboard&#34; width=&#34;1855&#34;
     height=&#34;895&#34;/&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id=&#34;summary&#34;&gt;Summary&lt;/h2&gt;
&lt;p&gt;In this guide, you created a Grafana Cloud stack along with a data source, folder, and dashboard imported from a JSON file using Terraform.&lt;/p&gt;
&lt;p&gt;To learn more about managing Grafana Cloud using Terraform, refer to the &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;Grafana provider documentation&lt;/a&gt;.&lt;/p&gt;
]]></content><description>&lt;h1 id="create-and-manage-a-grafana-cloud-stack-using-terraform">Create and manage a Grafana Cloud stack using Terraform&lt;/h1>
&lt;p>Learn how to add a data source, a dashboard, and a folder to a Grafana Cloud stack using Terraform.&lt;/p></description></item><item><title>Create and manage dashboards using Terraform and GitHub Actions</title><link>https://grafana.com/docs/grafana/v12.4/as-code/infrastructure-as-code/terraform/dashboards-github-action/</link><pubDate>Fri, 03 Apr 2026 12:35:46 -0500</pubDate><guid>https://grafana.com/docs/grafana/v12.4/as-code/infrastructure-as-code/terraform/dashboards-github-action/</guid><content><![CDATA[&lt;h1 id=&#34;create-and-manage-dashboards-using-terraform-and-github-actions&#34;&gt;Create and manage dashboards using Terraform and GitHub Actions&lt;/h1&gt;
&lt;p&gt;Learn how to create and manage multiple dashboards represented as JSON source code for Grafana using Terraform and GitHub Actions.&lt;/p&gt;
&lt;h2 id=&#34;prerequisites&#34;&gt;Prerequisites&lt;/h2&gt;
&lt;p&gt;Before you begin, ensure you have the following:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;A Grafana Cloud account, as shown in &lt;a href=&#34;/docs/grafana-cloud/get-started/&#34;&gt;Get started&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;A &lt;a href=&#34;https://github.com/&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;GitHub&lt;/a&gt; repository&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id=&#34;add-dashboards-to-a-github-repository&#34;&gt;Add Dashboards to a GitHub repository&lt;/h2&gt;
&lt;p&gt;This guide shows you how to add dashboards for ElasticSearch, InfluxDB, and AWS EC2. You can use different dashboards according to your configured data sources.&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;In your GitHub repository, create a folder named &lt;code&gt;dashboards&lt;/code&gt; in the root directory.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;In the &lt;code&gt;dashboards&lt;/code&gt; folder create three sub-folders. For this guide, we will create three sub-folders named &lt;code&gt;elasticsearch&lt;/code&gt;, &lt;code&gt;influxdb&lt;/code&gt;, and &lt;code&gt;aws&lt;/code&gt;.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Add dashboard JSON source code to each of the three sub-folders.&lt;/p&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;h2 id=&#34;terraform-configuration-for-grafana-provider&#34;&gt;Terraform configuration for Grafana provider&lt;/h2&gt;
&lt;p&gt;This Terraform configuration configures the &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;Grafana provider&lt;/a&gt; to provide necessary authentication when creating folders and dashboards in the Grafana instance.&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;Create a service account and token in the Grafana instance by following these steps:&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;&lt;a href=&#34;/docs/grafana-cloud/account-management/authentication-and-permissions/service-accounts/#create-a-service-account-in-grafana&#34;&gt;Create a service account in Grafana&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;/docs/grafana-cloud/account-management/authentication-and-permissions/service-accounts/#add-a-token-to-a-service-account-in-grafana&#34;&gt;Add a token to a service account&lt;/a&gt;&lt;/li&gt;
&lt;/ol&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Create a file named &lt;code&gt;main.tf&lt;/code&gt; in the Git root directory and add the following code block:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;terraform&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-terraform&#34;&gt;terraform {
   required_providers {
      grafana = {
         source  = &amp;#34;grafana/grafana&amp;#34;
         version = &amp;#34;&amp;gt;= 2.9.0&amp;#34;
      }
   }
}

provider &amp;#34;grafana&amp;#34; {
   alias = &amp;#34;cloud&amp;#34;

   url   = &amp;#34;&amp;lt;Grafana-instance-url&amp;gt;&amp;#34;
   auth  = &amp;#34;&amp;lt;Grafana-Service-Account-token&amp;gt;&amp;#34;
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Replace the following field values:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;&amp;lt;Grafana-instance-url&amp;gt;&lt;/code&gt; with the URL of your Grafana instance, for example &lt;code&gt;&amp;quot;https://my-stack.grafana.net/&amp;quot;&lt;/code&gt;.&lt;/li&gt;
&lt;li&gt;&lt;code&gt;&amp;lt;Grafana-Service-Account-token&amp;gt;&lt;/code&gt; with a Service Account token from the Grafana instance.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;h2 id=&#34;terraform-configuration-for-folders&#34;&gt;Terraform configuration for folders&lt;/h2&gt;
&lt;p&gt;This Terraform configuration creates three folders named &lt;code&gt;ElasticSearch&lt;/code&gt;, &lt;code&gt;InfluxDB&lt;/code&gt; and &lt;code&gt;AWS&lt;/code&gt; in the Grafana instance using &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs/resources/folder&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;grafana_folder (Resource)&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;Create a file named &lt;code&gt;folders.tf&lt;/code&gt; in the Git root directory and add the following code block:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;terraform&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-terraform&#34;&gt;resource &amp;#34;grafana_folder&amp;#34; &amp;#34;ElasticSearch&amp;#34; {
  provider = grafana.cloud

  title = &amp;#34;ElasticSearch&amp;#34;
}

resource &amp;#34;grafana_folder&amp;#34; &amp;#34;InfluxDB&amp;#34; {
  provider = grafana.cloud

  title = &amp;#34;InfluxDB&amp;#34;
}

resource &amp;#34;grafana_folder&amp;#34; &amp;#34;AWS&amp;#34; {
  provider = grafana.cloud

  title = &amp;#34;AWS&amp;#34;
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;h2 id=&#34;terraform-configuration-for-dashboards&#34;&gt;Terraform configuration for dashboards&lt;/h2&gt;
&lt;p&gt;This Terraform configuration iterates through the Json files in the three folders (&lt;code&gt;elasticsearch&lt;/code&gt;, &lt;code&gt;influxdb&lt;/code&gt; and &lt;code&gt;aws&lt;/code&gt;) you created in the GitHub repository and adds them to the respective folders in the Grafana instance using &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs/resources/dashboard&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;grafana_dashboard (Resource)&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;For example, the dashboard represented as JSON source code in the &lt;code&gt;elasticsearch&lt;/code&gt; folder in the GitHub repository will be created in the &lt;code&gt;ElasticSearch&lt;/code&gt; folder in the Grafana instance.&lt;/p&gt;
&lt;p&gt;Create a file named &lt;code&gt;dashboards.tf&lt;/code&gt; in the Git root directory and add the following code block:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;terraform&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-terraform&#34;&gt;resource &amp;#34;grafana_dashboard&amp;#34; &amp;#34;elasticsearch&amp;#34; {
  provider = grafana.cloud

  for_each    = fileset(&amp;#34;${path.module}/dashboards/elasticsearch&amp;#34;, &amp;#34;*.json&amp;#34;)
  config_json = file(&amp;#34;${path.module}/dashboards/elasticsearch/${each.key}&amp;#34;)
  folder      = grafana_folder.ElasticSearch.id
}

resource &amp;#34;grafana_dashboard&amp;#34; &amp;#34;influxdb&amp;#34; {
  provider = grafana.cloud

  for_each    = fileset(&amp;#34;${path.module}/dashboards/influxdb&amp;#34;, &amp;#34;*.json&amp;#34;)
  config_json = file(&amp;#34;${path.module}/dashboards/influxdb/${each.key}&amp;#34;)
  folder      = grafana_folder.InfluxDB.id
}

resource &amp;#34;grafana_dashboard&amp;#34; &amp;#34;aws&amp;#34; {
  provider = grafana.cloud

  for_each    = fileset(&amp;#34;${path.module}/dashboards/aws&amp;#34;, &amp;#34;*.json&amp;#34;)
  config_json = file(&amp;#34;${path.module}/dashboards/aws/${each.key}&amp;#34;)
  folder      = grafana_folder.AWS.id
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;h2 id=&#34;github-workflow-for-managing-dashboards-using-terraform&#34;&gt;GitHub workflow for managing dashboards using Terraform&lt;/h2&gt;
&lt;p&gt;This GitHub workflow consists of the following steps:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Using the &lt;a href=&#34;https://github.com/actions/checkout&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;actions/checkout@v3&lt;/a&gt; action, The GitHub repository is checked out so that the GitHub workflow can access it.&lt;/li&gt;
&lt;li&gt;The Terraform CLI is installed on the GitHub runner using the &lt;a href=&#34;https://github.com/hashicorp/setup-terraform&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;hashicorp/setup-terraform@v1&lt;/a&gt; action.&lt;/li&gt;
&lt;li&gt;&lt;code&gt;terraform init&lt;/code&gt; is run as a bash command in the GitHub runner to initialize a working directory containing Terraform configuration files.&lt;/li&gt;
&lt;li&gt;&lt;code&gt;terraform fmt -check&lt;/code&gt; is run as a bash command in the GitHub runner to check if the Terraform configuration files are properly formatted. If the Terraform configuration files are not properly formatted, the workflow will fail at this step.&lt;/li&gt;
&lt;li&gt;&lt;code&gt;terraform plan&lt;/code&gt; is run as a bash command in the GitHub runner to preview the changes that Terraform will make.&lt;/li&gt;
&lt;li&gt;Using &lt;a href=&#34;https://github.com/mshick/add-pr-comment&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;mshick/add-pr-comment@v1&lt;/a&gt; action, the preview from Terraform plan is posted as a comment on the pull request. This helps in reviewing the changes that Terraform will make before the pull request is merged.&lt;/li&gt;
&lt;li&gt;&lt;code&gt;terraform appy -auto-approve&lt;/code&gt; is run as a bash command in the GitHub runner to apply the Terraform configuration files. &lt;code&gt;-auto-approve&lt;/code&gt; flag is added to the command to skip interactive approval of plan before applying and make the workflow automated.
This step is run only when changes are committed to &lt;code&gt;main&lt;/code&gt; branch. When a pull request is merged, the merge action creates a commit to the &lt;code&gt;main&lt;/code&gt; branch which triggers the &lt;code&gt;terraform apply -auto-approve&lt;/code&gt; step to execute.&lt;/li&gt;
&lt;/ul&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;In your GitHub repository, create a folder named &lt;code&gt;.github&lt;/code&gt; in the root directory .&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;In the &lt;code&gt;.github&lt;/code&gt; folder create a sub-folder named &lt;code&gt;workflows&lt;/code&gt;.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;To add the GitHub workflow to your GitHub repository, create a file named &lt;code&gt;terraform.yml&lt;/code&gt; in the &lt;code&gt;workflows&lt;/code&gt; directory and add the following code block:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;YAML&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-yaml&#34;&gt;name: Terraform

on:
  push:
    branches:
      - &amp;#39;main&amp;#39;
  pull_request:

jobs:
  terraform:
    runs-on: ubuntu-latest

    steps:
      # Checkout the repository to the GitHub Actions runner
      - name: Checkout
        uses: actions/checkout@v3

      # Install the latest version of Terraform CLI
      - name: Setup Terraform
        uses: hashicorp/setup-terraform@v1

      # Initialize a new or existing Terraform working directory by creating initial files, loading any remote state, downloading modules, etc.
      - name: Terraform Init
        run: terraform init

      # Checks that all Terraform configuration files adhere to a canonical format
      - name: Terraform Format
        run: terraform fmt -check

      # Previews the changes that Terraform will make
      - name: Plan Terraform
        id: plan
        continue-on-error: true
        run: terraform plan -input=false -no-color

      # Post the preview (terraform plan) from the previous step as a GitHub pull request comment
      - name: Post Plan to GitHub PR
        if: github.ref != &amp;#39;refs/heads/main&amp;#39;
        uses: mshick/add-pr-comment@v1
        with:
          repo-token: ${{ secrets.GITHUB_TOKEN }}
          repo-token-user-login: &amp;#39;github-actions[bot]&amp;#39;
          message: |
            Applying:

            ```
            ${{ steps.plan.outputs.stdout }}
            ```

      # Applies the terraform configuration files when the branch is `main`
      - name: Apply Terraform
        if: github.ref == &amp;#39;refs/heads/main&amp;#39;
        id: apply
        continue-on-error: true
        run: |
          terraform apply -auto-approve&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Commit the changes made to the &lt;code&gt;terraform.yml&lt;/code&gt; in the previous step to the &lt;code&gt;main&lt;/code&gt; branch in your GitHub repository. Once the changes are committed, The GitHub workflow you created should start to run automatically as the workflow we defined in the previous step runs when a pull request is created or when changes are committed to &lt;code&gt;main&lt;/code&gt; branch.&lt;/p&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;h2 id=&#34;managing-the-terraform-state&#34;&gt;Managing the Terraform state&lt;/h2&gt;
&lt;p&gt;If you are not using a &lt;a href=&#34;https://www.terraform.io/language/settings/backends/configuration&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;Terraform backend&lt;/a&gt; to store the &lt;code&gt;.tfstate&lt;/code&gt; file, add the following code block to the end of the GitHub workflow file to make sure the Terraform state file is stored in Git.&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;YAML&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-yaml&#34;&gt;- name: commit the terraform state
  if: github.ref == &amp;#39;refs/heads/main&amp;#39;
  uses: stefanzweifel/git-auto-commit-action@v4
  with:
    commit_message: Updating Terraform state
    file_pattern: terraform.tfstate&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;When you run &lt;code&gt;terraform apply&lt;/code&gt;, Terraform automatically manages and updates the &lt;code&gt;terraform.tfstate&lt;/code&gt; file to store state about your infrastructure and configuration.
This step uses the &lt;a href=&#34;https://github.com/stefanzweifel/git-auto-commit-action&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;stefanzweifel/git-auto-commit-action@v4&lt;/a&gt; action to auto-commit the &lt;code&gt;terraform.tfstate&lt;/code&gt; file for changes made by running the &lt;code&gt;terraform apply&lt;/code&gt; step.&lt;/p&gt;


&lt;div class=&#34;admonition admonition-note&#34;&gt;&lt;blockquote&gt;&lt;p class=&#34;title text-uppercase&#34;&gt;Note&lt;/p&gt;&lt;p&gt;The Terraform state file (terraform.tfstate) shouldn&amp;rsquo;t be stored in Git to avoid leakage of sensitive data. Instead, store Terraform state files using a remote backend like AWS S3 with proper RBAC. For more information, refer to &lt;a href=&#34;https://www.terraform.io/language/state&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;Terraform state&lt;/a&gt;.&lt;/p&gt;&lt;/blockquote&gt;&lt;/div&gt;

&lt;h2 id=&#34;validation&#34;&gt;Validation&lt;/h2&gt;
&lt;p&gt;Once the GitHub workflow run is successful, you should be able to verify the following:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;code&gt;ElasticSearch&lt;/code&gt;, &lt;code&gt;InfluxDB&lt;/code&gt; and &lt;code&gt;AWS&lt;/code&gt; folders are created in the Grafana instance.&lt;/p&gt;
&lt;p&gt;&lt;img
  class=&#34;lazyload d-inline-block&#34;
  data-src=&#34;/media/docs/grafana-cloud/screenshot-folders-github-action-tf.png&#34;
  alt=&#34;Folders in Dashboards&#34; width=&#34;2390&#34;
     height=&#34;734&#34;/&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Dashboard represented as JSON source code from &lt;code&gt;elasticsearch&lt;/code&gt; folder in GitHub are added under the &lt;code&gt;ElasticSearch&lt;/code&gt; folder in the Grafana instance.&lt;/p&gt;
&lt;p&gt;&lt;img
  class=&#34;lazyload d-inline-block&#34;
  data-src=&#34;/media/docs/grafana-cloud/screenshot-elastic-folder-github-action-tf.png&#34;
  alt=&#34;ElasticSearch Folder&#34; width=&#34;2432&#34;
     height=&#34;708&#34;/&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Dashboard source code from the &lt;code&gt;influxdb&lt;/code&gt; folder in GitHub is added under the &lt;code&gt;InfluxDB&lt;/code&gt; folder in the Grafana instance.&lt;/p&gt;
&lt;p&gt;&lt;img
  class=&#34;lazyload d-inline-block&#34;
  data-src=&#34;/media/docs/grafana-cloud/screenshot-influxdb-folder-github-action-tf.png&#34;
  alt=&#34;InfluxDB Folder&#34; width=&#34;2428&#34;
     height=&#34;708&#34;/&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Dashboards from &lt;code&gt;aws&lt;/code&gt; folder in GitHub are added under the &lt;code&gt;AWS&lt;/code&gt; folder in the Grafana instance.&lt;/p&gt;
&lt;p&gt;&lt;img
  class=&#34;lazyload d-inline-block&#34;
  data-src=&#34;/media/docs/grafana-cloud/screenshots-aws-folder-github-action-tf.png&#34;
  alt=&#34;AWS EC2 Folder&#34; width=&#34;2434&#34;
     height=&#34;692&#34;/&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id=&#34;summary&#34;&gt;Summary&lt;/h2&gt;
&lt;p&gt;In this guide, you created a GitHub workflow using Terraform to manage dashboard source code. Using this workflow, the dashboards in the Grafana instance are synchronized with the JSON source code files for dashboards in GitHub.&lt;/p&gt;
&lt;p&gt;To learn more about managing Grafana Cloud using Terraform, refer to the &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;Grafana provider documentation&lt;/a&gt;.&lt;/p&gt;
]]></content><description>&lt;h1 id="create-and-manage-dashboards-using-terraform-and-github-actions">Create and manage dashboards using Terraform and GitHub Actions&lt;/h1>
&lt;p>Learn how to create and manage multiple dashboards represented as JSON source code for Grafana using Terraform and GitHub Actions.&lt;/p></description></item><item><title>Manage Grafana IRM in Grafana Cloud using Terraform</title><link>https://grafana.com/docs/grafana/v12.4/as-code/infrastructure-as-code/terraform/terraform-oncall/</link><pubDate>Fri, 03 Apr 2026 12:35:46 -0500</pubDate><guid>https://grafana.com/docs/grafana/v12.4/as-code/infrastructure-as-code/terraform/terraform-oncall/</guid><content><![CDATA[&lt;h1 id=&#34;manage-grafana-irm-in-grafana-cloud-using-terraform&#34;&gt;Manage Grafana IRM in Grafana Cloud using Terraform&lt;/h1&gt;
&lt;p&gt;Learn how to use Terraform to manage &lt;a href=&#34;/docs/grafana-cloud/alerting-and-irm/irm/&#34;&gt;Grafana IRM&lt;/a&gt; resources.
This guide shows you how to connect an integration, configure escalation policies, and add on-call schedules using Terraform.&lt;/p&gt;
&lt;p&gt;To illustrate the use of IRM across multiple teams, this guide features examples with two teams: &lt;code&gt;Devs&lt;/code&gt; and &lt;code&gt;SREs&lt;/code&gt;.
Additionally, it includes the necessary steps to configure Slack for IRM.&lt;/p&gt;


&lt;div class=&#34;admonition admonition-note&#34;&gt;&lt;blockquote&gt;&lt;p class=&#34;title text-uppercase&#34;&gt;Note&lt;/p&gt;&lt;p&gt;Grafana IRM supports Terraform-based configuration for a limited set of resources, primarily those related to OnCall functionality.
These resources use the &lt;code&gt;grafana_oncall_&lt;/code&gt; naming convention in Terraform. Additional IRM components are not yet configurable via Terraform.&lt;/p&gt;&lt;/blockquote&gt;&lt;/div&gt;

&lt;h2 id=&#34;before-you-begin&#34;&gt;Before you begin&lt;/h2&gt;
&lt;p&gt;Before you begin, ensure you have the following:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;A Grafana Cloud account, as shown in &lt;a href=&#34;/docs/grafana-cloud/get-started/&#34;&gt;Get started&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://www.terraform.io/downloads&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;Terraform&lt;/a&gt; installed on your machine&lt;/li&gt;
&lt;li&gt;Administrator permissions in your Grafana instance&lt;/li&gt;
&lt;li&gt;(Optional) Administrator permissions in your Slack workspace, if you plan to integrate Slack with Grafana IRM&lt;/li&gt;
&lt;/ul&gt;


&lt;div class=&#34;admonition admonition-note&#34;&gt;&lt;blockquote&gt;&lt;p class=&#34;title text-uppercase&#34;&gt;Note&lt;/p&gt;&lt;p&gt;All of the following Terraform configuration files should be saved in the same directory.&lt;/p&gt;&lt;/blockquote&gt;&lt;/div&gt;

&lt;h2 id=&#34;connect-slack-to-grafana-irm&#34;&gt;Connect Slack to Grafana IRM&lt;/h2&gt;
&lt;p&gt;Before including Slack settings in your Terraform setup, you must first configure the Slack integration with Grafana IRM.&lt;/p&gt;
&lt;p&gt;To connect your Slack workspace to Grafana IRM, refer to the &lt;a href=&#34;/docs/grafana-cloud/alerting-and-irm/irm/configure/integrations/irm-slack/&#34;&gt;Slack integration for Grafana IRM&lt;/a&gt; documentation.&lt;/p&gt;
&lt;h2 id=&#34;configure-the-grafana-provider&#34;&gt;Configure the Grafana provider&lt;/h2&gt;
&lt;p&gt;This Terraform configuration sets up the &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;Grafana provider&lt;/a&gt; to provide necessary authentication when managing resources for Grafana IRM.&lt;/p&gt;
&lt;p&gt;You can reuse a similar setup to the one described in &lt;a href=&#34;../terraform-cloud-stack/&#34;&gt;Creating and managing a Grafana Cloud stack using Terraform&lt;/a&gt; to set up a service account and a token.&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;Create a Service account and token in Grafana. To create a new one, refer to &lt;a href=&#34;/docs/grafana/latest/administration/service-accounts/#service-account-tokens&#34;&gt;Service account tokens&lt;/a&gt;.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Create a file named &lt;code&gt;main.tf&lt;/code&gt; and add the following:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;terraform&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-terraform&#34;&gt;terraform {
  required_providers {
    grafana = {
      source  = &amp;#34;grafana/grafana&amp;#34;
      version = &amp;#34;&amp;gt;= 3.15.3&amp;#34;
    }
  }
}

provider &amp;#34;grafana&amp;#34; {
  alias = &amp;#34;oncall&amp;#34;

  url  = &amp;#34;&amp;lt;Stack-URL&amp;gt;&amp;#34;
  auth = &amp;#34;&amp;lt;Service-account-token&amp;gt;&amp;#34;
  oncall_url = &amp;#34;&amp;lt;OnCall-URL&amp;gt;&amp;#34;
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Replace the following field values:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;&amp;lt;Stack-URL&amp;gt;&lt;/code&gt; with the URL of your Grafana stack&lt;/li&gt;
&lt;li&gt;&lt;code&gt;&amp;lt;Service-account-token&amp;gt;&lt;/code&gt; with the service account token that you created&lt;/li&gt;
&lt;li&gt;&lt;code&gt;&amp;lt;OnCall-URL&amp;gt;&lt;/code&gt; with the API URL found on the &lt;strong&gt;Admin &amp;amp; API&lt;/strong&gt; tab of the IRM &lt;strong&gt;Settings&lt;/strong&gt; page&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ol&gt;


&lt;div class=&#34;admonition admonition-note&#34;&gt;&lt;blockquote&gt;&lt;p class=&#34;title text-uppercase&#34;&gt;Note&lt;/p&gt;&lt;p&gt;If the service account has the right permissions, this provider setup also allows you to manage other Grafana resources.&lt;/p&gt;&lt;/blockquote&gt;&lt;/div&gt;

&lt;h3 id=&#34;authentication-via-oncall-api-tokens-deprecated&#34;&gt;Authentication via OnCall API tokens (deprecated)&lt;/h3&gt;
&lt;p&gt;OnCall API tokens are being deprecated.
While existing tokens will continue to work, we recommend using
&lt;a href=&#34;/docs/grafana-cloud/security-and-account-management/authentication-and-permissions/service-accounts/&#34;&gt;Grafana Cloud service account tokens&lt;/a&gt; for all new API authentication.&lt;/p&gt;
&lt;div class=&#34;collapse&#34; x-data=&#34;app_collapse()&#34;&gt;
  &lt;button class=&#34;collapse-trigger&#34; @click=&#34;toggle()&#34;&gt;
    &lt;span class=&#34;body-large&#34;&gt;Authentication via OnCall API tokens&lt;/span&gt;
    &lt;span class=&#34;collapse-trigger__icon&#34; :class=&#34;{ &#39;collapse-trigger__icon-open&#39; : open }&#34;&gt;
      
  &lt;svg width=&#34;27&#34; height=&#34;26&#34; viewBox=&#34;0 0 27 26&#34; fill=&#34;none&#34; xmlns=&#34;http://www.w3.org/2000/svg&#34;&gt;
&lt;path opacity=&#34;0.2&#34; d=&#34;M1.73047 12.8359C1.73047 19.4634 7.10305 24.8359 13.7305 24.8359C20.3579 24.8359 25.7305 19.4634 25.7305 12.8359C25.7305 6.20852 20.3579 0.835937 13.7305 0.835937C7.10305 0.835937 1.73047 6.20852 1.73047 12.8359Z&#34; stroke=&#34;black&#34; stroke-width=&#34;1.5&#34; stroke-linecap=&#34;round&#34; stroke-linejoin=&#34;round&#34;/&gt;
&lt;path d=&#34;M18.2344 12.8359L9.23438 12.8359&#34; stroke=&#34;black&#34; stroke-width=&#34;1.5&#34; stroke-linecap=&#34;round&#34; stroke-linejoin=&#34;round&#34;/&gt;
&lt;path d=&#34;M13.7344 8.33594L13.7344 17.3359&#34; stroke=&#34;black&#34; stroke-width=&#34;1.5&#34; stroke-linecap=&#34;round&#34; stroke-linejoin=&#34;round&#34;/&gt;
&lt;/svg&gt;


    &lt;/span&gt;
  &lt;/button&gt;
  &lt;div class=&#34;collapse-content&#34; x-ref=&#34;content&#34; hidden=&#34;until-found&#34;&gt;
    &lt;div class=&#34;collapse-content__inner&#34; x-ref=&#34;content-inner&#34;&gt;&lt;p&gt;To use an existing OnCall API token:&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;Log into your Grafana Cloud instance&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Select &lt;strong&gt;Alerts &amp;amp; IRM&lt;/strong&gt; &amp;gt; &lt;strong&gt;IRM&lt;/strong&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Click &lt;strong&gt;Settings&lt;/strong&gt;, and then select &lt;strong&gt;Admin &amp;amp; API&lt;/strong&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Locate the &lt;strong&gt;Grafana IRM API&lt;/strong&gt; section&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;View, copy or revoke existing &lt;strong&gt;OnCall API tokens&lt;/strong&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Create a file named &lt;code&gt;main.tf&lt;/code&gt; and add the following:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;terraform&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-terraform&#34;&gt;terraform {
  required_providers {
    grafana = {
      source  = &amp;#34;grafana/grafana&amp;#34;
      version = &amp;#34;&amp;gt;= 2.9.0&amp;#34;
    }
  }
}

provider &amp;#34;grafana&amp;#34; {
  alias = &amp;#34;oncall&amp;#34;

  oncall_access_token = &amp;#34;&amp;lt;OnCall-API-Token&amp;gt;&amp;#34;
  oncall_url = &amp;#34;&amp;lt;OnCall-URL&amp;gt;&amp;#34;
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Replace the following field values:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;&amp;lt;OnCall-API-Token&amp;gt;&lt;/code&gt; with your existing OnCall API Token&lt;/li&gt;
&lt;li&gt;&lt;code&gt;&amp;lt;OnCall-URL&amp;gt;&lt;/code&gt; with the API URL found on the &lt;strong&gt;Admin &amp;amp; API&lt;/strong&gt; tab of the IRM &lt;strong&gt;Settings&lt;/strong&gt; page&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;/div&gt;
  &lt;/div&gt;
&lt;/div&gt;

&lt;h2 id=&#34;add-on-call-schedules&#34;&gt;Add on-call schedules&lt;/h2&gt;
&lt;p&gt;This Terraform configuration sets up two on-call schedules, &lt;code&gt;SREs&lt;/code&gt; and &lt;code&gt;Devs&lt;/code&gt;, using the &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs/resources/oncall_schedule&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;&lt;code&gt;grafana_oncall_schedule&lt;/code&gt; resource&lt;/a&gt; to define the schedules within Grafana IRM.
Additionally, this configuration includes Slack channels to receive notifications for the on-call schedules of each team.&lt;/p&gt;
&lt;p&gt;To learn more about managing on-call schedules, refer to the &lt;a href=&#34;/docs/grafana-cloud/alerting-and-irm/irm/manage/on-call-schedules/&#34;&gt;On-call schedules documentation&lt;/a&gt;.&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;Create two new calendars in your calendar service, one for &lt;code&gt;Devs&lt;/code&gt; and one for &lt;code&gt;SREs&lt;/code&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Locate and save the secret iCal URLs.
For example, in a Google calendar, these URLs can be found in &lt;strong&gt;Settings &amp;gt; Settings for my calendars &amp;gt; Integrate calendar&lt;/strong&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Create a file named &lt;code&gt;schedule.tf&lt;/code&gt; and add the following:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;terraform&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-terraform&#34;&gt;# Name of the Slack channel to notify about on-call schedules for Devs
data &amp;#34;grafana_oncall_slack_channel&amp;#34; &amp;#34;Devs&amp;#34; {
  provider = grafana.oncall

  name = &amp;#34;&amp;lt;Devs-channel-name&amp;gt;&amp;#34;
}

# Name of the Slack channel to notify about on-call schedules for SREs
data &amp;#34;grafana_oncall_slack_channel&amp;#34; &amp;#34;SREs&amp;#34; {
  provider = grafana.oncall

  name = &amp;#34;&amp;lt;SREs-channel-name&amp;gt;&amp;#34;
}

resource &amp;#34;grafana_oncall_schedule&amp;#34; &amp;#34;schedule_Devs&amp;#34; {
  provider = grafana.oncall

  name             = &amp;#34;Devs&amp;#34;
  type             = &amp;#34;ical&amp;#34;
  ical_url_primary = &amp;#34;&amp;lt;secret-iCal-URL-for-devs-calendar&amp;gt;&amp;#34;
  slack {
    channel_id = data.grafana_oncall_slack_channel.Devs.slack_id
  }
}

resource &amp;#34;grafana_oncall_schedule&amp;#34; &amp;#34;schedule_SREs&amp;#34; {
  provider = grafana.oncall

  name             = &amp;#34;SREs&amp;#34;
  type             = &amp;#34;ical&amp;#34;
  ical_url_primary = &amp;#34;&amp;lt;secret-iCal-URL-for-SREs-calendar&amp;gt;&amp;#34;
  slack {
    channel_id = data.grafana_oncall_slack_channel.SREs.slack_id
  }
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Replace the following field values:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;&amp;lt;Devs-channel-name&amp;gt;&lt;/code&gt; with name of the Slack channel to notify about on-call schedules for &lt;code&gt;Devs&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;&amp;lt;SREs-channel-name&amp;gt;&lt;/code&gt; with name of the Slack channel to notify about on-call schedules for &lt;code&gt;SREs&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;&amp;lt;secret-iCal-URL-for-devs-calendar&amp;gt;&lt;/code&gt; with the secret iCal URL created in the first step for &lt;code&gt;Devs&lt;/code&gt; Calendar&lt;/li&gt;
&lt;li&gt;&lt;code&gt;&amp;lt;secret-iCal-URL-for-SREs-calendar&amp;gt;&lt;/code&gt; with the secret iCal URL created in the first step for &lt;code&gt;SREs&lt;/code&gt; Calendar&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;h2 id=&#34;add-escalation-chains&#34;&gt;Add escalation chains&lt;/h2&gt;
&lt;p&gt;This Terraform configuration creates two escalation chains named &lt;code&gt;SREs&lt;/code&gt; and &lt;code&gt;Devs&lt;/code&gt; in Grafana IRM using the &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs/resources/oncall_escalation_chain&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;&lt;code&gt;grafana_oncall_escalation_chain&lt;/code&gt; (Resource)&lt;/a&gt;.
The configuration also adds the following three steps to each escalation chain using the &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs/resources/oncall_escalation&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;&lt;code&gt;grafana_oncall_escalation&lt;/code&gt; (Resource)&lt;/a&gt;:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Notify users from on-call schedule&lt;/li&gt;
&lt;li&gt;Wait for 5 minutes&lt;/li&gt;
&lt;li&gt;Notify default Slack channel&lt;/li&gt;
&lt;/ul&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;Create a file named &lt;code&gt;escalation-devs.tf&lt;/code&gt; and add the following:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;terraform&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-terraform&#34;&gt;resource &amp;#34;grafana_oncall_escalation_chain&amp;#34; &amp;#34;Devs&amp;#34; {
  provider = grafana.oncall

  name = &amp;#34;Devs&amp;#34;
}

// Notify users from on-call schedule
resource &amp;#34;grafana_oncall_escalation&amp;#34; &amp;#34;notify_schedule_step_Devs&amp;#34; {
  provider = grafana.oncall

  escalation_chain_id          = grafana_oncall_escalation_chain.Devs.id
  type                         = &amp;#34;notify_on_call_from_schedule&amp;#34;
  notify_on_call_from_schedule = grafana_oncall_schedule.schedule_Devs.id
  position                     = 0
}

// Wait step for 5 Minutes
resource &amp;#34;grafana_oncall_escalation&amp;#34; &amp;#34;wait_step_Devs&amp;#34; {
  provider = grafana.oncall

  escalation_chain_id = grafana_oncall_escalation_chain.Devs.id
  type                = &amp;#34;wait&amp;#34;
  duration            = 300
  position            = 1
}

// Notify default Slack channel step
resource &amp;#34;grafana_oncall_escalation&amp;#34; &amp;#34;notify_step_Devs&amp;#34; {
  provider = grafana.oncall

  escalation_chain_id = grafana_oncall_escalation_chain.Devs.id
  type                = &amp;#34;notify_whole_channel&amp;#34;
  important           = true
  position            = 2
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Create a file named &lt;code&gt;escalation-sre.tf&lt;/code&gt; and add the following:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;terraform&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-terraform&#34;&gt;resource &amp;#34;grafana_oncall_escalation_chain&amp;#34; &amp;#34;SREs&amp;#34; {
  provider = grafana.oncall

  name = &amp;#34;SREs&amp;#34;
}

// Notify users from on-call schedule
resource &amp;#34;grafana_oncall_escalation&amp;#34; &amp;#34;notify_schedule_step_SREs&amp;#34; {
  provider = grafana.oncall

  escalation_chain_id          = grafana_oncall_escalation_chain.SREs.id
  type                         = &amp;#34;notify_on_call_from_schedule&amp;#34;
  notify_on_call_from_schedule = grafana_oncall_schedule.schedule_SREs.id
  position                     = 0
}

// Wait step for 5 Minutes
resource &amp;#34;grafana_oncall_escalation&amp;#34; &amp;#34;wait_step_SREs&amp;#34; {
  provider = grafana.oncall

  escalation_chain_id = grafana_oncall_escalation_chain.SREs.id
  type                = &amp;#34;wait&amp;#34;
  duration            = 300
  position            = 1
}

// Notify default Slack channel step
resource &amp;#34;grafana_oncall_escalation&amp;#34; &amp;#34;notify_step_SREs&amp;#34; {
  provider = grafana.oncall

  escalation_chain_id = grafana_oncall_escalation_chain.SREs.id
  type                = &amp;#34;notify_whole_channel&amp;#34;
  important           = true
  position            = 2
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;h2 id=&#34;connect-an-integration-to-grafana-irm&#34;&gt;Connect an integration to Grafana IRM&lt;/h2&gt;
&lt;p&gt;This Terraform configuration connects Alertmanager to Grafana IRM using the &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs/resources/oncall_integration&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;&lt;code&gt;grafana_oncall_integration&lt;/code&gt; (Resource)&lt;/a&gt;.
It also adds the &lt;code&gt;Devs&lt;/code&gt; escalation chain as the default route for alerts.&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;Create a file named &lt;code&gt;integrations.tf&lt;/code&gt; and add the following:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;terraform&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-terraform&#34;&gt;resource &amp;#34;grafana_oncall_integration&amp;#34; &amp;#34;AlertManager&amp;#34; {
  provider = grafana.oncall

  name = &amp;#34;AlertManager&amp;#34;
  type = &amp;#34;alertmanager&amp;#34;
  default_route {
    escalation_chain_id = grafana_oncall_escalation_chain.Devs.id
  }
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;To configure Alertmanager, refer to the &lt;a href=&#34;/docs/grafana-cloud/alerting-and-irm/oncall/integrations/alertmanager/&#34;&gt;Alertmanager integration for Grafana OnCall&lt;/a&gt; documentation.&lt;/p&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;h2 id=&#34;set-up-a-route-to-configure-escalation-behavior-for-alert-group-notifications&#34;&gt;Set up a route to configure escalation behavior for alert group notifications&lt;/h2&gt;
&lt;p&gt;This Terraform configuration sets up a route to the Alertmanager integration using the &lt;code&gt;grafana_oncall_route&lt;/code&gt; (Resource).
This route ensures that notifications for alerts with &lt;code&gt;\&amp;quot;namespace\&amp;quot; *: *\&amp;quot;ops-.*\&amp;quot;&lt;/code&gt; in the payload are escalated to the &lt;code&gt;SREs&lt;/code&gt; escalation chain.&lt;/p&gt;
&lt;p&gt;Create a file named &lt;code&gt;routes.tf&lt;/code&gt; and add the following:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;terraform&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-terraform&#34;&gt;resource &amp;#34;grafana_oncall_route&amp;#34; &amp;#34;route_SREs&amp;#34; {
  provider = grafana.oncall

  integration_id      = grafana_oncall_integration.AlertManager.id
  escalation_chain_id = grafana_oncall_escalation_chain.SREs.id
  routing_regex       = &amp;#34;\&amp;#34;namespace\&amp;#34; *: *\&amp;#34;ops-.*\&amp;#34;&amp;#34;
  position            = 0
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;h2 id=&#34;apply-the-terraform-configuration&#34;&gt;Apply the Terraform configuration&lt;/h2&gt;
&lt;p&gt;In a terminal, run the following commands from the directory where all of the configuration files are located.&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;Initialize a working directory containing Terraform configuration files.&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;shell&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-shell&#34;&gt;terraform init&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Preview the changes that Terraform will make.&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;shell&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-shell&#34;&gt;terraform plan&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Apply the configuration files.&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;shell&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-shell&#34;&gt;terraform apply&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;h2 id=&#34;validation&#34;&gt;Validation&lt;/h2&gt;
&lt;p&gt;After you apply the changes in the Terraform configurations, you can verify the following:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;Two new Schedules named &lt;code&gt;Devs&lt;/code&gt; and &lt;code&gt;SREs&lt;/code&gt; are created in Grafana IRM:&lt;/p&gt;
&lt;p&gt;&lt;img
  class=&#34;lazyload d-inline-block&#34;
  data-src=&#34;/media/docs/grafana-cloud/alerting-and-irm/screenshot-oncall-schedules-tf.png&#34;
  alt=&#34;Devs and SREs OnCall schedules&#34; width=&#34;1320&#34;
     height=&#34;484&#34;/&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;New Escalation chain named &lt;code&gt;SREs&lt;/code&gt; is created in Grafana IRM:&lt;/p&gt;
&lt;p&gt;&lt;img
  class=&#34;lazyload d-inline-block&#34;
  data-src=&#34;/media/docs/grafana-cloud/alerting-and-irm/screenshot-oncall-escalation-sre-tf.png&#34;
  alt=&#34;SREs escalation chain&#34; width=&#34;1320&#34;
     height=&#34;580&#34;/&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;New Escalation chain named &lt;code&gt;Devs&lt;/code&gt; is created in Grafana IRM:&lt;/p&gt;
&lt;p&gt;&lt;img
  class=&#34;lazyload d-inline-block&#34;
  data-src=&#34;/media/docs/grafana-cloud/alerting-and-irm/screenshot-oncall-escalation-devs-tf.png&#34;
  alt=&#34;Devs escalation chain&#34; width=&#34;1320&#34;
     height=&#34;580&#34;/&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;The Alertmanager integration is added and configured with escalation policies:&lt;/p&gt;
&lt;p&gt;&lt;img
  class=&#34;lazyload d-inline-block&#34;
  data-src=&#34;/media/docs/grafana-cloud/alerting-and-irm/screenshot-oncall-alertmanager-tf.png&#34;
  alt=&#34;Alertmanager integration for SREs escalation&#34; width=&#34;1320&#34;
     height=&#34;716&#34;/&gt;&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id=&#34;summary&#34;&gt;Summary&lt;/h2&gt;
&lt;p&gt;In this guide, you learned how to use Terraform to manage Grafana IRM by connecting an integration, configuring escalation policies, and setting up on-call schedules.&lt;/p&gt;
&lt;p&gt;To learn more about managing Grafana Cloud using Terraform, refer to the &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;Grafana provider documentation&lt;/a&gt;.&lt;/p&gt;
]]></content><description>&lt;h1 id="manage-grafana-irm-in-grafana-cloud-using-terraform">Manage Grafana IRM in Grafana Cloud using Terraform&lt;/h1>
&lt;p>Learn how to use Terraform to manage &lt;a href="/docs/grafana-cloud/alerting-and-irm/irm/">Grafana IRM&lt;/a> resources.
This guide shows you how to connect an integration, configure escalation policies, and add on-call schedules using Terraform.&lt;/p></description></item><item><title>Manage Knowledge Graph in Grafana Cloud using Terraform</title><link>https://grafana.com/docs/grafana/v12.4/as-code/infrastructure-as-code/terraform/terraform-knowledge-graph/</link><pubDate>Fri, 03 Apr 2026 12:35:46 -0500</pubDate><guid>https://grafana.com/docs/grafana/v12.4/as-code/infrastructure-as-code/terraform/terraform-knowledge-graph/</guid><content><![CDATA[

  
    
      
    
  
&lt;div class=&#34;docs-hero my-2 &#34;&gt;
  &lt;div class=&#34;d-flex flex-direction-row flex-direction-column-small column-gap-20 row-gap-10 justify-content-start align-items-center align-items-start-small flex-wrap &#34;&gt;&lt;div class=&#34;d-flex flex-direction-column flex-1-1 minw-400 minw-xs-unset&#34;&gt;
      &lt;div&gt;&lt;h3
  
  id=&#34;&#34;
  &gt;&lt;/h3&gt;&lt;/div&gt;
      
    &lt;/div&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;hr /&gt;
&lt;h2 id=&#34;overview&#34;&gt;Overview&lt;/h2&gt;
&lt;p&gt;Terraform enables you to manage &lt;a href=&#34;/docs/grafana-cloud/knowledge-graph/&#34;&gt;Grafana Cloud Knowledge Graph&lt;/a&gt; resources using infrastructure as code. With Terraform, you can define, version control, and deploy Knowledge Graph configurations including stack onboarding, alert rules, suppression policies, entity models, log, trace, and profile correlations, and thresholds.&lt;/p&gt;
&lt;h2 id=&#34;explore&#34;&gt;Explore&lt;/h2&gt;

&lt;hr /&gt;
&lt;h2 id=&#34;related-resources&#34;&gt;Related resources&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;Grafana Terraform Provider Documentation&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;/docs/grafana-cloud/knowledge-graph/&#34;&gt;Knowledge Graph Documentation&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://www.terraform.io/docs/cloud/guides/recommended-practices/index.html&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;Terraform Best Practices&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
]]></content><description>&lt;div class="docs-hero my-2 ">
&lt;div class="d-flex flex-direction-row flex-direction-column-small column-gap-20 row-gap-10 justify-content-start align-items-center align-items-start-small flex-wrap ">&lt;div class="d-flex flex-direction-column flex-1-1 minw-400 minw-xs-unset">
&lt;div>&lt;h3
id=""
>&lt;/h3>&lt;/div>
&lt;/div>
&lt;/div>
&lt;/div>
&lt;hr />
&lt;h2 id="overview">Overview&lt;/h2>
&lt;p>Terraform enables you to manage &lt;a href="/docs/grafana-cloud/knowledge-graph/">Grafana Cloud Knowledge Graph&lt;/a> resources using infrastructure as code. With Terraform, you can define, version control, and deploy Knowledge Graph configurations including stack onboarding, alert rules, suppression policies, entity models, log, trace, and profile correlations, and thresholds.&lt;/p></description></item><item><title>Manage Fleet Management in Grafana Cloud using Terraform</title><link>https://grafana.com/docs/grafana/v12.4/as-code/infrastructure-as-code/terraform/terraform-fleet-management/</link><pubDate>Fri, 03 Apr 2026 12:35:46 -0500</pubDate><guid>https://grafana.com/docs/grafana/v12.4/as-code/infrastructure-as-code/terraform/terraform-fleet-management/</guid><content><![CDATA[&lt;h1 id=&#34;manage-fleet-management-in-grafana-cloud-using-terraform&#34;&gt;Manage Fleet Management in Grafana Cloud using Terraform&lt;/h1&gt;
&lt;p&gt;Learn how to create &lt;a href=&#34;/docs/grafana-cloud/send-data/fleet-management/&#34;&gt;Grafana Fleet Management&lt;/a&gt; collectors and pipelines in Grafana Cloud using Terraform.
This guide shows you how to create an access policy and a token for Fleet Management and &lt;a href=&#34;/docs/alloy/latest/&#34;&gt;Grafana Alloy&lt;/a&gt;, a collector with remote attributes, and a pipeline for profiling Alloy.&lt;/p&gt;
&lt;h2 id=&#34;before-you-begin&#34;&gt;Before you begin&lt;/h2&gt;
&lt;p&gt;Before you begin, ensure you have the following:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;A Grafana Cloud account, as shown in &lt;a href=&#34;/docs/grafana-cloud/get-started/&#34;&gt;Get started&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://www.terraform.io/downloads&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;Terraform&lt;/a&gt; installed on your machine&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;/docs/alloy/latest/set-up/install/&#34;&gt;Alloy&lt;/a&gt; installed on your machine&lt;/li&gt;
&lt;li&gt;Administrator permissions in your Grafana instance&lt;/li&gt;
&lt;/ul&gt;


&lt;div class=&#34;admonition admonition-note&#34;&gt;&lt;blockquote&gt;&lt;p class=&#34;title text-uppercase&#34;&gt;Note&lt;/p&gt;&lt;p&gt;All of the following Terraform configuration files should be saved in the same directory.&lt;/p&gt;&lt;/blockquote&gt;&lt;/div&gt;

&lt;h2 id=&#34;configure-a-provider-for-grafana-cloud&#34;&gt;Configure a provider for Grafana Cloud&lt;/h2&gt;
&lt;p&gt;This Terraform configuration configures the &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;Grafana provider&lt;/a&gt; to provide necessary authentication when interacting with the Cloud API.
The &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs/data-sources/cloud_stack&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;&lt;code&gt;grafana_cloud_stack&lt;/code&gt; (Data Source)&lt;/a&gt; is used to retrieve the user ID and URL details of your instance.&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;Create a Grafana Cloud access policy and token.
To create a new one, refer to &lt;a href=&#34;/docs/grafana-cloud/security-and-account-management/authentication-and-permissions/access-policies/&#34;&gt;Grafana Cloud Access Policies&lt;/a&gt;.
Add your stack to the realms list.
The scopes needed for the examples in this guide are:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;accesspolicies:read&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;accesspolicies:write&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;accesspolicies:delete&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;stacks:read&lt;/code&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Create a file named &lt;code&gt;cloud-provider.tf&lt;/code&gt; and add the following code block:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;terraform&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-terraform&#34;&gt;terraform {
  required_providers {
    grafana = {
      source  = &amp;#34;grafana/grafana&amp;#34;
      version = &amp;#34;&amp;gt;= 3.19.0&amp;#34;
    }
  }
}

provider &amp;#34;grafana&amp;#34; {
  alias = &amp;#34;cloud&amp;#34;

  cloud_access_policy_token = &amp;#34;&amp;lt;CLOUD_ACCESS_POLICY_TOKEN&amp;gt;&amp;#34;
}

data &amp;#34;grafana_cloud_stack&amp;#34; &amp;#34;stack&amp;#34; {
  provider = grafana.cloud

  slug = &amp;#34;&amp;lt;STACK_SLUG&amp;gt;&amp;#34;
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Replace the following field values:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;&amp;lt;CLOUD_ACCESS_POLICY_TOKEN&amp;gt;&lt;/code&gt; with the access policy token you created in the first step&lt;/li&gt;
&lt;li&gt;&lt;code&gt;&amp;lt;STACK_SLUG&amp;gt;&lt;/code&gt; with your stack slug, which is the subdomain where your Grafana Cloud instance is available: &lt;code&gt;https://&amp;lt;STACK_SLUG&amp;gt;.grafana.net&lt;/code&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;h2 id=&#34;create-an-access-policy-and-token-for-fleet-management&#34;&gt;Create an access policy and token for Fleet Management&lt;/h2&gt;
&lt;p&gt;This Terraform configuration creates the following:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;An access policy named &lt;code&gt;fleet-management-policy&lt;/code&gt; with &lt;code&gt;fleet-management:read&lt;/code&gt; and &lt;code&gt;fleet-management:write&lt;/code&gt; scopes, using &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs/resources/cloud_access_policy&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;&lt;code&gt;grafana_cloud_access_policy&lt;/code&gt; (Resource)&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;A token named &lt;code&gt;fleet-management-token&lt;/code&gt;, using &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs/resources/cloud_access_policy_token&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;&lt;code&gt;grafana_cloud_access_policy_token&lt;/code&gt; (Resource)&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;Create a file named &lt;code&gt;fm-access-policy.tf&lt;/code&gt; and add the following code block:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;terraform&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-terraform&#34;&gt;resource &amp;#34;grafana_cloud_access_policy&amp;#34; &amp;#34;fm_policy&amp;#34; {
  provider = grafana.cloud

  name   = &amp;#34;fleet-management-policy&amp;#34;
  region = data.grafana_cloud_stack.stack.region_slug

  scopes = [
    &amp;#34;fleet-management:read&amp;#34;,
    &amp;#34;fleet-management:write&amp;#34;
  ]

  realm {
    type       = &amp;#34;stack&amp;#34;
    identifier = data.grafana_cloud_stack.stack.id
  }
}

resource &amp;#34;grafana_cloud_access_policy_token&amp;#34; &amp;#34;fm_token&amp;#34; {
  provider = grafana.cloud

  name             = &amp;#34;fleet-management-token&amp;#34;
  region           = grafana_cloud_access_policy.fm_policy.region
  access_policy_id = grafana_cloud_access_policy.fm_policy.policy_id
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;h2 id=&#34;configure-a-provider-for-fleet-management&#34;&gt;Configure a provider for Fleet Management&lt;/h2&gt;
&lt;p&gt;This Terraform configuration configures the &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;Grafana provider&lt;/a&gt; to provide necessary authentication when interacting with the Fleet Management API.&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;Create a file named &lt;code&gt;fm-provider.tf&lt;/code&gt; and add the following code block:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;terraform&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-terraform&#34;&gt;locals {
  fm_id    = data.grafana_cloud_stack.stack.fleet_management_user_id
  fm_token = grafana_cloud_access_policy_token.fm_token.token
  fm_url   = data.grafana_cloud_stack.stack.fleet_management_url
}

provider &amp;#34;grafana&amp;#34; {
  alias = &amp;#34;fm&amp;#34;

  fleet_management_auth = &amp;#34;${local.fm_id}:${local.fm_token}&amp;#34;
  fleet_management_url  = local.fm_url
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;h2 id=&#34;create-a-fleet-management-collector&#34;&gt;Create a Fleet Management collector&lt;/h2&gt;
&lt;p&gt;This Terraform configuration creates a collector with a remote attribute, using &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs/resources/fleet_management_collector&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;&lt;code&gt;grafana_fleet_management_collector&lt;/code&gt; (Resource)&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;This configuration only preregisters the collector.
You must complete the &lt;a href=&#34;#run-alloy&#34;&gt;Run Alloy&lt;/a&gt; step for the collector to register with Fleet Management and be assigned remote attributes.&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;Create a file named &lt;code&gt;fm-collector.tf&lt;/code&gt; and add the following code block:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;terraform&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-terraform&#34;&gt;resource &amp;#34;grafana_fleet_management_collector&amp;#34; &amp;#34;fm_collector&amp;#34; {
  provider = grafana.fm

  id = &amp;#34;prod_collector&amp;#34;
  remote_attributes = {
    &amp;#34;env&amp;#34; = &amp;#34;PROD&amp;#34;
  }
  enabled = true
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;h2 id=&#34;create-a-fleet-management-pipeline&#34;&gt;Create a Fleet Management pipeline&lt;/h2&gt;
&lt;p&gt;This Terraform configuration creates a pipeline for Alloy profiling with a matcher for the collector declared in the previous step, using &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs/resources/fleet_management_pipeline&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;&lt;code&gt;grafana_fleet_management_pipeline&lt;/code&gt; (Resource)&lt;/a&gt;.
The pipeline writes the profiles to &lt;a href=&#34;/docs/grafana-cloud/monitor-applications/profiles/&#34;&gt;Grafana Cloud Profiles&lt;/a&gt;.&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;Create a file named &lt;code&gt;profiling.alloy.tftpl&lt;/code&gt; and add the following content:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;Alloy&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-alloy&#34;&gt;// This pipeline scrapes pprof Go profiles from Alloy and sends them to Pyroscope.
//
// It requires the following environment variables to be set where Alloy is running:
//   Required:
//     * GCLOUD_RW_API_KEY: The Grafana Cloud API key with write access to Pyroscope.
//   Optional:
//     * ALLOY_ADDRESS: The address Alloy listens on. Defaults to 127.0.0.1:12345.
pyroscope.scrape &amp;#34;alloy&amp;#34; {
    targets = [
        {
            &amp;#34;__address__&amp;#34; = coalesce(
                sys.env(&amp;#34;ALLOY_ADDRESS&amp;#34;),
                &amp;#34;127.0.0.1:12345&amp;#34;,
            ),
            &amp;#34;service_name&amp;#34; = &amp;#34;alloy&amp;#34;,
        },
    ]
    forward_to = [pyroscope.write.grafana_cloud.receiver]

    profiling_config {
        profile.process_cpu {
            enabled = true
        }

        profile.memory {
            enabled = true
        }

        profile.mutex {
            enabled = true
        }

        profile.block {
            enabled = true
        }

        profile.goroutine {
            enabled = true
        }
    }
}

pyroscope.write &amp;#34;grafana_cloud&amp;#34; {
    endpoint {
        url = &amp;#34;${profiles_url}&amp;#34;

        basic_auth {
            username = &amp;#34;${profiles_id}&amp;#34;
            password = sys.env(&amp;#34;GCLOUD_RW_API_KEY&amp;#34;)
        }
    }
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Create a file named &lt;code&gt;fm-pipeline.tf&lt;/code&gt; and add the following code block:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;terraform&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-terraform&#34;&gt;locals {
  profiles_id  = data.grafana_cloud_stack.stack.profiles_user_id
  profiles_url = data.grafana_cloud_stack.stack.profiles_url
}

resource &amp;#34;grafana_fleet_management_pipeline&amp;#34; &amp;#34;pipeline&amp;#34; {
  provider = grafana.fm

  name = &amp;#34;profiling&amp;#34;
  contents = templatefile(
    &amp;#34;profiling.alloy.tftpl&amp;#34;,
    {
      profiles_id  = local.profiles_id,
      profiles_url = local.profiles_url,
    },
  )
  matchers = [
    &amp;#34;env=\&amp;#34;PROD\&amp;#34;&amp;#34;
  ]
  enabled = true
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;h2 id=&#34;create-an-access-policy-and-token-for-alloy&#34;&gt;Create an access policy and token for Alloy&lt;/h2&gt;
&lt;p&gt;This Terraform configuration creates the following:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;An access policy named &lt;code&gt;alloy-policy&lt;/code&gt; with &lt;code&gt;set:alloy-data-write&lt;/code&gt; scope, using &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs/resources/cloud_access_policy&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;&lt;code&gt;grafana_cloud_access_policy&lt;/code&gt; (Resource)&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;A token named &lt;code&gt;alloy-token&lt;/code&gt;, using &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs/resources/cloud_access_policy_token&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;&lt;code&gt;grafana_cloud_access_policy_token&lt;/code&gt; (Resource)&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;Create a file named &lt;code&gt;alloy-access-policy.tf&lt;/code&gt; and add the following code block:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;terraform&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-terraform&#34;&gt;resource &amp;#34;grafana_cloud_access_policy&amp;#34; &amp;#34;alloy_policy&amp;#34; {
  provider = grafana.cloud

  name   = &amp;#34;alloy-policy&amp;#34;
  region = data.grafana_cloud_stack.stack.region_slug

  scopes = [
    &amp;#34;set:alloy-data-write&amp;#34;
  ]

  realm {
    type       = &amp;#34;stack&amp;#34;
    identifier = data.grafana_cloud_stack.stack.id
  }
}

resource &amp;#34;grafana_cloud_access_policy_token&amp;#34; &amp;#34;alloy_token&amp;#34; {
  provider = grafana.cloud

  name             = &amp;#34;alloy-token&amp;#34;
  region           = grafana_cloud_access_policy.alloy_policy.region
  access_policy_id = grafana_cloud_access_policy.alloy_policy.policy_id
}

output &amp;#34;alloy_token&amp;#34; {
  value     = grafana_cloud_access_policy_token.alloy_token.token
  sensitive = true
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;h2 id=&#34;create-a-configuration-file-for-alloy&#34;&gt;Create a configuration file for Alloy&lt;/h2&gt;
&lt;p&gt;This Terraform configuration creates an Alloy configuration file with the &lt;a href=&#34;/docs/grafana-cloud/send-data/alloy/reference/config-blocks/remotecfg/&#34;&gt;&lt;code&gt;remotecfg&lt;/code&gt; block&lt;/a&gt; for Fleet Management, using &lt;a href=&#34;https://registry.terraform.io/providers/hashicorp/local/latest/docs/resources/file&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;&lt;code&gt;local_file&lt;/code&gt; (Resource)&lt;/a&gt;.&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;Create a file named &lt;code&gt;config.alloy.tftpl&lt;/code&gt; and add the following content:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;Alloy&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-alloy&#34;&gt;remotecfg {
    id             = &amp;#34;${collector_id}&amp;#34;
    url            = &amp;#34;${fm_url}&amp;#34;
    poll_frequency = &amp;#34;60s&amp;#34;

    basic_auth {
        username = &amp;#34;${fm_id}&amp;#34;
        password = sys.env(&amp;#34;GCLOUD_RW_API_KEY&amp;#34;)
    }
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Create a file named &lt;code&gt;alloy-config.tf&lt;/code&gt; and add the following code block:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;terraform&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-terraform&#34;&gt;resource &amp;#34;local_file&amp;#34; &amp;#34;alloy_config&amp;#34; {
  filename = &amp;#34;&amp;lt;ALLOY_CONFIG_PATH&amp;gt;&amp;#34;
  content = templatefile(
    &amp;#34;config.alloy.tftpl&amp;#34;,
    {
      collector_id = &amp;#34;prod_collector&amp;#34;,
      fm_id        = local.fm_id,
      fm_url       = local.fm_url,
    },
  )
  directory_permission = &amp;#34;0644&amp;#34;
  file_permission      = &amp;#34;0644&amp;#34;
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Replace the following field values:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;&amp;lt;ALLOY_CONFIG_PATH&amp;gt;&lt;/code&gt; with the path the Alloy configuration file should be written to, for example &lt;code&gt;config.alloy&lt;/code&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;h2 id=&#34;apply-the-terraform-configuration&#34;&gt;Apply the Terraform configuration&lt;/h2&gt;
&lt;p&gt;In a terminal, run the following commands from the directory where all of the configuration files are located.&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;Initialize a working directory containing Terraform configuration files:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;shell&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-shell&#34;&gt;terraform init&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Preview the Terraform changes:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;shell&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-shell&#34;&gt;terraform plan&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Apply the configuration:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;shell&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-shell&#34;&gt;terraform apply&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;h2 id=&#34;run-alloy&#34;&gt;Run Alloy&lt;/h2&gt;
&lt;p&gt;To learn how to start or restart Alloy, refer to &lt;a href=&#34;/docs/alloy/latest/set-up/run/&#34;&gt;Run Grafana Alloy&lt;/a&gt;.&lt;/p&gt;


&lt;div class=&#34;admonition admonition-note&#34;&gt;&lt;blockquote&gt;&lt;p class=&#34;title text-uppercase&#34;&gt;Note&lt;/p&gt;&lt;p&gt;The variable &lt;code&gt;GCLOUD_RW_API_KEY&lt;/code&gt; must be set in the environment where Alloy is running for the remote configuration in this example to work.&lt;/p&gt;&lt;/blockquote&gt;&lt;/div&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;Run the following command to view the Alloy token:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;shell&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-shell&#34;&gt;terraform output -raw alloy_token&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Set the environment variable &lt;code&gt;GCLOUD_RW_API_KEY&lt;/code&gt; to the value from the first step.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Run Alloy.&lt;/p&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;h2 id=&#34;validation&#34;&gt;Validation&lt;/h2&gt;
&lt;p&gt;After you apply the changes in the Terraform configurations and run Alloy, you should be able to verify the following:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;A collector is added to the Fleet Management &lt;strong&gt;Inventory tab&lt;/strong&gt;:&lt;/p&gt;
&lt;figure
      class=&#34;figure-wrapper figure-wrapper__lightbox w-100p &#34;
      style=&#34;max-width: 2222px;&#34;
      itemprop=&#34;associatedMedia&#34;
      itemscope=&#34;&#34;
      itemtype=&#34;http://schema.org/ImageObject&#34;
    &gt;&lt;a
          class=&#34;lightbox-link&#34;
          href=&#34;/media/docs/fleet-management/screenshot-fleet-management-terraform-validate-collector.png&#34;
          itemprop=&#34;contentUrl&#34;
        &gt;&lt;div class=&#34;img-wrapper w-100p h-auto&#34;&gt;&lt;img
            class=&#34;lazyload &#34;
            data-src=&#34;/media/docs/fleet-management/screenshot-fleet-management-terraform-validate-collector.png&#34;data-srcset=&#34;/media/docs/fleet-management/screenshot-fleet-management-terraform-validate-collector.png?w=320 320w, /media/docs/fleet-management/screenshot-fleet-management-terraform-validate-collector.png?w=550 550w, /media/docs/fleet-management/screenshot-fleet-management-terraform-validate-collector.png?w=750 750w, /media/docs/fleet-management/screenshot-fleet-management-terraform-validate-collector.png?w=900 900w, /media/docs/fleet-management/screenshot-fleet-management-terraform-validate-collector.png?w=1040 1040w, /media/docs/fleet-management/screenshot-fleet-management-terraform-validate-collector.png?w=1240 1240w, /media/docs/fleet-management/screenshot-fleet-management-terraform-validate-collector.png?w=1920 1920w&#34;data-sizes=&#34;auto&#34;alt=&#34;The Inventory screen in the Fleet Management interface in Grafana Cloud which shows that a new collector called `prod_collector` is registered with attribute `env=PROD`, has a healthy status, and was last modified a few seconds ago.&#34;width=&#34;2222&#34;height=&#34;978&#34;/&gt;
          &lt;noscript&gt;
            &lt;img
              src=&#34;/media/docs/fleet-management/screenshot-fleet-management-terraform-validate-collector.png&#34;
              alt=&#34;The Inventory screen in the Fleet Management interface in Grafana Cloud which shows that a new collector called `prod_collector` is registered with attribute `env=PROD`, has a healthy status, and was last modified a few seconds ago.&#34;width=&#34;2222&#34;height=&#34;978&#34;/&gt;
          &lt;/noscript&gt;&lt;/div&gt;&lt;/a&gt;&lt;/figure&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;A pipeline is added to the Fleet Management &lt;strong&gt;Remote configuration tab&lt;/strong&gt;:&lt;/p&gt;
&lt;figure
      class=&#34;figure-wrapper figure-wrapper__lightbox w-100p &#34;
      style=&#34;max-width: 2228px;&#34;
      itemprop=&#34;associatedMedia&#34;
      itemscope=&#34;&#34;
      itemtype=&#34;http://schema.org/ImageObject&#34;
    &gt;&lt;a
          class=&#34;lightbox-link&#34;
          href=&#34;/media/docs/fleet-management/screenshot-fleet-management-terraform-validate-pipeline.png&#34;
          itemprop=&#34;contentUrl&#34;
        &gt;&lt;div class=&#34;img-wrapper w-100p h-auto&#34;&gt;&lt;img
            class=&#34;lazyload &#34;
            data-src=&#34;/media/docs/fleet-management/screenshot-fleet-management-terraform-validate-pipeline.png&#34;data-srcset=&#34;/media/docs/fleet-management/screenshot-fleet-management-terraform-validate-pipeline.png?w=320 320w, /media/docs/fleet-management/screenshot-fleet-management-terraform-validate-pipeline.png?w=550 550w, /media/docs/fleet-management/screenshot-fleet-management-terraform-validate-pipeline.png?w=750 750w, /media/docs/fleet-management/screenshot-fleet-management-terraform-validate-pipeline.png?w=900 900w, /media/docs/fleet-management/screenshot-fleet-management-terraform-validate-pipeline.png?w=1040 1040w, /media/docs/fleet-management/screenshot-fleet-management-terraform-validate-pipeline.png?w=1240 1240w, /media/docs/fleet-management/screenshot-fleet-management-terraform-validate-pipeline.png?w=1920 1920w&#34;data-sizes=&#34;auto&#34;alt=&#34;The Remote configuration screen in the Fleet Management interface in Grafana Cloud which shows that a new configuration pipeline called `profiling` is active and was last modified a few seconds ago.&#34;width=&#34;2228&#34;height=&#34;904&#34;/&gt;
          &lt;noscript&gt;
            &lt;img
              src=&#34;/media/docs/fleet-management/screenshot-fleet-management-terraform-validate-pipeline.png&#34;
              alt=&#34;The Remote configuration screen in the Fleet Management interface in Grafana Cloud which shows that a new configuration pipeline called `profiling` is active and was last modified a few seconds ago.&#34;width=&#34;2228&#34;height=&#34;904&#34;/&gt;
          &lt;/noscript&gt;&lt;/div&gt;&lt;/a&gt;&lt;/figure&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Alloy profiles are being exported to Grafana Cloud Profiles:&lt;/p&gt;
&lt;figure
      class=&#34;figure-wrapper figure-wrapper__lightbox w-100p &#34;
      style=&#34;max-width: 2228px;&#34;
      itemprop=&#34;associatedMedia&#34;
      itemscope=&#34;&#34;
      itemtype=&#34;http://schema.org/ImageObject&#34;
    &gt;&lt;a
          class=&#34;lightbox-link&#34;
          href=&#34;/media/docs/fleet-management/screenshot-fleet-management-terraform-validate-profiles.png&#34;
          itemprop=&#34;contentUrl&#34;
        &gt;&lt;div class=&#34;img-wrapper w-100p h-auto&#34;&gt;&lt;img
            class=&#34;lazyload &#34;
            data-src=&#34;/media/docs/fleet-management/screenshot-fleet-management-terraform-validate-profiles.png&#34;data-srcset=&#34;/media/docs/fleet-management/screenshot-fleet-management-terraform-validate-profiles.png?w=320 320w, /media/docs/fleet-management/screenshot-fleet-management-terraform-validate-profiles.png?w=550 550w, /media/docs/fleet-management/screenshot-fleet-management-terraform-validate-profiles.png?w=750 750w, /media/docs/fleet-management/screenshot-fleet-management-terraform-validate-profiles.png?w=900 900w, /media/docs/fleet-management/screenshot-fleet-management-terraform-validate-profiles.png?w=1040 1040w, /media/docs/fleet-management/screenshot-fleet-management-terraform-validate-profiles.png?w=1240 1240w, /media/docs/fleet-management/screenshot-fleet-management-terraform-validate-profiles.png?w=1920 1920w&#34;data-sizes=&#34;auto&#34;alt=&#34;A dashboard in Grafana Cloud which shows Alloy profiling data, including graphs for CPU and memory.&#34;width=&#34;2228&#34;height=&#34;1406&#34;/&gt;
          &lt;noscript&gt;
            &lt;img
              src=&#34;/media/docs/fleet-management/screenshot-fleet-management-terraform-validate-profiles.png&#34;
              alt=&#34;A dashboard in Grafana Cloud which shows Alloy profiling data, including graphs for CPU and memory.&#34;width=&#34;2228&#34;height=&#34;1406&#34;/&gt;
          &lt;/noscript&gt;&lt;/div&gt;&lt;/a&gt;&lt;/figure&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id=&#34;summary&#34;&gt;Summary&lt;/h2&gt;
&lt;p&gt;In this guide, you created an access policy and a token for Fleet Management and Alloy, a collector with remote attributes, and a pipeline for profiling Alloy, all using Terraform.&lt;/p&gt;
&lt;p&gt;To learn more about managing Grafana Cloud using Terraform, refer to the &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;Grafana provider documentation&lt;/a&gt;.&lt;/p&gt;
]]></content><description>&lt;h1 id="manage-fleet-management-in-grafana-cloud-using-terraform">Manage Fleet Management in Grafana Cloud using Terraform&lt;/h1>
&lt;p>Learn how to create &lt;a href="/docs/grafana-cloud/send-data/fleet-management/">Grafana Fleet Management&lt;/a> collectors and pipelines in Grafana Cloud using Terraform.
This guide shows you how to create an access policy and a token for Fleet Management and &lt;a href="/docs/alloy/latest/">Grafana Alloy&lt;/a>, a collector with remote attributes, and a pipeline for profiling Alloy.&lt;/p></description></item><item><title>Manage Frontend Observability in Grafana Cloud with Terraform</title><link>https://grafana.com/docs/grafana/v12.4/as-code/infrastructure-as-code/terraform/terraform-frontend-observability/</link><pubDate>Fri, 03 Apr 2026 12:35:46 -0500</pubDate><guid>https://grafana.com/docs/grafana/v12.4/as-code/infrastructure-as-code/terraform/terraform-frontend-observability/</guid><content><![CDATA[&lt;h1 id=&#34;manage-frontend-observability-in-grafana-cloud-with-terraform&#34;&gt;Manage Frontend Observability in Grafana Cloud with Terraform&lt;/h1&gt;
&lt;p&gt;Learn how to use Terraform to manage &lt;a href=&#34;/docs/grafana-cloud/frontend-observability/&#34;&gt;Grafana Frontend Observability&lt;/a&gt; resources, such as your applications.
This guide shows you how to create an access policy and a token for Frontend Observability so that you can connect to the Frontend Observability API.&lt;/p&gt;
&lt;h2 id=&#34;before-you-begin&#34;&gt;Before you begin&lt;/h2&gt;
&lt;p&gt;Before you begin, ensure you have the following:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;A Grafana Cloud account, as shown in &lt;a href=&#34;/docs/grafana-cloud/get-started/&#34;&gt;Get started&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;https://www.terraform.io/downloads&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;Terraform&lt;/a&gt; installed on your machine&lt;/li&gt;
&lt;li&gt;Administrator permissions in your Grafana instance&lt;/li&gt;
&lt;/ul&gt;


&lt;div class=&#34;admonition admonition-note&#34;&gt;&lt;blockquote&gt;&lt;p class=&#34;title text-uppercase&#34;&gt;Note&lt;/p&gt;&lt;p&gt;All of the following Terraform configuration files should be saved in the same directory.&lt;/p&gt;&lt;/blockquote&gt;&lt;/div&gt;

&lt;h2 id=&#34;configure-a-provider-for-grafana-cloud&#34;&gt;Configure a provider for Grafana Cloud&lt;/h2&gt;
&lt;p&gt;This Terraform configuration configures the &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;Grafana provider&lt;/a&gt; to provide necessary authentication when interacting with the Cloud API.
The &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs/data-sources/cloud_stack&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;&lt;code&gt;grafana_cloud_stack&lt;/code&gt; (Data Source)&lt;/a&gt; is used to retrieve the details of your instance.&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;Create a Grafana Cloud access policy and token.
To create a new one, refer to &lt;a href=&#34;/docs/grafana-cloud/security-and-account-management/authentication-and-permissions/access-policies/&#34;&gt;Grafana Cloud Access Policies&lt;/a&gt;.
Add your stack to the realms list.
The scopes needed for the examples in this guide are:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;accesspolicies:read&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;accesspolicies:write&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;accesspolicies:delete&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;dashboards:read&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;dashboards:write&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;dashboards:delete&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;orgs:read&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;orgs:write&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;stacks:read&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;stacks:write&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;stacks:delete&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;stack-dashboards:read&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;stack-dashboards:write&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;stack-dashboards:delete&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;stack-service-accounts:write&lt;/code&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Create a file named &lt;code&gt;cloud-provider.tf&lt;/code&gt; and add the following code block:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;terraform&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-terraform&#34;&gt;terraform {
  required_providers {
    grafana = {
      source  = &amp;#34;grafana/grafana&amp;#34;
    }
  }
}

provider &amp;#34;grafana&amp;#34; {
  alias = &amp;#34;cloud&amp;#34;

  cloud_access_policy_token = &amp;#34;&amp;lt;CLOUD_ACCESS_POLICY_TOKEN&amp;gt;&amp;#34;
}

data &amp;#34;grafana_cloud_stack&amp;#34; &amp;#34;stack&amp;#34; {
  provider = grafana.cloud

  slug = &amp;#34;&amp;lt;STACK_SLUG&amp;gt;&amp;#34;
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Replace the following field values:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;&amp;lt;CLOUD_ACCESS_POLICY_TOKEN&amp;gt;&lt;/code&gt; with the access policy token you created in the first step&lt;/li&gt;
&lt;li&gt;&lt;code&gt;&amp;lt;STACK_SLUG&amp;gt;&lt;/code&gt; with your stack slug, which is the subdomain where your Grafana Cloud instance is available: &lt;code&gt;https://&amp;lt;STACK_SLUG&amp;gt;.grafana.net&lt;/code&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;h2 id=&#34;create-an-access-policy-and-token-for-frontend-observability&#34;&gt;Create an access policy and token for Frontend Observability&lt;/h2&gt;
&lt;p&gt;You must create a Terraform configuration with the following:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;An access policy with &lt;code&gt;frontend-observability:read&lt;/code&gt;, &lt;code&gt;frontend-observability:write&lt;/code&gt;, and &lt;code&gt;frontend-observability:delete&lt;/code&gt; scopes, using &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs/resources/cloud_access_policy&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;&lt;code&gt;grafana_cloud_access_policy&lt;/code&gt; (Resource)&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;A token named &lt;code&gt;frontend_o11y_api_access_token&lt;/code&gt;, using &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs/resources/cloud_access_policy_token&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;&lt;code&gt;grafana_cloud_access_policy_token&lt;/code&gt; (Resource)&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id=&#34;configure-the-provider-to-use-the-frontend-observability-api&#34;&gt;Configure the provider to use the Frontend Observability API&lt;/h2&gt;
&lt;p&gt;After you have created the token, you can configure the provider as follows:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;terraform&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-terraform&#34;&gt;provider &amp;#34;grafana&amp;#34; {
  frontend_o11y_api_access_token = &amp;#34;&amp;lt;access token from previous step&amp;gt;&amp;#34;
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;h2 id=&#34;summary&#34;&gt;Summary&lt;/h2&gt;
&lt;p&gt;In this guide, you created an access policy and a token for Frontend Observability using Terraform.&lt;/p&gt;
&lt;p&gt;To learn more about managing Grafana Cloud using Terraform, refer to the &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;Grafana provider documentation&lt;/a&gt;.&lt;/p&gt;
]]></content><description>&lt;h1 id="manage-frontend-observability-in-grafana-cloud-with-terraform">Manage Frontend Observability in Grafana Cloud with Terraform&lt;/h1>
&lt;p>Learn how to use Terraform to manage &lt;a href="/docs/grafana-cloud/frontend-observability/">Grafana Frontend Observability&lt;/a> resources, such as your applications.
This guide shows you how to create an access policy and a token for Frontend Observability so that you can connect to the Frontend Observability API.&lt;/p></description></item><item><title>Manage Cloud Provider Observability in Grafana Cloud using Terraform</title><link>https://grafana.com/docs/grafana/v12.4/as-code/infrastructure-as-code/terraform/terraform-cloud-provider-o11y/</link><pubDate>Fri, 03 Apr 2026 12:35:46 -0500</pubDate><guid>https://grafana.com/docs/grafana/v12.4/as-code/infrastructure-as-code/terraform/terraform-cloud-provider-o11y/</guid><content><![CDATA[&lt;h1 id=&#34;manage-cloud-provider-observability-in-grafana-cloud-using-terraform&#34;&gt;Manage Cloud Provider Observability in Grafana Cloud using Terraform&lt;/h1&gt;
&lt;p&gt;Manage Cloud Provider Observability, including Amazon CloudWatch and Microsoft Azure resources, in Grafana Cloud using Terraform.
For more information on Cloud Provider Observability, refer to the &lt;a href=&#34;/docs/grafana-cloud/monitor-infrastructure/monitor-cloud-provider/&#34;&gt;Cloud Provider Observability&lt;/a&gt; documentation.&lt;/p&gt;
&lt;h2 id=&#34;before-you-begin&#34;&gt;Before you begin&lt;/h2&gt;
&lt;p&gt;Before you begin, ensure you have the following:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;A Grafana Cloud account
&lt;ul&gt;
&lt;li&gt;For more information on setting up a Grafana Cloud account, refer to &lt;a href=&#34;/docs/grafana-cloud/get-started/&#34;&gt;Get started&lt;/a&gt;.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;Terraform installed on your machine
&lt;ul&gt;
&lt;li&gt;For more information on how to install Terraform, refer to the &lt;a href=&#34;https://developer.hashicorp.com/terraform/install&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;Terraform install documentation&lt;/a&gt;.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;Administrator permissions in your Grafana instance
&lt;ul&gt;
&lt;li&gt;For more information on assigning Grafana RBAC roles, refer to &lt;a href=&#34;/docs/grafana-cloud/security-and-account-management/authentication-and-permissions/access-control/assign-rbac-roles/&#34;&gt;Assign RBAC roles&lt;/a&gt;.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;


&lt;div class=&#34;admonition admonition-note&#34;&gt;&lt;blockquote&gt;&lt;p class=&#34;title text-uppercase&#34;&gt;Note&lt;/p&gt;&lt;p&gt;Save all of the following Terraform configuration files in the same directory.&lt;/p&gt;&lt;/blockquote&gt;&lt;/div&gt;

&lt;h2 id=&#34;configure-authentication-for-the-grafana-provider&#34;&gt;Configure authentication for the Grafana Provider&lt;/h2&gt;
&lt;p&gt;The Grafana Provider is a logical abstraction of an upstream API that you can use to interact with Grafana Cloud resources.
You must configure it with the following information:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;A Grafana Cloud access policy token that includes the permissions the provider needs to access the Grafana Cloud Provider API.&lt;/li&gt;
&lt;li&gt;A regional cloud provider API endpoint to establish which Grafana Cloud stack you are accessing.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;To configure authentication for the Grafana Provider:&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;Create a Grafana Cloud access policy and token.&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;To create an access policy for your organization, refer to the &lt;a href=&#34;/docs/grafana-cloud/security-and-account-management/authentication-and-permissions/access-policies/create-access-policies/#create-an-access-policy-for-a-stack&#34;&gt;Create an access policy for a stack steps&lt;/a&gt; and use the following scopes listed for the supported Amazon CloudWatch or Microsoft Azure resources:
&lt;ul&gt;
&lt;li&gt;Amazon CloudWatch
&lt;ul&gt;
&lt;li&gt;Metrics scrape or resource metadata scrape
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;integration-management:read&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;integration-management:write&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;stacks:read&lt;/code&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;Metric streams
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;metrics:write&lt;/code&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;ALB access logs, logs with Lambda, or logs with Amazon Data Firehose
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;logs:write&lt;/code&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;Microsoft Azure
&lt;ul&gt;
&lt;li&gt;Serverless metrics
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;integration-management:read&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;integration-management:write&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;stacks:read&lt;/code&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;Logs with Azure functions
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;logs:write&lt;/code&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Obtain the regional Cloud Provider API endpoint.&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;To obtain the regional Cloud provider API endpoint, use your access policy token and the following command to return a list of all of the Grafana stacks you own, along with their respective Cloud Provider API hostnames:&lt;/li&gt;
&lt;/ul&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;Bash&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-bash&#34;&gt;curl -sH &amp;#34;Authorization: Bearer &amp;lt;Access Token from previous step&amp;gt;&amp;#34; &amp;#34;https://grafana.com/api/instances&amp;#34; | \
jq &amp;#39;[.items[]|{stackName: .slug, clusterName:.clusterSlug, cloudProviderAPIURL: &amp;#34;https://cloud-provider-api-\(.clusterSlug).grafana.net&amp;#34;}]&amp;#39;&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Create a file named &lt;code&gt;cloud-provider.tf&lt;/code&gt; and add the following code block:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;tf&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-tf&#34;&gt;terraform {
    required_providers {
    grafana = {
        source  = &amp;#34;grafana/grafana&amp;#34;
    }
  }
}

provider &amp;#34;grafana&amp;#34; {
    cloud_api_url      = &amp;#34;&amp;lt;CLOUD_PROVIDER_API_URL&amp;gt;&amp;#34;
    cloud_access_policy_token     = &amp;#34;&amp;lt;CLOUD_ACCESS_POLICY_TOKEN&amp;gt;&amp;#34;
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Create a &lt;code&gt;variables.tf&lt;/code&gt; file and paste the &lt;code&gt;&amp;lt;CLOUD_ACCESS_POLICY_TOKEN&amp;gt;&lt;/code&gt; and &lt;code&gt;&amp;lt;CLOUD_PROVIDER_API_URL&lt;/code&gt; variables with your values.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Run the following Terraform command:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;tf&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-tf&#34;&gt;terraform apply -var-file=&amp;#34;variables.tf&amp;#34;&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;h2 id=&#34;configure-your-resources&#34;&gt;Configure your resources&lt;/h2&gt;
&lt;p&gt;To find instructions for configuring specific Amazon CloudWatch and Microsoft Azure resources in Cloud Provider Observability using Terraform, refer to the following documents:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Amazon CloudWatch
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;/docs/grafana-cloud/monitor-infrastructure/monitor-cloud-provider/aws/cloudwatch-metrics/config-cw-metric-scrape/&#34;&gt;Metrics scrape&lt;/a&gt;: Pull CloudWatch metrics from multiple regions for your AWS account, without needing to install Grafana Alloy.&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;/docs/grafana-cloud/monitor-infrastructure/monitor-cloud-provider/aws/cloudwatch-metrics/config-cw-metric-streams/#configure-metric-streams-with-terraform&#34;&gt;Metric streams&lt;/a&gt;: Push metrics with CloudWatch metric streams using Amazon Data Firehose, providing real-time insights and scalability while simplifying configuration and reducing cost and manual effort.&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;/docs/grafana-cloud/monitor-infrastructure/monitor-cloud-provider/aws/logs/cloudwatch-logs/config-alb-access-logs-lambda/#configure-with-terraform&#34;&gt;ALB access logs&lt;/a&gt;: Send application load balancer access logs from AWS to Grafana Cloud using a Lambda function.&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;/docs/grafana-cloud/monitor-infrastructure/monitor-cloud-provider/aws/logs/cloudwatch-logs/config-cw-logs-lambda/#configure-with-terraform&#34;&gt;Logs with Lambda&lt;/a&gt;: Send logs to Grafana Cloud from multiple AWS services using a lambda-promtail function.&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;/docs/grafana-cloud/monitor-infrastructure/monitor-cloud-provider/aws/logs/firehose-logs/config-firehose-logs/#configure-with-terraform&#34;&gt;Logs with Amazon Data Firehose&lt;/a&gt;: Send logs from AWS to Grafana Cloud with Amazon Data Firehose and minimal infrastructure.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;li&gt;Microsoft Azure
&lt;ul&gt;
&lt;li&gt;&lt;a href=&#34;/docs/grafana-cloud/monitor-infrastructure/monitor-cloud-provider/azure/collect-azure-serverless/config-azure-metrics-serverless/&#34;&gt;Serverless metrics&lt;/a&gt;: Monitor your Azure resources without the need to configure or deploy a collector by using Cloud Provider Observability.&lt;/li&gt;
&lt;li&gt;&lt;a href=&#34;/docs/grafana-cloud/monitor-infrastructure/monitor-cloud-provider/azure/config-azure-logs-azure-function/&#34;&gt;Logs with Azure functions&lt;/a&gt;: Send Azure event logs to a Loki endpoint using an Azure function that subscribes to an Azure event hub.&lt;/li&gt;
&lt;/ul&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id=&#34;grafana-cloud-provider-resources&#34;&gt;Grafana cloud provider resources&lt;/h2&gt;
&lt;p&gt;You can define the following Cloud Provider Observability resources and data sources using Terraform:&lt;/p&gt;
&lt;section class=&#34;expand-table-wrapper&#34;&gt;&lt;div class=&#34;button-div&#34;&gt;
      &lt;button class=&#34;expand-table-btn&#34;&gt;Expand table&lt;/button&gt;
    &lt;/div&gt;&lt;div class=&#34;responsive-table-wrapper&#34;&gt;
    &lt;table&gt;
      &lt;thead&gt;
          &lt;tr&gt;
              &lt;th&gt;Resource name&lt;/th&gt;
              &lt;th&gt;Description&lt;/th&gt;
          &lt;/tr&gt;
      &lt;/thead&gt;
      &lt;tbody&gt;
          &lt;tr&gt;
              &lt;td&gt;&lt;code&gt;grafana_cloud_provider_aws_account&lt;/code&gt;&lt;/td&gt;
              &lt;td&gt;Represents an AWS IAM role that authorizes Grafana Cloud to pull Amazon CloudWatch metrics for a set of regions. Usually, there&amp;rsquo;s one of these resources per configured AWS account. For a full reference of this resource, refer to the &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs/resources/cloud_provider_aws_account&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;Terraform Grafana Provider reference documentation&lt;/a&gt;.&lt;/td&gt;
          &lt;/tr&gt;
          &lt;tr&gt;
              &lt;td&gt;&lt;code&gt;grafana_cloud_provider_aws_cloudwatch_scrape_job&lt;/code&gt;&lt;/td&gt;
              &lt;td&gt;Represents a Grafana AWS scrape job. This configures Grafana to fetch a list of metrics and statistics for one or many AWS services, and for a given &lt;code&gt;grafana_cloud_provider_aws_account&lt;/code&gt;. For a full reference of this resource, refer to the &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs/resources/cloud_provider_aws_cloudwatch_scrape_job&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;Terraform Grafana Provider reference documentation&lt;/a&gt;.&lt;/td&gt;
          &lt;/tr&gt;
          &lt;tr&gt;
              &lt;td&gt;&lt;code&gt;grafana_cloud_provider_aws_resource_metadata_scrape_job&lt;/code&gt;&lt;/td&gt;
              &lt;td&gt;Represents a Grafana AWS Resource Metadata scrape job. This resource configures Grafana to fetch resource metadata for one or multiple AWS services, for a given &lt;code&gt;grafana_cloud_provider_aws_account&lt;/code&gt;. For a full reference of this resource, refer to the &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs/resources/cloud_provider_aws_resource_metadata_scrape_job&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;Terraform Grafana Provider reference documentation&lt;/a&gt;.&lt;/td&gt;
          &lt;/tr&gt;
          &lt;tr&gt;
              &lt;td&gt;&lt;code&gt;grafana_cloud_provider_azure_credential&lt;/code&gt;&lt;/td&gt;
              &lt;td&gt;A resource representing an Azure Service Principal credential used by Grafana Cloud to pull Azure Monitor metrics from one or more subscriptions. For a full reference of this resource, refer to the &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs/resources/cloud_provider_azure_credential&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;Terraform Grafana Provider resource documentation&lt;/a&gt;.&lt;/td&gt;
          &lt;/tr&gt;
      &lt;/tbody&gt;
    &lt;/table&gt;
  &lt;/div&gt;
&lt;/section&gt;]]></content><description>&lt;h1 id="manage-cloud-provider-observability-in-grafana-cloud-using-terraform">Manage Cloud Provider Observability in Grafana Cloud using Terraform&lt;/h1>
&lt;p>Manage Cloud Provider Observability, including Amazon CloudWatch and Microsoft Azure resources, in Grafana Cloud using Terraform.
For more information on Cloud Provider Observability, refer to the &lt;a href="/docs/grafana-cloud/monitor-infrastructure/monitor-cloud-provider/">Cloud Provider Observability&lt;/a> documentation.&lt;/p></description></item><item><title>Install plugins in Grafana Cloud using Terraform</title><link>https://grafana.com/docs/grafana/v12.4/as-code/infrastructure-as-code/terraform/terraform-plugins/</link><pubDate>Fri, 03 Apr 2026 12:35:46 -0500</pubDate><guid>https://grafana.com/docs/grafana/v12.4/as-code/infrastructure-as-code/terraform/terraform-plugins/</guid><content><![CDATA[&lt;h1 id=&#34;install-plugins-in-grafana-cloud-using-terraform&#34;&gt;Install plugins in Grafana Cloud using Terraform&lt;/h1&gt;
&lt;p&gt;This guide shows you how to install plugins in Grafana Cloud using Terraform. For more information about Grafana plugins, refer to the &lt;a href=&#34;/docs/grafana-cloud/introduction/find-and-use-plugins/&#34;&gt;Find and use Grafana plugins&lt;/a&gt; documentation.&lt;/p&gt;
&lt;h2 id=&#34;before-you-begin&#34;&gt;Before you begin&lt;/h2&gt;
&lt;p&gt;Before you begin, ensure you have the following:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;A Grafana Cloud account; for more information on setting up a Grafana Cloud account, refer to &lt;a href=&#34;/docs/grafana-cloud/get-started/&#34;&gt;Get started&lt;/a&gt;.&lt;/li&gt;
&lt;li&gt;Terraform installed on your machine; for more information on how to install Terraform, refer to the &lt;a href=&#34;https://developer.hashicorp.com/terraform/install&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;Terraform install documentation&lt;/a&gt;.&lt;/li&gt;
&lt;li&gt;Administrator permissions in your Grafana instance; for more information on assigning Grafana RBAC roles, refer to &lt;a href=&#34;/docs/grafana-cloud/security-and-account-management/authentication-and-permissions/access-control/assign-rbac-roles/&#34;&gt;Assign RBAC roles&lt;/a&gt;.&lt;/li&gt;
&lt;/ul&gt;


&lt;div class=&#34;admonition admonition-note&#34;&gt;&lt;blockquote&gt;&lt;p class=&#34;title text-uppercase&#34;&gt;Note&lt;/p&gt;&lt;p&gt;Save all of the following Terraform configuration files in the same directory.&lt;/p&gt;&lt;/blockquote&gt;&lt;/div&gt;

&lt;h2 id=&#34;configure-the-grafana-provider&#34;&gt;Configure the Grafana provider&lt;/h2&gt;
&lt;p&gt;Use this Terraform configuration to set up the &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;Grafana provider&lt;/a&gt; to provide the authentication required to manage plugin resources.&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;
&lt;p&gt;Create a service account and token in Grafana. For more information on creating a service account and token, refer to &lt;a href=&#34;/docs/grafana/latest/administration/service-accounts/#service-account-tokens&#34;&gt;Service account tokens&lt;/a&gt;. You can also refer to &lt;a href=&#34;../terraform-cloud-stack/&#34;&gt;Creating and managing a Grafana Cloud stack using Terraform&lt;/a&gt; to set up a service account and a token.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;Make sure that the token has the following permissions:&lt;/p&gt;
&lt;/li&gt;
&lt;/ol&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;stack-plugins:read&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;stack-plugins:write&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;stack-plugins:delete&lt;/code&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Next, create a file named &lt;code&gt;main.tf&lt;/code&gt; and add the following:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;terraform&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-terraform&#34;&gt;   terraform {
     required_providers {
       grafana = {
         source  = &amp;#34;grafana/grafana&amp;#34;
         version = &amp;#34;&amp;gt;= 4.5.3&amp;#34;
       }
     }
   }

   provider &amp;#34;grafana&amp;#34; {
     cloud_api_url      = &amp;#34;&amp;lt;Stack-URL&amp;gt;&amp;#34;
     cloud_access_policy_token     = &amp;#34;&amp;lt;Service-account-token&amp;gt;&amp;#34;
   }&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;Replace the following field values:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;code&gt;Stack-URL&lt;/code&gt; with the URL of your Grafana stack, for example &lt;code&gt;https://my-stack.grafana.net/&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;&lt;code&gt;Service-account-token&lt;/code&gt; with the service account token that you created&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id=&#34;create-new-plugin-resource&#34;&gt;Create new plugin resource&lt;/h2&gt;
&lt;p&gt;Create a file named &lt;code&gt;plugins.tf&lt;/code&gt; and add the following:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;terraform&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-terraform&#34;&gt;resource &amp;#34;grafana_cloud_plugin_installation&amp;#34; &amp;#34;grafana-clock-panel&amp;#34; {
  stack_slug   = &amp;#34;&amp;lt;Your-Stack-Slug&amp;gt;&amp;#34;
  slug         = &amp;#34;grafana-clock-panel&amp;#34;
  version      = &amp;#34;latest&amp;#34;
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;h2 id=&#34;summary&#34;&gt;Summary&lt;/h2&gt;
&lt;p&gt;In this guide, you learned how to install a plugin in Grafana Cloud using Terraform.&lt;/p&gt;
&lt;p&gt;To learn more about plugin installation, refer to the &lt;a href=&#34;https://registry.terraform.io/providers/grafana/grafana/latest/docs/resources/cloud_plugin_installation&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;Grafana provider documentation&lt;/a&gt;.&lt;/p&gt;
]]></content><description>&lt;h1 id="install-plugins-in-grafana-cloud-using-terraform">Install plugins in Grafana Cloud using Terraform&lt;/h1>
&lt;p>This guide shows you how to install plugins in Grafana Cloud using Terraform. For more information about Grafana plugins, refer to the &lt;a href="/docs/grafana-cloud/introduction/find-and-use-plugins/">Find and use Grafana plugins&lt;/a> documentation.&lt;/p></description></item></channel></rss>