github.com/ovechkin-dm/go-dyno@v0.0.23/README.md (about)

     1  ## go-dyno
     2  
     3  ### Dynamic proxy for golang >= 1.18
     4  
     5  ![go-dyno](https://user-images.githubusercontent.com/6629797/219674966-bab33ecb-24b1-4a23-9d9f-8928e46f8bb7.png)
     6  
     7  An attempt to bring java-like dynamic proxy to golang.
     8  
     9  You can use dynamic proxies for AOP, logging, caching, metrics and mocking.
    10  
    11  Basic example of caching proxy:
    12  
    13  ```go
    14  package main
    15  
    16  import (
    17  	"fmt"
    18  	"github.com/ovechkin-dm/go-dyno/pkg/dyno"
    19  	"reflect"
    20  	"time"
    21  )
    22  
    23  type Service interface {
    24  	Foo(s string) string
    25  	Bar(i int) int
    26  }
    27  
    28  type Impl struct {
    29  }
    30  
    31  func (h *Impl) Foo(s string) string {
    32  	time.Sleep(2 * time.Second)
    33  	return s + " world!"
    34  }
    35  
    36  func (h *Impl) Bar(i int) int {
    37  	time.Sleep(2 * time.Second)
    38  	return i + 1
    39  }
    40  
    41  type CachingProxy struct {
    42  	delegate interface{}
    43  	cache    map[int][]reflect.Value
    44  }
    45  
    46  func (c *CachingProxy) Handle(method *dyno.Method, values []reflect.Value) []reflect.Value {
    47  	_, ok := c.cache[method.Num]
    48  	ref := reflect.ValueOf(c.delegate)
    49  	if !ok {
    50  		out := ref.Method(method.Num).Call(values)
    51  		c.cache[method.Num] = out
    52  	}
    53  	return c.cache[method.Num]
    54  
    55  }
    56  
    57  func CreateCachingProxyFor[T any](t T) (T, error) {
    58  	proxy := &CachingProxy{
    59  		delegate: t,
    60  		cache:    make(map[int][]reflect.Value),
    61  	}
    62  	return dyno.Dynamic[T](proxy)
    63  }
    64  
    65  func main() {
    66  	s := &Impl{}
    67  	proxy, err := CreateCachingProxyFor[Service](s)
    68  	if err != nil {
    69  		panic(err)
    70  	}
    71  	fmt.Println(proxy.Foo("hello"))
    72  	fmt.Println(proxy.Foo("hello"))
    73  	fmt.Println(proxy.Foo("hello"))
    74  }
    75  
    76  ```
    77  
    78  For golang <= 1.16 you can look at dpig project