github.com/stackb/rules_proto@v0.0.0-20240221195024-5428336c51f1/pkg/protoc/language_rule_config_test.go (about) 1 package protoc 2 3 import "testing" 4 5 type languageRuleConfigCheck func(t *testing.T, cfg *LanguageRuleConfig) 6 7 func TestLanguageRuleConfigClone(t *testing.T) { 8 a := NewLanguageRuleConfig(nil, "proto_compile") 9 a.Deps = map[string]bool{ 10 "d1": true, 11 "d2": true, 12 } 13 b := a.clone() 14 15 check := allRuleChecks( 16 withLanguageRuleName("proto_compile"), 17 withLanguageRuleEnabled(true), 18 withRuleDepsEquals("d1", "d2"), 19 ) 20 21 check(t, a) 22 check(t, b) 23 24 b.Enabled = false 25 26 withLanguageRuleEnabled(true)(t, a) 27 withLanguageRuleEnabled(false)(t, b) 28 } 29 30 func TestRuleDirectives(t *testing.T) { 31 testDirectives(t, map[string]packageConfigTestCase{ 32 "proto_rule enabled": { 33 directives: withDirectives("proto_rule", "fake_proto_library enabled true"), 34 check: withLanguageRule("fake_proto_library", withLanguageRuleEnabled(true)), 35 }, 36 "proto_rule dep": { 37 directives: withDirectives( 38 "proto_rule", "fake_proto_library dep @fake//lib", 39 ), 40 check: withLanguageRule("fake_proto_library", withRuleDepsEquals("@fake//lib")), 41 }, 42 "proto_rule -dep": { 43 directives: withDirectives( 44 "proto_rule", "fake_proto_library +dep @fake//lib", 45 "proto_rule", "fake_proto_library -dep @fake//lib", 46 ), 47 check: withLanguageRule("fake_proto_library", withRuleDepsEquals()), 48 }, 49 "proto_rule resolve": { 50 directives: withDirectives( 51 "proto_rule", "fake_proto_library resolve google/protobuf/([a-z]+).proto @org_golang_google_protobuf//types/known/$1pb", 52 ), 53 check: withLanguageRule("fake_proto_library", withRuleResolvesEquals( 54 "google/protobuf/([a-z]+).proto @org_golang_google_protobuf//types/known/$1pb", 55 )), 56 }, 57 "proto_rule attr 1": { 58 directives: withDirectives( 59 "proto_rule", "fake_proto_library attr count 1", 60 ), 61 check: withLanguageRule("fake_proto_library", withRuleAttrEquals( 62 "count", 63 "1", 64 )), 65 }, 66 "proto_rule attr 2": { 67 directives: withDirectives( 68 "proto_rule", "fake_proto_library attr count 1", 69 "proto_rule", "fake_proto_library attr count 2", 70 ), 71 check: withLanguageRule("fake_proto_library", withRuleAttrEquals( 72 "count", 73 "1", 74 "2", 75 )), 76 }, 77 "proto_rule attr -count": { 78 directives: withDirectives( 79 "proto_rule", "fake_proto_library attr count 1", 80 "proto_rule", "fake_proto_library attr count 2", 81 "proto_rule", "fake_proto_library attr -count 1", 82 ), 83 check: withLanguageRule("fake_proto_library", withRuleAttrEquals( 84 "count", 85 "2", 86 )), 87 }, 88 "proto_rule -attr count": { 89 directives: withDirectives( 90 "proto_rule", "fake_proto_library attr count 1", 91 "proto_rule", "fake_proto_library attr count 2", 92 "proto_rule", "fake_proto_library -attr count", 93 ), 94 check: withLanguageRule("fake_proto_library", withRuleAttrEquals( 95 "count", 96 )), 97 }, 98 "proto_rule attr with space": { 99 directives: withDirectives( 100 "proto_rule", "fake_proto_library attr args --lib ES2015", 101 ), 102 check: withLanguageRule("fake_proto_library", withRuleAttrEquals( 103 "--lib ES2015", 104 )), 105 }, 106 }) 107 } 108 109 func allRuleChecks(checks ...languageRuleConfigCheck) languageRuleConfigCheck { 110 return func(t *testing.T, cfg *LanguageRuleConfig) { 111 for _, check := range checks { 112 check(t, cfg) 113 } 114 } 115 } 116 117 func withLanguageRule(name string, checks ...languageRuleConfigCheck) packageConfigCheck { 118 return func(t *testing.T, cfg *PackageConfig) { 119 rule, ok := cfg.rules[name] 120 if !ok { 121 t.Fatal("rule not found", name) 122 } 123 for _, check := range checks { 124 check(t, rule) 125 } 126 } 127 } 128 129 func withLanguageRuleEnabled(enabled bool) languageRuleConfigCheck { 130 return func(t *testing.T, cfg *LanguageRuleConfig) { 131 if cfg.Enabled != enabled { 132 t.Errorf("rule label: want %t, got %t", enabled, cfg.Enabled) 133 } 134 } 135 } 136 137 func withLanguageRuleName(name string) languageRuleConfigCheck { 138 return func(t *testing.T, cfg *LanguageRuleConfig) { 139 if cfg.Name != name { 140 t.Errorf("rule name: want %s, got %s", name, cfg.Name) 141 } 142 } 143 } 144 145 func withRuleDepsEquals(deps ...string) languageRuleConfigCheck { 146 return func(t *testing.T, cfg *LanguageRuleConfig) { 147 got := cfg.GetDeps() 148 if len(deps) != len(got) { 149 t.Fatalf("rule deps: want %d, got %d", len(deps), len(got)) 150 } 151 for i := 0; i < len(got); i++ { 152 expected := deps[i] 153 actual := got[i] 154 if expected != actual { 155 t.Errorf("rule dep #%d: want %s, got %s", i, expected, actual) 156 } 157 } 158 } 159 } 160 161 func withRuleResolvesEquals(resolves ...string) languageRuleConfigCheck { 162 return func(t *testing.T, cfg *LanguageRuleConfig) { 163 got := cfg.GetRewrites() 164 if len(resolves) != len(got) { 165 t.Fatalf("rule resolves: want %d, got %d", len(resolves), len(got)) 166 } 167 for i := 0; i < len(got); i++ { 168 expected := resolves[i] 169 actual := got[i] 170 original := actual.Match.String() + " " + actual.Replace 171 if expected != original { 172 t.Errorf("rule resolve #%d: want %s, got %s", i, expected, original) 173 } 174 } 175 } 176 } 177 178 func withRuleAttrEquals(name string, want ...string) languageRuleConfigCheck { 179 return func(t *testing.T, cfg *LanguageRuleConfig) { 180 got := cfg.GetAttr(name) 181 if len(want) != len(got) { 182 t.Fatalf("rule attr %s: want %d, got %d", name, len(want), len(got)) 183 } 184 for i := 0; i < len(got); i++ { 185 expected := want[i] 186 actual := got[i] 187 if expected != actual { 188 t.Errorf("rule attr %s #%d: want %s, got %s", name, i, expected, actual) 189 } 190 } 191 } 192 }