package e2etest import ( "context" "time" "github.com/cenkalti/backoff/v4" "go.mau.fi/mautrix-telegram/pkg/gotd/bin" "go.mau.fi/mautrix-telegram/pkg/gotd/tg" "go.mau.fi/mautrix-telegram/pkg/gotd/tgerr" ) type retryInvoker struct { prev tg.Invoker } func retryResult[T any](ctx context.Context, cb func() (T, error)) (T, error) { var zero T return backoff.RetryWithData[T](func() (T, error) { res, err := cb() if err != nil { if tgerr.IsCode(err, -500) { return zero, err } if tgerr.Is(err, "CONNECTION_NOT_INITED") { return zero, err } if ok, err := tgerr.FloodWait(ctx, err); ok { return zero, err } return zero, backoff.Permanent(err) } return res, nil }, backoff.WithContext(backoff.NewConstantBackOff(time.Millisecond*500), ctx)) } func retry(ctx context.Context, cb func() error) error { return backoff.Retry(func() error { if err := cb(); err != nil { if tgerr.IsCode(err, -500) { return err } if tgerr.Is(err, "CONNECTION_NOT_INITED") { return err } if ok, err := tgerr.FloodWait(ctx, err); ok { return err } return backoff.Permanent(err) } return nil }, backoff.WithContext(backoff.NewExponentialBackOff(), ctx)) } func (w retryInvoker) Invoke(ctx context.Context, input bin.Encoder, output bin.Decoder) error { return retry(ctx, func() error { return w.prev.Invoke(ctx, input, output) }) }