@@ -10,52 +10,36 @@ import (
1010 "golang.org/x/oauth2/clientcredentials"
1111
1212 "github.com/plgd-dev/kit/log"
13+ "github.com/plgd-dev/kit/net/http/transport"
1314 "golang.org/x/oauth2"
1415)
1516
1617// Manager holds certificates from filesystem watched for changes
1718type Manager struct {
18- mutex sync.Mutex
19- config clientcredentials.Config
20- tlsCfg * tls.Config
21- requestTimeout time.Duration
22- tickFrequency time.Duration
23- startRefreshToken time.Time
24- token * oauth2.Token
25- httpClient * http.Client
26- tokenErr error
27- doneWg sync.WaitGroup
28- done chan struct {}
19+ mutex sync.Mutex
20+ config clientcredentials.Config
21+ tlsCfg * tls.Config
22+ requestTimeout time.Duration
23+ token * oauth2.Token
24+ tokenErr error
25+ doneWg sync.WaitGroup
26+ done chan struct {}
2927}
3028
3129// NewManagerFromConfiguration creates a new oauth manager which refreshing token.
3230func NewManagerFromConfiguration (config Config , tlsCfg * tls.Config ) (* Manager , error ) {
3331 cfg := config .ToClientCrendtials ()
34- t := http .DefaultTransport .(* http.Transport ).Clone ()
35- t .MaxIdleConns = 1
36- t .MaxConnsPerHost = 1
37- t .MaxIdleConnsPerHost = 1
38- t .IdleConnTimeout = time .Second * 30
39- t .TLSClientConfig = tlsCfg
40- httpClient := & http.Client {
41- Transport : t ,
42- Timeout : config .RequestTimeout ,
43- }
44- token , startRefreshToken , err := getToken (cfg , httpClient , config .RequestTimeout )
32+ token , err := getToken (cfg , tlsCfg , config .RequestTimeout )
4533 if err != nil {
4634 return nil , err
4735 }
48-
4936 mgr := & Manager {
50- config : cfg ,
51- token : token ,
52- tlsCfg : tlsCfg ,
53- startRefreshToken : startRefreshToken ,
54- requestTimeout : config .RequestTimeout ,
55- httpClient : httpClient ,
56- tickFrequency : config .TickFrequency ,
57-
58- done : make (chan struct {}),
37+ config : cfg ,
38+ token : token ,
39+ tlsCfg : tlsCfg ,
40+
41+ requestTimeout : config .RequestTimeout ,
42+ done : make (chan struct {}),
5943 }
6044 mgr .doneWg .Add (1 )
6145
@@ -79,50 +63,48 @@ func (a *Manager) Close() {
7963 }
8064}
8165
82- func (a * Manager ) wantToRefresh () bool {
83- return time .Now ().After (a .startRefreshToken )
66+ func (a * Manager ) nextRenewal () time.Duration {
67+ t , _ := a .GetToken (context .Background ())
68+ now := time .Now ()
69+ lifetime := t .Expiry .Sub (now ) * 2 / 3
70+ if lifetime < a .requestTimeout {
71+ lifetime = a .requestTimeout
72+ }
73+ return lifetime
8474}
8575
86- func getToken (cfg clientcredentials.Config , httpClient * http. Client , requestTimeout time.Duration ) (* oauth2.Token , time. Time , error ) {
76+ func getToken (cfg clientcredentials.Config , tlsCfg * tls. Config , requestTimeout time.Duration ) (* oauth2.Token , error ) {
8777 ctx , cancel := context .WithTimeout (context .Background (), requestTimeout )
8878 defer cancel ()
8979
80+ t := transport .NewDefaultTransport ()
81+ t .TLSClientConfig = tlsCfg
82+ httpClient := & http.Client {Transport : t }
9083 ctx = context .WithValue (ctx , oauth2 .HTTPClient , httpClient )
9184
92- token , err := cfg .Token (ctx )
93- var startRefreshToken time.Time
94- if err == nil {
95- now := time .Now ()
96- startRefreshToken = now .Add (token .Expiry .Sub (now ) * 2 / 3 )
97- }
98- return token , startRefreshToken , err
85+ return cfg .Token (ctx )
9986}
10087
10188func (a * Manager ) refreshToken () {
102- token , startRefreshToken , err := getToken (a .config , a .httpClient , a .requestTimeout )
89+ token , err := getToken (a .config , a .tlsCfg , a .requestTimeout )
10390 if err != nil {
10491 log .Errorf ("cannot refresh token: %v" , err )
10592 }
10693 a .mutex .Lock ()
10794 defer a .mutex .Unlock ()
10895 a .token = token
10996 a .tokenErr = err
110- a .startRefreshToken = startRefreshToken
11197}
11298
11399func (a * Manager ) watchToken () {
114100 defer a .doneWg .Done ()
115- t := time .NewTicker (a .tickFrequency )
116- defer t .Stop ()
117-
118101 for {
102+ nextRenewal := a .nextRenewal ()
119103 select {
120104 case <- a .done :
121105 return
122- case <- t .C :
123- if a .wantToRefresh () {
124- a .refreshToken ()
125- }
106+ case <- time .After (nextRenewal ):
107+ a .refreshToken ()
126108 }
127109 }
128110}
0 commit comments