'When I use `golang.org/x/time` NewLimiter(), limit higher burst, Allow() will return true higher burst

What version of Go are you using (go version)?

go version

Output:

go version go1.12.17 darwin/amd64

What version of package are you using (rate version)?

golang.org/x/time v0.0.0-20190308202827-9d24e82272b4

What did you do?

Run the following on amd64:

package main

import (
    "fmt"
    "golang.org/x/time/rate"
    "sync"
    "sync/atomic"
    "time"
)

func main() {
    now := time.Now()
    t := time.After(time.Second)

    limit := rate.Limit(100)
    burst := 10
    l := rate.NewLimiter(limit, burst)

    var count int
    for {
        select {
        case <-t:
            fmt.Printf("%ds, %d\n", time.Now().Sub(now).Nanoseconds()/1e9, count)
            return
        default:
            if l.Allow() {
                count++
            }
        }
    }
}

What did you expect to see?

1s, 10

What did you see instead?

1s, 110

I am confused about count is not equal to the burst size. When I set Limit=100, burst=10, it should Allow() for maximum calls is burst.



Solution 1:[1]

Burst is not the maximum rate. It's the number of tokens in the bucket in addition to the refill rate.

You set the rate to 100 tokens per second and the burst capacity to 10.

It is not surprising at all that you can consume 100 tokens in the one second your program runs, plus the 10 tokens added by the burst capacity.

If you want to allow no more than 10 things to happen in one second, set the rate to 10 and burst to zero.

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1 Peter Mortensen