Cory Klein
Cory Klein

Reputation: 55720

Wrapping one of many methods on a type struct?

A library I use has a type with multiple methods:

type Foo struct {
}

func (f *Foo) method1() int { ... }
func (f *Foo) method2() int { ... }
func (f *Foo) method3() int { ... }
// ... and so on

I'd really like to apply some specific behavior anytime I call method1 on this type:

func (f *Foo) method1Wrapper() int {
    incrementCounter()
    return f.method1()
}

But this adds a new method I'd have to call instead of just directly calling method1() itself.

Alternatively, I imagine I could create my own type:

type Foo2 struct {
    Foo
}

func (f *Foo2) method1() int {
    incrementCounter()
    return f.Foo.method1()
}

But then I'd have to create a bunch of boilerplate code to proxy all the calls to method2, method3, etc down to the Foo implementation, and I'd have to change all my usages of Foo to Foo2. 😩

Is it possible to directly patch or wrap Foo.method1() itself without creating a subclass?

Upvotes: 2

Views: 282

Answers (1)

Mr_Pink
Mr_Pink

Reputation: 109406

You don't need to proxy the method calls to delegate them, this is exactly what embedding is for.

type Foo struct {
}

func (f *Foo) method1() int { return 1 }
func (f *Foo) method2() int { return 2 }
func (f *Foo) method3() int { return 3 }

type Foo2 struct {
    *Foo
}

func (f Foo2) method1() int {
    fmt.Println("WRAPPED")
    return f.Foo.method1()
}

Foo2 has the same method set as Foo, but method1 is "intercepted" by Foo2, which explicitly calls Foo.method1 internally.

https://play.golang.org/p/q8tea5ZuHl4

Upvotes: 3

Related Questions