github.com/v2fly/tools@v0.100.0/internal/event/label/label_test.go (about)

     1  // Copyright 2020 The Go Authors. All rights reserved.
     2  // Use of this source code is governed by a BSD-style
     3  // license that can be found in the LICENSE file.
     4  
     5  package label_test
     6  
     7  import (
     8  	"bytes"
     9  	"fmt"
    10  	"runtime"
    11  	"testing"
    12  	"unsafe"
    13  
    14  	"github.com/v2fly/tools/internal/event/keys"
    15  	"github.com/v2fly/tools/internal/event/label"
    16  )
    17  
    18  var (
    19  	AKey = keys.NewString("A", "")
    20  	BKey = keys.NewString("B", "")
    21  	CKey = keys.NewString("C", "")
    22  	A    = AKey.Of("a")
    23  	B    = BKey.Of("b")
    24  	C    = CKey.Of("c")
    25  	all  = []label.Label{A, B, C}
    26  )
    27  
    28  func TestList(t *testing.T) {
    29  	for _, test := range []struct {
    30  		name   string
    31  		labels []label.Label
    32  		expect string
    33  	}{{
    34  		name: "empty",
    35  	}, {
    36  		name:   "single",
    37  		labels: []label.Label{A},
    38  		expect: `A="a"`,
    39  	}, {
    40  		name:   "invalid",
    41  		labels: []label.Label{{}},
    42  		expect: ``,
    43  	}, {
    44  		name:   "two",
    45  		labels: []label.Label{A, B},
    46  		expect: `A="a", B="b"`,
    47  	}, {
    48  		name:   "three",
    49  		labels: []label.Label{A, B, C},
    50  		expect: `A="a", B="b", C="c"`,
    51  	}, {
    52  		name:   "missing A",
    53  		labels: []label.Label{{}, B, C},
    54  		expect: `B="b", C="c"`,
    55  	}, {
    56  		name:   "missing B",
    57  		labels: []label.Label{A, {}, C},
    58  		expect: `A="a", C="c"`,
    59  	}, {
    60  		name:   "missing C",
    61  		labels: []label.Label{A, B, {}},
    62  		expect: `A="a", B="b"`,
    63  	}, {
    64  		name:   "missing AB",
    65  		labels: []label.Label{{}, {}, C},
    66  		expect: `C="c"`,
    67  	}, {
    68  		name:   "missing AC",
    69  		labels: []label.Label{{}, B, {}},
    70  		expect: `B="b"`,
    71  	}, {
    72  		name:   "missing BC",
    73  		labels: []label.Label{A, {}, {}},
    74  		expect: `A="a"`,
    75  	}} {
    76  		t.Run(test.name, func(t *testing.T) {
    77  			got := printList(label.NewList(test.labels...))
    78  			if got != test.expect {
    79  				t.Errorf("got %q want %q", got, test.expect)
    80  			}
    81  		})
    82  	}
    83  }
    84  
    85  func TestFilter(t *testing.T) {
    86  	for _, test := range []struct {
    87  		name    string
    88  		labels  []label.Label
    89  		filters []label.Key
    90  		expect  string
    91  	}{{
    92  		name:   "no filters",
    93  		labels: all,
    94  		expect: `A="a", B="b", C="c"`,
    95  	}, {
    96  		name:    "no labels",
    97  		filters: []label.Key{AKey},
    98  		expect:  ``,
    99  	}, {
   100  		name:    "filter A",
   101  		labels:  all,
   102  		filters: []label.Key{AKey},
   103  		expect:  `B="b", C="c"`,
   104  	}, {
   105  		name:    "filter B",
   106  		labels:  all,
   107  		filters: []label.Key{BKey},
   108  		expect:  `A="a", C="c"`,
   109  	}, {
   110  		name:    "filter C",
   111  		labels:  all,
   112  		filters: []label.Key{CKey},
   113  		expect:  `A="a", B="b"`,
   114  	}, {
   115  		name:    "filter AC",
   116  		labels:  all,
   117  		filters: []label.Key{AKey, CKey},
   118  		expect:  `B="b"`,
   119  	}} {
   120  		t.Run(test.name, func(t *testing.T) {
   121  			labels := label.NewList(test.labels...)
   122  			got := printList(label.Filter(labels, test.filters...))
   123  			if got != test.expect {
   124  				t.Errorf("got %q want %q", got, test.expect)
   125  			}
   126  		})
   127  	}
   128  }
   129  
   130  func TestMap(t *testing.T) {
   131  	for _, test := range []struct {
   132  		name   string
   133  		labels []label.Label
   134  		keys   []label.Key
   135  		expect string
   136  	}{{
   137  		name:   "no labels",
   138  		keys:   []label.Key{AKey},
   139  		expect: `nil`,
   140  	}, {
   141  		name:   "match A",
   142  		labels: all,
   143  		keys:   []label.Key{AKey},
   144  		expect: `A="a"`,
   145  	}, {
   146  		name:   "match B",
   147  		labels: all,
   148  		keys:   []label.Key{BKey},
   149  		expect: `B="b"`,
   150  	}, {
   151  		name:   "match C",
   152  		labels: all,
   153  		keys:   []label.Key{CKey},
   154  		expect: `C="c"`,
   155  	}, {
   156  		name:   "match ABC",
   157  		labels: all,
   158  		keys:   []label.Key{AKey, BKey, CKey},
   159  		expect: `A="a", B="b", C="c"`,
   160  	}, {
   161  		name:   "missing A",
   162  		labels: []label.Label{{}, B, C},
   163  		keys:   []label.Key{AKey, BKey, CKey},
   164  		expect: `nil, B="b", C="c"`,
   165  	}, {
   166  		name:   "missing B",
   167  		labels: []label.Label{A, {}, C},
   168  		keys:   []label.Key{AKey, BKey, CKey},
   169  		expect: `A="a", nil, C="c"`,
   170  	}, {
   171  		name:   "missing C",
   172  		labels: []label.Label{A, B, {}},
   173  		keys:   []label.Key{AKey, BKey, CKey},
   174  		expect: `A="a", B="b", nil`,
   175  	}} {
   176  		t.Run(test.name, func(t *testing.T) {
   177  			lm := label.NewMap(test.labels...)
   178  			got := printMap(lm, test.keys)
   179  			if got != test.expect {
   180  				t.Errorf("got %q want %q", got, test.expect)
   181  			}
   182  		})
   183  	}
   184  }
   185  
   186  func TestMapMerge(t *testing.T) {
   187  	for _, test := range []struct {
   188  		name   string
   189  		maps   []label.Map
   190  		keys   []label.Key
   191  		expect string
   192  	}{{
   193  		name:   "no maps",
   194  		keys:   []label.Key{AKey},
   195  		expect: `nil`,
   196  	}, {
   197  		name:   "one map",
   198  		maps:   []label.Map{label.NewMap(all...)},
   199  		keys:   []label.Key{AKey},
   200  		expect: `A="a"`,
   201  	}, {
   202  		name:   "invalid map",
   203  		maps:   []label.Map{label.NewMap()},
   204  		keys:   []label.Key{AKey},
   205  		expect: `nil`,
   206  	}, {
   207  		name:   "two maps",
   208  		maps:   []label.Map{label.NewMap(B, C), label.NewMap(A)},
   209  		keys:   []label.Key{AKey, BKey, CKey},
   210  		expect: `A="a", B="b", C="c"`,
   211  	}, {
   212  		name:   "invalid start map",
   213  		maps:   []label.Map{label.NewMap(), label.NewMap(B, C)},
   214  		keys:   []label.Key{AKey, BKey, CKey},
   215  		expect: `nil, B="b", C="c"`,
   216  	}, {
   217  		name:   "invalid mid map",
   218  		maps:   []label.Map{label.NewMap(A), label.NewMap(), label.NewMap(C)},
   219  		keys:   []label.Key{AKey, BKey, CKey},
   220  		expect: `A="a", nil, C="c"`,
   221  	}, {
   222  		name:   "invalid end map",
   223  		maps:   []label.Map{label.NewMap(A, B), label.NewMap()},
   224  		keys:   []label.Key{AKey, BKey, CKey},
   225  		expect: `A="a", B="b", nil`,
   226  	}, {
   227  		name:   "three maps one nil",
   228  		maps:   []label.Map{label.NewMap(A), label.NewMap(B), nil},
   229  		keys:   []label.Key{AKey, BKey, CKey},
   230  		expect: `A="a", B="b", nil`,
   231  	}, {
   232  		name:   "two maps one nil",
   233  		maps:   []label.Map{label.NewMap(A, B), nil},
   234  		keys:   []label.Key{AKey, BKey, CKey},
   235  		expect: `A="a", B="b", nil`,
   236  	}} {
   237  		t.Run(test.name, func(t *testing.T) {
   238  			tagMap := label.MergeMaps(test.maps...)
   239  			got := printMap(tagMap, test.keys)
   240  			if got != test.expect {
   241  				t.Errorf("got %q want %q", got, test.expect)
   242  			}
   243  		})
   244  	}
   245  }
   246  
   247  func printList(list label.List) string {
   248  	buf := &bytes.Buffer{}
   249  	for index := 0; list.Valid(index); index++ {
   250  		l := list.Label(index)
   251  		if !l.Valid() {
   252  			continue
   253  		}
   254  		if buf.Len() > 0 {
   255  			buf.WriteString(", ")
   256  		}
   257  		fmt.Fprint(buf, l)
   258  	}
   259  	return buf.String()
   260  }
   261  
   262  func printMap(lm label.Map, keys []label.Key) string {
   263  	buf := &bytes.Buffer{}
   264  	for _, key := range keys {
   265  		if buf.Len() > 0 {
   266  			buf.WriteString(", ")
   267  		}
   268  		fmt.Fprint(buf, lm.Find(key))
   269  	}
   270  	return buf.String()
   271  }
   272  
   273  func TestAttemptedStringCorruption(t *testing.T) {
   274  	defer func() {
   275  		r := recover()
   276  		if _, ok := r.(*runtime.TypeAssertionError); !ok {
   277  			t.Fatalf("wanted to recover TypeAssertionError, got %T", r)
   278  		}
   279  	}()
   280  
   281  	var x uint64 = 12390
   282  	p := unsafe.Pointer(&x)
   283  	l := label.OfValue(AKey, p)
   284  	_ = l.UnpackString()
   285  }