<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: Thierno BAH</title>
    <description>The latest articles on DEV Community by Thierno BAH (@soulbah).</description>
    <link>https://dev.to/soulbah</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F4181584%2F21a60096-4bf6-477f-a297-27e6414032f2.png</url>
      <title>DEV Community: Thierno BAH</title>
      <link>https://dev.to/soulbah</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/soulbah"/>
    <language>en</language>
    <item>
      <title>What does an arrow in a Terraform graph actually mean?</title>
      <dc:creator>Thierno BAH</dc:creator>
      <pubDate>Tue, 13 Oct 2026 15:40:46 +0000</pubDate>
      <link>https://dev.to/soulbah/what-does-an-arrow-in-a-terraform-graph-actually-mean-4o63</link>
      <guid>https://dev.to/soulbah/what-does-an-arrow-in-a-terraform-graph-actually-mean-4o63</guid>
      <description>&lt;p&gt;An S3 bucket can depend on a VPC in Terraform without being placed inside it. Put the VPC's ID in a bucket tag, and Terraform infers a dependency. Use the same ID in a subnet's &lt;code&gt;vpc_id&lt;/code&gt;, and Terraform infers another dependency. Only the second reference configures network placement.&lt;/p&gt;

&lt;p&gt;I built Rootform, which interprets Terraform and OpenTofu exports. This is one of the distinctions its architecture model needs to preserve.&lt;/p&gt;

&lt;h2&gt;
  
  
  Two references to the same VPC
&lt;/h2&gt;

&lt;p&gt;Here are the three resources. The complete provider setup is at the end.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight hcl"&gt;&lt;code&gt;&lt;span class="nx"&gt;resource&lt;/span&gt; &lt;span class="s2"&gt;"aws_vpc"&lt;/span&gt; &lt;span class="s2"&gt;"main"&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nx"&gt;cidr_block&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"10.20.0.0/16"&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="nx"&gt;resource&lt;/span&gt; &lt;span class="s2"&gt;"aws_subnet"&lt;/span&gt; &lt;span class="s2"&gt;"application"&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nx"&gt;vpc_id&lt;/span&gt;     &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;aws_vpc&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;main&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;id&lt;/span&gt;
  &lt;span class="nx"&gt;cidr_block&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"10.20.1.0/24"&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="nx"&gt;resource&lt;/span&gt; &lt;span class="s2"&gt;"aws_s3_bucket"&lt;/span&gt; &lt;span class="s2"&gt;"audit"&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nx"&gt;bucket_prefix&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"rootform-graph-example-"&lt;/span&gt;

  &lt;span class="nx"&gt;tags&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nx"&gt;NetworkId&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;aws_vpc&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;main&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;id&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Terraform &lt;a href="https://developer.hashicorp.com/terraform/language/expressions/references#named-values-and-dependencies" rel="noopener noreferrer"&gt;infers dependencies from resource references&lt;/a&gt;. The subnet's &lt;code&gt;vpc_id&lt;/code&gt; specifies &lt;a href="https://docs.aws.amazon.com/AWSEC2/latest/APIReference/API_CreateSubnet.html" rel="noopener noreferrer"&gt;its VPC&lt;/a&gt;, while the bucket's &lt;code&gt;tags&lt;/code&gt; map records &lt;a href="https://docs.aws.amazon.com/AmazonS3/latest/userguide/tagging.html#how-tags-work" rel="noopener noreferrer"&gt;metadata&lt;/a&gt;. The tag assignment does not configure a network path to the bucket.&lt;/p&gt;

