mirror of
https://github.com/rclone/rclone.git
synced 2026-10-10 15:01:37 -04:00
Shutdown was calling expiryTimer.Stop without holding ts.mu, so it could panic if OnExpiry had not created the timer yet, and raced the write in OnExpiry. Hold the lock and skip Stop when the timer is still nil. Fixes #9980
44 lines
1.1 KiB
Go
44 lines
1.1 KiB
Go
package oauthutil
|
|
|
|
import (
|
|
"context"
|
|
"encoding/json"
|
|
"testing"
|
|
"time"
|
|
|
|
"github.com/rclone/rclone/fs/config/configmap"
|
|
)
|
|
|
|
func newTestTokenSource(t *testing.T) *TokenSource {
|
|
t.Helper()
|
|
tok, err := json.Marshal(map[string]any{
|
|
"access_token": "A",
|
|
"token_type": "bearer",
|
|
"refresh_token": "R",
|
|
"expiry": time.Now().Add(time.Hour).UTC().Format(time.RFC3339),
|
|
})
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
_, ts, err := NewClient(context.Background(), "repro", configmap.Simple{"token": string(tok)},
|
|
&Config{TokenURL: "https://127.0.0.1:1/token"})
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
return ts
|
|
}
|
|
|
|
// Shutdown before the renewOnExpiry goroutine calls OnExpiry must not panic.
|
|
func TestShutdownBeforeRenewerStarts(t *testing.T) {
|
|
for i := 0; i < 1000; i++ {
|
|
NewRenew("repro", newTestTokenSource(t), func() error { return nil }).Shutdown()
|
|
}
|
|
}
|
|
|
|
// Shutdown must not race OnExpiry's write of expiryTimer.
|
|
func TestShutdownRacesOnExpiry(t *testing.T) {
|
|
r := NewRenew("repro", newTestTokenSource(t), func() error { return nil })
|
|
time.Sleep(50 * time.Millisecond)
|
|
r.Shutdown()
|
|
}
|