github.com/opiuman/genqlient@v1.0.0/generate/names_test.go (about)

     1  package generate
     2  
     3  import (
     4  	"testing"
     5  
     6  	"github.com/vektah/gqlparser/v2/ast"
     7  )
     8  
     9  func fakeField(containingTypeName, fieldName string) *ast.Field {
    10  	// (just the fields we need, probably not usable outside this file)
    11  	return &ast.Field{
    12  		Alias:            fieldName,
    13  		ObjectDefinition: &ast.Definition{Name: containingTypeName},
    14  	}
    15  }
    16  
    17  func TestTypeNames(t *testing.T) {
    18  	tests := []struct {
    19  		expectedTypeName string
    20  		fields           []*ast.Field
    21  		leafTypeName     string
    22  	}{{
    23  		"OperationFieldType",
    24  		[]*ast.Field{fakeField("Query", "field")},
    25  		"Type",
    26  	}, {
    27  		"OperationUser",
    28  		[]*ast.Field{fakeField("Query", "user")},
    29  		"User",
    30  	}, {
    31  		// We don't shorten field-names.
    32  		"OperationOperationUser",
    33  		[]*ast.Field{fakeField("Query", "operationUser")},
    34  		"User",
    35  	}, {
    36  		// We do shorten across multiple prefixes.
    37  		"OperationUser",
    38  		[]*ast.Field{fakeField("Query", "user")},
    39  		"OperationUser",
    40  	}, {
    41  		"OperationFavoriteUser",
    42  		[]*ast.Field{fakeField("Query", "favoriteUser")},
    43  		"User",
    44  	}, {
    45  		"OperationField1Type1Field2Type2",
    46  		[]*ast.Field{fakeField("Query", "field1"), fakeField("Type1", "field2")},
    47  		"Type2",
    48  	}, {
    49  		"OperationUpperFieldLowerType",
    50  		// This is legal GraphQL!
    51  		[]*ast.Field{fakeField("Query", "UpperField")},
    52  		"lowerType",
    53  	}, {
    54  		"OperationUpperLowerUpperLower",
    55  		[]*ast.Field{fakeField("Query", "Upper"), fakeField("lower", "Upper")},
    56  		"lower",
    57  	}}
    58  	for _, test := range tests {
    59  		test := test
    60  		t.Run(test.expectedTypeName, func(t *testing.T) {
    61  			prefix := newPrefixList("Operation")
    62  			for _, field := range test.fields {
    63  				prefix = nextPrefix(prefix, field)
    64  			}
    65  			actualTypeName := makeTypeName(prefix, test.leafTypeName)
    66  			if actualTypeName != test.expectedTypeName {
    67  				t.Errorf("name mismatch:\ngot:  %s\nwant: %s",
    68  					actualTypeName, test.expectedTypeName)
    69  			}
    70  		})
    71  	}
    72  }
    73  
    74  func TestTypeNameCollisions(t *testing.T) {
    75  	tests := []struct {
    76  		fields       []*ast.Field
    77  		leafTypeName string
    78  	}{
    79  		{[]*ast.Field{fakeField("Query", "user")}, "UserInterface"},
    80  		{[]*ast.Field{fakeField("Query", "user")}, "User"},
    81  		{[]*ast.Field{fakeField("Query", "user")}, "QueryUser"},
    82  		{[]*ast.Field{fakeField("Query", "queryUser")}, "User"},
    83  		// Known issues, described in names.go file-documentation:
    84  		// Interface/implementation collision:
    85  		// 	{[]*ast.Field{fakeField("Query", "queryUser")}, "QueryUser"},
    86  		// Case collision:
    87  		// 	{[]*ast.Field{fakeField("Query", "QueryUser")}, "User"},
    88  		// Overlapping-parts collision:
    89  		//	{[]*ast.Field{fakeField("Query", "userQuery")}, "User"},
    90  	}
    91  	seen := map[string]int{} // name -> index of test that had it
    92  	for i, test := range tests {
    93  		prefix := newPrefixList("Operation")
    94  		for _, field := range test.fields {
    95  			prefix = nextPrefix(prefix, field)
    96  		}
    97  		actualTypeName := makeTypeName(prefix, test.leafTypeName)
    98  
    99  		otherIndex, ok := seen[actualTypeName]
   100  		if ok {
   101  			t.Errorf("name collision:\ncase %2d: %#v\ncase %2d: %#v",
   102  				i, test, otherIndex, tests[otherIndex])
   103  		}
   104  		seen[actualTypeName] = i
   105  	}
   106  }