&lt;p&gt;After initializing the complete example, generate the default dependency graph and render it with Graphviz:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;terraform graph &lt;span class="o"&gt;&amp;gt;&lt;/span&gt; dependencies.dot
dot &lt;span class="nt"&gt;-Tsvg&lt;/span&gt; dependencies.dot &lt;span class="nt"&gt;-o&lt;/span&gt; dependencies.svg
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Femtnwfcsdaba9svzcsb0.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Femtnwfcsdaba9svzcsb0.png" alt="Default Terraform dependency graph with arrows from aws_subnet.application and aws_s3_bucket.audit toward aws_vpc.main." width="800" height="259"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Default &lt;code&gt;terraform graph&lt;/code&gt; output with Terraform 1.12.2. Both arrows point to the referenced VPC.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Terraform &lt;a href="https://developer.hashicorp.com/terraform/cli/commands/graph#usage" rel="noopener noreferrer"&gt;describes this output&lt;/a&gt; as a simplified graph of resource dependency ordering. More detailed operation graphs are available with options such as &lt;code&gt;-type=plan&lt;/code&gt; and &lt;code&gt;-type=apply&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;The bucket's edge is legitimate: Terraform needs to track the value used in its tag. The graph does not claim that the bucket is inside the VPC. That meaning would be added by whoever interprets the edge as network placement.&lt;/p&gt;

&lt;p&gt;An explicit &lt;a href="https://developer.hashicorp.com/terraform/language/meta-arguments/depends_on" rel="noopener noreferrer"&gt;&lt;code&gt;depends_on&lt;/code&gt;&lt;/a&gt; also controls operation ordering. On its own, it does not describe a network connection.&lt;/p&gt;

&lt;p&gt;For an architecture view, the argument being set matters. Changing the bucket's &lt;code&gt;NetworkId&lt;/code&gt; tag and changing the subnet's &lt;code&gt;vpc_id&lt;/code&gt; describe different changes to the infrastructure, even when both reference a different VPC.&lt;/p&gt;

&lt;h2&gt;
  
  
  Follow a placement back to its evidence
&lt;/h2&gt;

&lt;p&gt;Rootform's AWS subnet Rule interprets &lt;code&gt;vpc_id&lt;/code&gt; as network placement. It records the target VPC and the evidence used to identify it. The output calls this placement a &lt;em&gt;network Context&lt;/em&gt;.&lt;/p&gt;

&lt;p&gt;For a new VPC, the ID can be unknown until apply. The plan JSON includes &lt;a href="https://developer.hashicorp.com/terraform/internals/json-format#expression-representation" rel="noopener noreferrer"&gt;expression references&lt;/a&gt;, but not the full expression tree. A list of references tells an analysis tool which objects an expression mentions, not exactly how it uses them.&lt;/p&gt;

&lt;p&gt;Rootform uses the configuration snapshot in a &lt;a href="https://github.com/rootform-dev/rootform/blob/37f8e564134689187b41581f9bf787d931930dcd/docs/inputs/plans.md#pair-the-saved-plan" rel="noopener noreferrer"&gt;matching saved plan&lt;/a&gt; to verify direct references such as &lt;code&gt;aws_vpc.main.id&lt;/code&gt;. This lets it identify the VPC while the evaluated ID is still unknown.&lt;/p&gt;

&lt;p&gt;Generate a saved plan, export that same plan, then inspect the subnet:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;terraform plan &lt;span class="nt"&gt;-refresh&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="nb"&gt;false&lt;/span&gt; &lt;span class="nt"&gt;-input&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="nb"&gt;false&lt;/span&gt; &lt;span class="nt"&gt;-out&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;plan.tfplan
terraform show &lt;span class="nt"&gt;-json&lt;/span&gt; plan.tfplan &lt;span class="o"&gt;&amp;gt;&lt;/span&gt; plan.json

rootform run plan.json &lt;span class="nt"&gt;--plan-file&lt;/span&gt; plan.tfplan &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;--require-enrichment&lt;/span&gt; &lt;span class="nt"&gt;--no-serve&lt;/span&gt; &lt;span class="nt"&gt;-o&lt;/span&gt; with-saved-plan.form.json

