package lazy import ( "context" "sync" ) type Lazy[T any] struct { Get func() (T, error) once sync.Once val T err error } func MakeLazy[T any](get func() (T, error)) *Lazy[T] { return &Lazy[T]{ Get: get, } } func (l *Lazy[T]) Val() (T, error) { l.once.Do(func() { l.val, l.err = l.Get() }) return l.val, l.err } type LazyCtx[T any] struct { Get func(context.Context) (T, error) once sync.Once val T err error } func MakeLazyCtx[T any](get func(ctx context.Context) (T, error)) *LazyCtx[T] { return &LazyCtx[T]{ Get: get, } } func (l *LazyCtx[T]) Val(ctx context.Context) (T, error) { l.once.Do(func() { l.val, l.err = l.Get(ctx) }) return l.val, l.err }