github.com/mineiros-io/terradoc@v0.0.9-0.20220711062319-018bd4ae81f5/internal/parsers/hclparser/hcltype_test.go (about)

     1  package hclparser
     2  
     3  import (
     4  	"testing"
     5  
     6  	"github.com/hashicorp/hcl/v2"
     7  	"github.com/hashicorp/hcl/v2/hclsyntax"
     8  	"github.com/madlambda/spells/assert"
     9  	"github.com/mineiros-io/terradoc/internal/entities"
    10  	"github.com/mineiros-io/terradoc/internal/types"
    11  	"github.com/mineiros-io/terradoc/test"
    12  )
    13  
    14  var varTests = []struct {
    15  	expression string
    16  	want       entities.Type
    17  }{
    18  	{
    19  		expression: `list(my_object)`,
    20  		want: entities.Type{
    21  			TFType: types.TerraformList,
    22  			Nested: &entities.Type{
    23  				TFType: types.TerraformObject,
    24  				Label:  "my_object",
    25  			},
    26  		},
    27  	},
    28  	{
    29  		expression: `list(string)`,
    30  		want: entities.Type{
    31  			TFType: types.TerraformList,
    32  			Nested: &entities.Type{
    33  				TFType: types.TerraformString,
    34  			},
    35  		},
    36  	},
    37  	{
    38  		expression: `set(number)`,
    39  		want: entities.Type{
    40  			TFType: types.TerraformSet,
    41  			Nested: &entities.Type{
    42  				TFType: types.TerraformNumber,
    43  			},
    44  		},
    45  	},
    46  	{
    47  		expression: `list(number)`,
    48  		want: entities.Type{
    49  			TFType: types.TerraformList,
    50  			Nested: &entities.Type{
    51  				TFType: types.TerraformNumber,
    52  			},
    53  		},
    54  	},
    55  	{
    56  		expression: `list(another_object)`,
    57  		want: entities.Type{
    58  			TFType: types.TerraformList,
    59  			Nested: &entities.Type{
    60  				TFType: types.TerraformObject,
    61  				Label:  "another_object",
    62  			},
    63  		},
    64  	},
    65  	{
    66  		expression: `set(another_object)`,
    67  		want: entities.Type{
    68  			TFType: types.TerraformSet,
    69  			Nested: &entities.Type{
    70  				TFType: types.TerraformObject,
    71  				Label:  "another_object",
    72  			},
    73  		},
    74  	},
    75  	{
    76  		expression: `object(my_object_name)`,
    77  		want: entities.Type{
    78  			TFType: types.TerraformObject,
    79  			Label:  "my_object_name",
    80  		},
    81  	},
    82  	{
    83  		expression: `map(my_object_name)`,
    84  		want: entities.Type{
    85  			TFType: types.TerraformMap,
    86  			Nested: &entities.Type{
    87  				TFType: types.TerraformObject,
    88  				Label:  "my_object_name",
    89  			},
    90  		},
    91  	},
    92  	{
    93  		expression: `object(another_object_name)`,
    94  		want: entities.Type{
    95  			TFType: types.TerraformObject,
    96  			Label:  "another_object_name",
    97  		},
    98  	},
    99  	{
   100  		expression: `string`,
   101  		want: entities.Type{
   102  			TFType: types.TerraformString,
   103  		},
   104  	},
   105  	{
   106  		expression: `number`,
   107  		want: entities.Type{
   108  			TFType: types.TerraformNumber,
   109  		},
   110  	},
   111  	{
   112  		expression: `bool`,
   113  		want: entities.Type{
   114  			TFType: types.TerraformBool,
   115  		},
   116  	},
   117  }
   118  
   119  func TestGetVarTypeFromExpression(t *testing.T) {
   120  	for _, tt := range varTests {
   121  		t.Run(tt.expression, func(t *testing.T) {
   122  			t.Run("when expression is literal", func(t *testing.T) {
   123  				expr, parseDiags := hclsyntax.ParseExpression([]byte(tt.expression), "", hcl.Pos{Line: 1, Column: 1, Byte: 0})
   124  				if parseDiags.HasErrors() {
   125  					t.Errorf("Error parsing expression: %v", parseDiags.Errs())
   126  				}
   127  
   128  				got, err := GetVarTypeFromExpression(expr)
   129  				assert.NoError(t, err)
   130  
   131  				test.AssertEqualTypes(t, tt.want, got)
   132  			})
   133  
   134  			t.Run("when expression is a string", func(t *testing.T) {
   135  				got, err := getVarTypeFromString(tt.expression, hcl.Pos{Line: 1, Column: 1, Byte: 0})
   136  				assert.NoError(t, err)
   137  
   138  				test.AssertEqualTypes(t, tt.want, got)
   139  			})
   140  		})
   141  	}
   142  }
   143  
   144  var outputTests = []struct {
   145  	expression string
   146  	want       entities.Type
   147  }{
   148  	{
   149  		expression: `list(my_object)`,
   150  		want: entities.Type{
   151  			TFType: types.TerraformList,
   152  			Nested: &entities.Type{
   153  				TFType: types.TerraformObject,
   154  				Label:  "my_object",
   155  			},
   156  		},
   157  	},
   158  	{
   159  		expression: `list(string)`,
   160  		want: entities.Type{
   161  			TFType: types.TerraformList,
   162  			Nested: &entities.Type{
   163  				TFType: types.TerraformString,
   164  			},
   165  		},
   166  	},
   167  	{
   168  		expression: `set(number)`,
   169  		want: entities.Type{
   170  			TFType: types.TerraformSet,
   171  			Nested: &entities.Type{
   172  				TFType: types.TerraformNumber,
   173  			},
   174  		},
   175  	},
   176  	{
   177  		expression: `list(number)`,
   178  		want: entities.Type{
   179  			TFType: types.TerraformList,
   180  			Nested: &entities.Type{
   181  				TFType: types.TerraformNumber,
   182  			},
   183  		},
   184  	},
   185  	{
   186  		expression: `list(another_object)`,
   187  		want: entities.Type{
   188  			TFType: types.TerraformList,
   189  			Nested: &entities.Type{
   190  				TFType: types.TerraformObject,
   191  				Label:  "another_object",
   192  			},
   193  		},
   194  	},
   195  	{
   196  		expression: `set(another_object)`,
   197  		want: entities.Type{
   198  			TFType: types.TerraformSet,
   199  			Nested: &entities.Type{
   200  				TFType: types.TerraformObject,
   201  				Label:  "another_object",
   202  			},
   203  		},
   204  	},
   205  	{
   206  		expression: `object(my_object_name)`,
   207  		want: entities.Type{
   208  			TFType: types.TerraformObject,
   209  			Label:  "my_object_name",
   210  		},
   211  	},
   212  	{
   213  		expression: `map(my_object_name)`,
   214  		want: entities.Type{
   215  			TFType: types.TerraformMap,
   216  			Nested: &entities.Type{
   217  				TFType: types.TerraformObject,
   218  				Label:  "my_object_name",
   219  			},
   220  		},
   221  	},
   222  	{
   223  		expression: `object(another_object_name)`,
   224  		want: entities.Type{
   225  			TFType: types.TerraformObject,
   226  			Label:  "another_object_name",
   227  		},
   228  	},
   229  	{
   230  		expression: `string`,
   231  		want: entities.Type{
   232  			TFType: types.TerraformString,
   233  		},
   234  	},
   235  	{
   236  		expression: `number`,
   237  		want: entities.Type{
   238  			TFType: types.TerraformNumber,
   239  		},
   240  	},
   241  	{
   242  		expression: `bool`,
   243  		want: entities.Type{
   244  			TFType: types.TerraformBool,
   245  		},
   246  	},
   247  	{
   248  		expression: `resource(foo_bar_baz)`,
   249  		want: entities.Type{
   250  			TFType: types.TerraformResource,
   251  			Label:  "foo_bar_baz",
   252  		},
   253  	},
   254  }
   255  
   256  func TestGetOutputTypeFromExpression(t *testing.T) {
   257  	for _, tt := range outputTests {
   258  		t.Run(tt.expression, func(t *testing.T) {
   259  			expr, parseDiags := hclsyntax.ParseExpression([]byte(tt.expression), "", hcl.Pos{Line: 1, Column: 1, Byte: 0})
   260  			if parseDiags.HasErrors() {
   261  				t.Errorf("Error parsing expression: %v", parseDiags.Errs())
   262  			}
   263  
   264  			got, err := GetOutputTypeFromExpression(expr)
   265  			assert.NoError(t, err)
   266  
   267  			test.AssertEqualTypes(t, tt.want, got)
   268  		})
   269  	}
   270  }