rootform explain instance aws_subnet.application &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;--input&lt;/span&gt; with-saved-plan.form.json
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Relevant excerpt from &lt;code&gt;rootform explain&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;aws_subnet.application
  Instance        managed instance of aws_subnet; planned (create)
  Provider        registry.terraform.io/hashicorp/aws
  Interpretation  applied aws.rule.subnet as subnet
  Conclusion      Interpreted as subnet by aws.rule.subnet: network context to
                  aws_vpc.main.

  Facts
    -&amp;gt; context network  aws_vpc.main  evidence: traversal

  Closures
    context network -&amp;gt; virtual-network
      via source.vpc_id, match exact by id
      resolved, 1 fact
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;a href="https://dev-to-uploads.s3.us-east-2.amazonaws.com/uploads/articles/q30gvk42619yfsvw1996.jpg" rel="noopener noreferrer"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fm6rx3ntdohdxy5eji0oe.jpg" alt="Rootform Explorer showing the application subnet's resolved placement in the main VPC, with the Rule and saved-plan traversal evidence." width="800" height="477"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;em&gt;The same saved Form in Rootform 0.3.0, with the subnet selected and its placement evidence open.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Now repeat the analysis without the saved plan:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;rootform run plan.json &lt;span class="nt"&gt;--no-serve&lt;/span&gt; &lt;span class="nt"&gt;-o&lt;/span&gt; without-saved-plan.form.json

rootform explain instance aws_subnet.application &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;--input&lt;/span&gt; without-saved-plan.form.json
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Using the same &lt;code&gt;plan.json&lt;/code&gt;, Rootform 0.3.0 produces:&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Input&lt;/th&gt;
&lt;th&gt;Subnet placement&lt;/th&gt;
&lt;th&gt;Target and evidence&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;JSON + paired saved plan&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;resolved&lt;/code&gt;, 1 fact&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;aws_vpc.main&lt;/code&gt;, &lt;code&gt;traversal&lt;/code&gt;
&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;JSON alone&lt;/td&gt;
&lt;td&gt;
&lt;code&gt;indeterminate&lt;/code&gt;, &lt;code&gt;unknown_until_apply&lt;/code&gt;
&lt;/td&gt;
&lt;td&gt;No established target or placement fact&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;In the JSON-only run, Rootform does not treat the reference list as proof of a direct identity reference. The placement stays indeterminate. That means the available evidence did not establish it, not that the subnet has no VPC.&lt;/p&gt;

&lt;p&gt;The bucket is also interpreted, by &lt;code&gt;aws.rule.s3-bucket&lt;/code&gt;. That Rule does not derive network placement from &lt;code&gt;tags.NetworkId&lt;/code&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  A delivery target changes
&lt;/h2&gt;

&lt;p&gt;In Rootform's synthetic Azure event-driven fixture, an Event Grid subscription changes its delivery target. To review it, we need to identify the new destination and see whether the source topic and previous queue remain in place.&lt;/p&gt;

&lt;p&gt;Selected fields from the head plan's &lt;code&gt;resource_changes&lt;/code&gt; entry:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"address"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"azurerm_eventgrid_event_subscription.claims_scored_review"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"change"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"actions"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"update"&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"after_unknown"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"service_bus_queue_id"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;true&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The plan proposes an in-place update, but the destination ID is unknown until apply. The saved configuration sets &lt;code&gt;service_bus_queue_id&lt;/code&gt; to &lt;code&gt;azurerm_servicebus_queue.claims_review_priority.id&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://dev-to-uploads.s3.us-east-2.amazonaws.com/uploads/articles/qa9rqroadjqynmezc83z.jpg" rel="noopener noreferrer"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2F54lkfpjj0pg1mcz6kelj.jpg" alt="Rootform Planned changes for claims_scored_review: delivery to claims_review removed, delivery to claims_review_priority added, and the claims_scored topic retained." width="800" height="465"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Planned changes (Refreshed → Planned): the old delivery relation is removed and the new one is added.&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;Rootform shows the &lt;code&gt;delivers-to&lt;/code&gt; relation changing from &lt;code&gt;claims_review&lt;/code&gt; to &lt;code&gt;claims_review_priority&lt;/code&gt;. The source topic remains &lt;code&gt;claims_scored&lt;/code&gt;, and the original queue is still present.&lt;/p&gt;

&lt;p&gt;Rule &lt;code&gt;azure.rule.event-grid-event-subscription&lt;/code&gt; resolves the destination through &lt;code&gt;source.service_bus_queue_id&lt;/code&gt;: an evaluated value before the change, and a verified saved-plan traversal after it.&lt;/p&gt;

