github.com/opentofu/opentofu@v1.7.1/internal/tofu/transform_targets_test.go (about)

     1  // Copyright (c) The OpenTofu Authors
     2  // SPDX-License-Identifier: MPL-2.0
     3  // Copyright (c) 2023 HashiCorp, Inc.
     4  // SPDX-License-Identifier: MPL-2.0
     5  
     6  package tofu
     7  
     8  import (
     9  	"strings"
    10  	"testing"
    11  
    12  	"github.com/opentofu/opentofu/internal/addrs"
    13  )
    14  
    15  func TestTargetsTransformer(t *testing.T) {
    16  	mod := testModule(t, "transform-targets-basic")
    17  
    18  	g := Graph{Path: addrs.RootModuleInstance}
    19  	{
    20  		tf := &ConfigTransformer{Config: mod}
    21  		if err := tf.Transform(&g); err != nil {
    22  			t.Fatalf("err: %s", err)
    23  		}
    24  	}
    25  
    26  	{
    27  		transform := &AttachResourceConfigTransformer{Config: mod}
    28  		if err := transform.Transform(&g); err != nil {
    29  			t.Fatalf("err: %s", err)
    30  		}
    31  	}
    32  
    33  	{
    34  		transform := &ReferenceTransformer{}
    35  		if err := transform.Transform(&g); err != nil {
    36  			t.Fatalf("err: %s", err)
    37  		}
    38  	}
    39  
    40  	{
    41  		transform := &TargetsTransformer{
    42  			Targets: []addrs.Targetable{
    43  				addrs.RootModuleInstance.Resource(
    44  					addrs.ManagedResourceMode, "aws_instance", "me",
    45  				),
    46  			},
    47  		}
    48  		if err := transform.Transform(&g); err != nil {
    49  			t.Fatalf("err: %s", err)
    50  		}
    51  	}
    52  
    53  	actual := strings.TrimSpace(g.String())
    54  	expected := strings.TrimSpace(`
    55  aws_instance.me
    56    aws_subnet.me
    57  aws_subnet.me
    58    aws_vpc.me
    59  aws_vpc.me
    60  	`)
    61  	if actual != expected {
    62  		t.Fatalf("bad:\n\nexpected:\n%s\n\ngot:\n%s\n", expected, actual)
    63  	}
    64  }
    65  
    66  func TestTargetsTransformer_downstream(t *testing.T) {
    67  	mod := testModule(t, "transform-targets-downstream")
    68  
    69  	g := Graph{Path: addrs.RootModuleInstance}
    70  	{
    71  		transform := &ConfigTransformer{Config: mod}
    72  		if err := transform.Transform(&g); err != nil {
    73  			t.Fatalf("%T failed: %s", transform, err)
    74  		}
    75  	}
    76  
    77  	{
    78  		transform := &AttachResourceConfigTransformer{Config: mod}
    79  		if err := transform.Transform(&g); err != nil {
    80  			t.Fatalf("%T failed: %s", transform, err)
    81  		}
    82  	}
    83  
    84  	{
    85  		transform := &AttachResourceConfigTransformer{Config: mod}
    86  		if err := transform.Transform(&g); err != nil {
    87  			t.Fatalf("%T failed: %s", transform, err)
    88  		}
    89  	}
    90  
    91  	{
    92  		transform := &OutputTransformer{Config: mod}
    93  		if err := transform.Transform(&g); err != nil {
    94  			t.Fatalf("%T failed: %s", transform, err)
    95  		}
    96  	}
    97  
    98  	{
    99  		transform := &ReferenceTransformer{}
   100  		if err := transform.Transform(&g); err != nil {
   101  			t.Fatalf("err: %s", err)
   102  		}
   103  	}
   104  
   105  	{
   106  		transform := &TargetsTransformer{
   107  			Targets: []addrs.Targetable{
   108  				addrs.RootModuleInstance.
   109  					Child("child", addrs.NoKey).
   110  					Child("grandchild", addrs.NoKey).
   111  					Resource(
   112  						addrs.ManagedResourceMode, "aws_instance", "foo",
   113  					),
   114  			},
   115  		}
   116  		if err := transform.Transform(&g); err != nil {
   117  			t.Fatalf("%T failed: %s", transform, err)
   118  		}
   119  	}
   120  
   121  	actual := strings.TrimSpace(g.String())
   122  	// Even though we only asked to target the grandchild resource, all of the
   123  	// outputs that descend from it are also targeted.
   124  	expected := strings.TrimSpace(`
   125  module.child.module.grandchild.aws_instance.foo
   126  module.child.module.grandchild.output.id (expand)
   127    module.child.module.grandchild.aws_instance.foo
   128  module.child.output.grandchild_id (expand)
   129    module.child.module.grandchild.output.id (expand)
   130  output.grandchild_id (expand)
   131    module.child.output.grandchild_id (expand)
   132  	`)
   133  	if actual != expected {
   134  		t.Fatalf("bad:\n\nexpected:\n%s\n\ngot:\n%s\n", expected, actual)
   135  	}
   136  }
   137  
   138  // This tests the TargetsTransformer targeting a whole module,
   139  // rather than a resource within a module instance.
   140  func TestTargetsTransformer_wholeModule(t *testing.T) {
   141  	mod := testModule(t, "transform-targets-downstream")
   142  
   143  	g := Graph{Path: addrs.RootModuleInstance}
   144  	{
   145  		transform := &ConfigTransformer{Config: mod}
   146  		if err := transform.Transform(&g); err != nil {
   147  			t.Fatalf("%T failed: %s", transform, err)
   148  		}
   149  	}
   150  
   151  	{
   152  		transform := &AttachResourceConfigTransformer{Config: mod}
   153  		if err := transform.Transform(&g); err != nil {
   154  			t.Fatalf("%T failed: %s", transform, err)
   155  		}
   156  	}
   157  
   158  	{
   159  		transform := &AttachResourceConfigTransformer{Config: mod}
   160  		if err := transform.Transform(&g); err != nil {
   161  			t.Fatalf("%T failed: %s", transform, err)
   162  		}
   163  	}
   164  
   165  	{
   166  		transform := &OutputTransformer{Config: mod}
   167  		if err := transform.Transform(&g); err != nil {
   168  			t.Fatalf("%T failed: %s", transform, err)
   169  		}
   170  	}
   171  
   172  	{
   173  		transform := &ReferenceTransformer{}
   174  		if err := transform.Transform(&g); err != nil {
   175  			t.Fatalf("err: %s", err)
   176  		}
   177  	}
   178  
   179  	{
   180  		transform := &TargetsTransformer{
   181  			Targets: []addrs.Targetable{
   182  				addrs.RootModule.
   183  					Child("child").
   184  					Child("grandchild"),
   185  			},
   186  		}
   187  		if err := transform.Transform(&g); err != nil {
   188  			t.Fatalf("%T failed: %s", transform, err)
   189  		}
   190  	}
   191  
   192  	actual := strings.TrimSpace(g.String())
   193  	// Even though we only asked to target the grandchild module, all of the
   194  	// outputs that descend from it are also targeted.
   195  	expected := strings.TrimSpace(`
   196  module.child.module.grandchild.aws_instance.foo
   197  module.child.module.grandchild.output.id (expand)
   198    module.child.module.grandchild.aws_instance.foo
   199  module.child.output.grandchild_id (expand)
   200    module.child.module.grandchild.output.id (expand)
   201  output.grandchild_id (expand)
   202    module.child.output.grandchild_id (expand)
   203  	`)
   204  	if actual != expected {
   205  		t.Fatalf("bad:\n\nexpected:\n%s\n\ngot:\n%s\n", expected, actual)
   206  	}
   207  }