rate limit: make context aware (#731)

* rate limits: Make context aware

* binance: rate limit allow for cancellation of reservation when deadline is exceeded

* request: add context.done() before initiating any bulk work.

* binance: update error return for rate limiting

* request: updated dealine check to remove after time.Now procedure as this will obfuscate a deadline which will be limited by the context check on every attempt, so no need to sleep with delay.
This commit is contained in:
Ryan O'Hara-Reid
2021-08-10 12:08:27 +10:00
committed by GitHub
parent 4602ade809
commit 232d6ebc1f
18 changed files with 245 additions and 198 deletions

View File

@@ -1,6 +1,7 @@
package request
import (
"context"
"errors"
"sync/atomic"
"time"
@@ -22,9 +23,8 @@ type BasicLimit struct {
}
// Limit executes a single rate limit set by NewRateLimit
func (b *BasicLimit) Limit(_ EndpointLimit) error {
time.Sleep(b.r.Reserve().Delay())
return nil
func (b *BasicLimit) Limit(ctx context.Context, _ EndpointLimit) error {
return b.r.Wait(ctx)
}
// EndpointLimit defines individual endpoint rate limits that are set when
@@ -35,7 +35,7 @@ type EndpointLimit int
// wrapper for extended rate limiting configuration i.e. Shells of rate
// limits with a global rate for sub rates.
type Limiter interface {
Limit(EndpointLimit) error
Limit(context.Context, EndpointLimit) error
}
// NewRateLimit creates a new RateLimit based of time interval and how many
@@ -59,13 +59,13 @@ func NewBasicRateLimit(interval time.Duration, actions int) Limiter {
}
// InitiateRateLimit sleeps for designated end point rate limits
func (r *Requester) InitiateRateLimit(e EndpointLimit) error {
func (r *Requester) InitiateRateLimit(ctx context.Context, e EndpointLimit) error {
if atomic.LoadInt32(&r.disableRateLimiter) == 1 {
return nil
}
if r.limiter != nil {
return r.limiter.Limit(e)
return r.limiter.Limit(ctx, e)
}
return nil