&lt;p&gt;The subscription, both destinations and the unchanged topic are visible together, with the evidence behind the change available for inspection. These are planned delivery targets, not observed message traffic.&lt;/p&gt;

&lt;h2&gt;
  
  
  Reproduce the examples
&lt;/h2&gt;

&lt;p&gt;The VPC example is regenerated locally. The Azure example replays the &lt;a href="https://github.com/rootform-dev/rootform/blob/37f8e564134689187b41581f9bf787d931930dcd/examples/playground/event-driven-platform/README.md" rel="noopener noreferrer"&gt;version-pinned fixture&lt;/a&gt; with Rootform. Its supplied plan was generated against a synthetic existing state.&lt;/p&gt;

&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Example&lt;/th&gt;
&lt;th&gt;Terraform&lt;/th&gt;
&lt;th&gt;Provider&lt;/th&gt;
&lt;th&gt;Rootform&lt;/th&gt;
&lt;th&gt;Graphviz&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;VPC example, regenerated&lt;/td&gt;
&lt;td&gt;1.12.2&lt;/td&gt;
&lt;td&gt;AWS 6.62.0&lt;/td&gt;
&lt;td&gt;0.3.0&lt;/td&gt;
&lt;td&gt;12.2.1&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td&gt;Event-driven example, exports replayed&lt;/td&gt;
&lt;td&gt;1.16.4&lt;/td&gt;
&lt;td&gt;AzureRM 5.3.0&lt;/td&gt;
&lt;td&gt;0.3.0&lt;/td&gt;
&lt;td&gt;—&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;

&lt;p&gt;VPC example: provider setup and commands&lt;/p&gt;

&lt;p&gt;Create an empty directory and save the three resource blocks above in &lt;code&gt;main.tf&lt;/code&gt;. Add this configuration to the same file:&lt;/p&gt;
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight hcl"&gt;&lt;code&gt;&lt;span class="nx"&gt;terraform&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nx"&gt;required_version&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"= 1.12.2"&lt;/span&gt;

  &lt;span class="nx"&gt;required_providers&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nx"&gt;aws&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="nx"&gt;source&lt;/span&gt;  &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"hashicorp/aws"&lt;/span&gt;
      &lt;span class="nx"&gt;version&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"= 6.62.0"&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="nx"&gt;provider&lt;/span&gt; &lt;span class="s2"&gt;"aws"&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nx"&gt;region&lt;/span&gt;                      &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"us-east-1"&lt;/span&gt;
  &lt;span class="nx"&gt;access_key&lt;/span&gt;                  &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"example"&lt;/span&gt;
  &lt;span class="nx"&gt;secret_key&lt;/span&gt;                  &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="s2"&gt;"example"&lt;/span&gt;
  &lt;span class="nx"&gt;max_retries&lt;/span&gt;                 &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;
  &lt;span class="nx"&gt;skip_credentials_validation&lt;/span&gt; &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt;
  &lt;span class="nx"&gt;skip_metadata_api_check&lt;/span&gt;     &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt;
  &lt;span class="nx"&gt;skip_region_validation&lt;/span&gt;      &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt;
  &lt;span class="nx"&gt;skip_requesting_account_id&lt;/span&gt;  &lt;span class="p"&gt;=&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;
&lt;p&gt;With Terraform, Rootform and Graphviz installed, run:&lt;/p&gt;
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;terraform init &lt;span class="nt"&gt;-input&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="nb"&gt;false
&lt;/span&gt;terraform validate
terraform graph &amp;amp;gt&lt;span class="p"&gt;;&lt;/span&gt; dependencies.dot
dot &lt;span class="nt"&gt;-Tsvg&lt;/span&gt; dependencies.dot &lt;span class="nt"&gt;-o&lt;/span&gt; dependencies.svg
dot &lt;span class="nt"&gt;-Tpng&lt;/span&gt; &lt;span class="nt"&gt;-Gdpi&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;192 dependencies.dot &lt;span class="nt"&gt;-o&lt;/span&gt; dependencies.png

