Codebase list golang-github-mitchellh-reflectwalk / e1709c8c-8be5-462b-a105-6de8318c12e2/upstream
Import upstream version 1.0.2 Debian Janitor 2 years ago
2 changed file(s) with 87 addition(s) and 0 deletion(s). Raw diff Collapse all Expand all
6666 type PointerWalker interface {
6767 PointerEnter(bool) error
6868 PointerExit(bool) error
69 }
70
71 // PointerValueWalker implementations are notified with the value of
72 // a particular pointer when a pointer is walked. Pointer is called
73 // right before PointerEnter.
74 type PointerValueWalker interface {
75 Pointer(reflect.Value) error
6976 }
7077
7178 // SkipEntry can be returned from walk functions to skip walking
129136 }
130137
131138 if pointerV.Kind() == reflect.Ptr {
139 if pw, ok := w.(PointerValueWalker); ok {
140 if err = pw.Pointer(pointerV); err != nil {
141 if err == SkipEntry {
142 // Skip the rest of this entry but clear the error
143 return nil
144 }
145
146 return
147 }
148 }
149
132150 pointer = true
133151 v = reflect.Indirect(pointerV)
134152 }
4545 return fmt.Errorf("bad pointer exit '%t' at exit %d", v, t.exits)
4646 }
4747 t.pointers = t.pointers[:len(t.pointers)-1]
48 return nil
49 }
50
51 type TestPointerValueWalker struct {
52 skip bool
53 pointers []reflect.Type
54 }
55
56 func (t *TestPointerValueWalker) Pointer(v reflect.Value) error {
57 t.pointers = append(t.pointers, v.Type())
58 if t.skip {
59 return SkipEntry
60 }
61
4862 return nil
4963 }
5064
481495 }
482496 }
483497
498 func TestWalk_PointerValue(t *testing.T) {
499 type X struct{}
500 type T struct {
501 x *X
502 }
503
504 v := &T{x: &X{}}
505
506 expected := []reflect.Type{
507 reflect.TypeOf(v),
508 reflect.TypeOf(v.x),
509 }
510
511 w := new(TestPointerValueWalker)
512 err := Walk(v, w)
513 if err != nil {
514 t.Fatal(err)
515 }
516
517 if !reflect.DeepEqual(expected, w.pointers) {
518 t.Fatalf("unexpected pointer order or length (expected len=%d, actual len=%d)", len(expected), len(w.pointers))
519 }
520 }
521
522 func TestWalk_PointerValueSkip(t *testing.T) {
523 type T struct{}
524 type W struct {
525 TestPointerValueWalker
526 TestPointerWalker
527 }
528
529 v := &T{}
530 w := &W{
531 TestPointerValueWalker: TestPointerValueWalker{
532 skip: true,
533 },
534 }
535 err := Walk(v, w)
536 if err != nil {
537 t.Fatal(err)
538 }
539
540 if len(w.TestPointerValueWalker.pointers) != 1 {
541 t.Errorf("expected len=1, got len=%d", len(w.TestPointerValueWalker.pointers))
542 }
543
544 if w.TestPointerValueWalker.pointers[0] != reflect.TypeOf(v) {
545 t.Error("pointer value type mismatch")
546 }
547
548 if w.enters != 0 || w.exits != 0 {
549 t.Error("should have been skipped and have zero enters or exits")
550 }
551 }
552
484553 func TestWalk_Slice(t *testing.T) {
485554 w := new(TestSliceWalker)
486555