github.com/zoumo/helm@v2.5.0+incompatible/pkg/strvals/parser_test.go (about) 1 /* 2 Copyright 2016 The Kubernetes Authors All rights reserved. 3 Licensed under the Apache License, Version 2.0 (the "License"); 4 you may not use this file except in compliance with the License. 5 You may obtain a copy of the License at 6 7 http://www.apache.org/licenses/LICENSE-2.0 8 9 Unless required by applicable law or agreed to in writing, software 10 distributed under the License is distributed on an "AS IS" BASIS, 11 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 See the License for the specific language governing permissions and 13 limitations under the License. 14 */ 15 16 package strvals 17 18 import ( 19 "testing" 20 21 "github.com/ghodss/yaml" 22 ) 23 24 func TestSetIndex(t *testing.T) { 25 tests := []struct { 26 name string 27 initial []interface{} 28 expect []interface{} 29 add int 30 val int 31 }{ 32 { 33 name: "short", 34 initial: []interface{}{0, 1}, 35 expect: []interface{}{0, 1, 2}, 36 add: 2, 37 val: 2, 38 }, 39 { 40 name: "equal", 41 initial: []interface{}{0, 1}, 42 expect: []interface{}{0, 2}, 43 add: 1, 44 val: 2, 45 }, 46 { 47 name: "long", 48 initial: []interface{}{0, 1, 2, 3, 4, 5}, 49 expect: []interface{}{0, 1, 2, 4, 4, 5}, 50 add: 3, 51 val: 4, 52 }, 53 } 54 55 for _, tt := range tests { 56 got := setIndex(tt.initial, tt.add, tt.val) 57 if len(got) != len(tt.expect) { 58 t.Fatalf("%s: Expected length %d, got %d", tt.name, len(tt.expect), len(got)) 59 } 60 61 if gg := got[tt.add].(int); gg != tt.val { 62 t.Errorf("%s, Expected value %d, got %d", tt.name, tt.val, gg) 63 } 64 } 65 } 66 67 func TestParseSet(t *testing.T) { 68 tests := []struct { 69 str string 70 expect map[string]interface{} 71 err bool 72 }{ 73 { 74 "name1=value1", 75 map[string]interface{}{"name1": "value1"}, 76 false, 77 }, 78 { 79 "name1=value1,name2=value2", 80 map[string]interface{}{"name1": "value1", "name2": "value2"}, 81 false, 82 }, 83 { 84 "name1=value1,name2=value2,", 85 map[string]interface{}{"name1": "value1", "name2": "value2"}, 86 false, 87 }, 88 { 89 str: "name1=value1,,,,name2=value2,", 90 err: true, 91 }, 92 { 93 str: "name1=,name2=value2", 94 expect: map[string]interface{}{"name1": "", "name2": "value2"}, 95 }, 96 { 97 str: "name1,name2=", 98 err: true, 99 }, 100 { 101 str: "name1,name2=value2", 102 err: true, 103 }, 104 { 105 str: "name1,name2=value2\\", 106 err: true, 107 }, 108 { 109 str: "name1,name2", 110 err: true, 111 }, 112 { 113 "name1=one\\,two,name2=three\\,four", 114 map[string]interface{}{"name1": "one,two", "name2": "three,four"}, 115 false, 116 }, 117 { 118 "name1=one\\=two,name2=three\\=four", 119 map[string]interface{}{"name1": "one=two", "name2": "three=four"}, 120 false, 121 }, 122 { 123 "name1=one two three,name2=three two one", 124 map[string]interface{}{"name1": "one two three", "name2": "three two one"}, 125 false, 126 }, 127 { 128 "outer.inner=value", 129 map[string]interface{}{"outer": map[string]interface{}{"inner": "value"}}, 130 false, 131 }, 132 { 133 "outer.middle.inner=value", 134 map[string]interface{}{"outer": map[string]interface{}{"middle": map[string]interface{}{"inner": "value"}}}, 135 false, 136 }, 137 { 138 "outer.inner1=value,outer.inner2=value2", 139 map[string]interface{}{"outer": map[string]interface{}{"inner1": "value", "inner2": "value2"}}, 140 false, 141 }, 142 { 143 "outer.inner1=value,outer.middle.inner=value", 144 map[string]interface{}{ 145 "outer": map[string]interface{}{ 146 "inner1": "value", 147 "middle": map[string]interface{}{ 148 "inner": "value", 149 }, 150 }, 151 }, 152 false, 153 }, 154 { 155 str: "name1.name2", 156 err: true, 157 }, 158 { 159 str: "name1.name2,name1.name3", 160 err: true, 161 }, 162 { 163 str: "name1.name2=", 164 expect: map[string]interface{}{"name1": map[string]interface{}{"name2": ""}}, 165 }, 166 { 167 str: "name1.=name2", 168 err: true, 169 }, 170 { 171 str: "name1.,name2", 172 err: true, 173 }, 174 { 175 "name1={value1,value2}", 176 map[string]interface{}{"name1": []string{"value1", "value2"}}, 177 false, 178 }, 179 { 180 "name1={value1,value2},name2={value1,value2}", 181 map[string]interface{}{ 182 "name1": []string{"value1", "value2"}, 183 "name2": []string{"value1", "value2"}, 184 }, 185 false, 186 }, 187 { 188 "name1={1021,902}", 189 map[string]interface{}{"name1": []int{1021, 902}}, 190 false, 191 }, 192 { 193 "name1.name2={value1,value2}", 194 map[string]interface{}{"name1": map[string]interface{}{"name2": []string{"value1", "value2"}}}, 195 false, 196 }, 197 { 198 str: "name1={1021,902", 199 err: true, 200 }, 201 // List support 202 { 203 str: "list[0]=foo", 204 expect: map[string]interface{}{"list": []string{"foo"}}, 205 }, 206 { 207 str: "list[0].foo=bar", 208 expect: map[string]interface{}{ 209 "list": []interface{}{ 210 map[string]interface{}{"foo": "bar"}, 211 }, 212 }, 213 }, 214 { 215 str: "list[0].foo=bar,list[0].hello=world", 216 expect: map[string]interface{}{ 217 "list": []interface{}{ 218 map[string]interface{}{"foo": "bar", "hello": "world"}, 219 }, 220 }, 221 }, 222 { 223 str: "list[0]=foo,list[1]=bar", 224 expect: map[string]interface{}{"list": []string{"foo", "bar"}}, 225 }, 226 { 227 str: "list[0]=foo,list[1]=bar,", 228 expect: map[string]interface{}{"list": []string{"foo", "bar"}}, 229 }, 230 { 231 str: "list[0]=foo,list[3]=bar", 232 expect: map[string]interface{}{"list": []interface{}{"foo", nil, nil, "bar"}}, 233 }, 234 { 235 str: "illegal[0]name.foo=bar", 236 err: true, 237 }, 238 { 239 str: "noval[0]", 240 expect: map[string]interface{}{"noval": []interface{}{}}, 241 }, 242 { 243 str: "noval[0]=", 244 expect: map[string]interface{}{"noval": []interface{}{""}}, 245 }, 246 { 247 str: "nested[0][0]=1", 248 expect: map[string]interface{}{"nested": []interface{}{[]interface{}{1}}}, 249 }, 250 { 251 str: "nested[1][1]=1", 252 expect: map[string]interface{}{"nested": []interface{}{nil, []interface{}{nil, 1}}}, 253 }, 254 } 255 256 for _, tt := range tests { 257 got, err := Parse(tt.str) 258 if err != nil { 259 if tt.err { 260 continue 261 } 262 t.Fatalf("%s: %s", tt.str, err) 263 } 264 if tt.err { 265 t.Errorf("%s: Expected error. Got nil", tt.str) 266 } 267 268 y1, err := yaml.Marshal(tt.expect) 269 if err != nil { 270 t.Fatal(err) 271 } 272 y2, err := yaml.Marshal(got) 273 if err != nil { 274 t.Fatalf("Error serializing parsed value: %s", err) 275 } 276 277 if string(y1) != string(y2) { 278 t.Errorf("%s: Expected:\n%s\nGot:\n%s", tt.str, y1, y2) 279 } 280 } 281 } 282 283 func TestParseInto(t *testing.T) { 284 got := map[string]interface{}{ 285 "outer": map[string]interface{}{ 286 "inner1": "overwrite", 287 "inner2": "value2", 288 }, 289 } 290 input := "outer.inner1=value1,outer.inner3=value3" 291 expect := map[string]interface{}{ 292 "outer": map[string]interface{}{ 293 "inner1": "value1", 294 "inner2": "value2", 295 "inner3": "value3", 296 }, 297 } 298 299 if err := ParseInto(input, got); err != nil { 300 t.Fatal(err) 301 } 302 303 y1, err := yaml.Marshal(expect) 304 if err != nil { 305 t.Fatal(err) 306 } 307 y2, err := yaml.Marshal(got) 308 if err != nil { 309 t.Fatalf("Error serializing parsed value: %s", err) 310 } 311 312 if string(y1) != string(y2) { 313 t.Errorf("%s: Expected:\n%s\nGot:\n%s", input, y1, y2) 314 } 315 } 316 317 func TestToYAML(t *testing.T) { 318 // The TestParse does the hard part. We just verify that YAML formatting is 319 // happening. 320 o, err := ToYAML("name=value") 321 if err != nil { 322 t.Fatal(err) 323 } 324 expect := "name: value\n" 325 if o != expect { 326 t.Errorf("Expected %q, got %q", expect, o) 327 } 328 }