terraform plan &lt;span class="nt"&gt;-refresh&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="nb"&gt;false&lt;/span&gt; &lt;span class="nt"&gt;-input&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="nb"&gt;false&lt;/span&gt; &lt;span class="nt"&gt;-out&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;plan.tfplan
terraform show &lt;span class="nt"&gt;-json&lt;/span&gt; plan.tfplan &amp;amp;gt&lt;span class="p"&gt;;&lt;/span&gt; plan.json

rootform run plan.json &lt;span class="nt"&gt;--plan-file&lt;/span&gt; plan.tfplan &lt;span class="nt"&gt;--require-enrichment&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;--no-serve&lt;/span&gt; &lt;span class="nt"&gt;-o&lt;/span&gt; with-saved-plan.form.json &lt;span class="nt"&gt;-o&lt;/span&gt; architecture.html

rootform run plan.json &lt;span class="nt"&gt;--no-serve&lt;/span&gt; &lt;span class="nt"&gt;-o&lt;/span&gt; without-saved-plan.form.json
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;
&lt;p&gt;Open &lt;code&gt;architecture.html&lt;/code&gt; to explore the result. Use the &lt;code&gt;rootform explain&lt;/code&gt; commands above to inspect each Form.&lt;/p&gt;

&lt;p&gt;This example uses placeholder credentials and does not require an AWS account. &lt;code&gt;terraform init&lt;/code&gt; downloads the provider. Do not run &lt;code&gt;terraform apply&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;Azure example: replay the existing plan exports&lt;/p&gt;

&lt;p&gt;Retrieve the pinned Rootform revision and enter the fixture directory:&lt;/p&gt;
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git clone https://github.com/rootform-dev/rootform.git rootform-article-example
&lt;span class="nb"&gt;cd &lt;/span&gt;rootform-article-example
git checkout &lt;span class="nt"&gt;--detach&lt;/span&gt; 37f8e564134689187b41581f9bf787d931930dcd
&lt;span class="nb"&gt;cd &lt;/span&gt;examples/playground/event-driven-platform/head
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;
&lt;p&gt;Run Rootform against the supplied exports:&lt;/p&gt;
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;rootform run plan.json &lt;span class="nt"&gt;--plan-file&lt;/span&gt; plan.tfplan &lt;span class="nt"&gt;--require-enrichment&lt;/span&gt; &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;--no-serve&lt;/span&gt; &lt;span class="nt"&gt;-o&lt;/span&gt; analysis.form.json &lt;span class="nt"&gt;-o&lt;/span&gt; architecture.html

rootform explain instance azurerm_eventgrid_event_subscription.claims_scored_review &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;--input&lt;/span&gt; analysis.form.json &lt;span class="nt"&gt;--stage&lt;/span&gt; refreshed

rootform explain instance azurerm_eventgrid_event_subscription.claims_scored_review &lt;span class="se"&gt;\&lt;/span&gt;
  &lt;span class="nt"&gt;--input&lt;/span&gt; analysis.form.json &lt;span class="nt"&gt;--stage&lt;/span&gt; planned
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;
&lt;p&gt;Open &lt;code&gt;architecture.html&lt;/code&gt; and select &lt;strong&gt;Planned changes&lt;/strong&gt;. This uses the head plan's own Refreshed → Planned comparison, without running Terraform or the Azure provider.&lt;/p&gt;

&lt;p&gt;Real saved plans and JSON exports can contain cleartext secrets. Use synthetic inputs for public examples.&lt;/p&gt;

&lt;p&gt;The dependency graph remains useful for understanding Terraform's dependencies. An architecture view adds claims about what those dependencies mean.&lt;/p&gt;

&lt;p&gt;The subnet and the bucket both reference the VPC. Only one uses that reference to configure placement. Before relying on an architecture diagram in a review, I want to be able to trace that claim back to the argument and evidence behind it.&lt;/p&gt;

</description>
      <category>terraform</category>
      <category>devops</category>
      <category>architecture</category>
    </item>
  </channel>
</rss>
