Merge pull request #7639 from heyitsanthony/fix-userflag-timeout

clientv3: respect dial timeout in auth
This commit is contained in:
Anthony Romano 2017-04-03 09:30:48 -07:00 committed by GitHub
commit f13bea0bb0
2 changed files with 49 additions and 26 deletions

View File

@ -294,8 +294,16 @@ func (c *Client) dial(endpoint string, dopts ...grpc.DialOption) (*grpc.ClientCo
tokenMu: &sync.RWMutex{}, tokenMu: &sync.RWMutex{},
} }
err := c.getToken(c.ctx) ctx := c.ctx
if err != nil { if c.cfg.DialTimeout > 0 {
cctx, cancel := context.WithTimeout(ctx, c.cfg.DialTimeout)
defer cancel()
ctx = cctx
}
if err := c.getToken(ctx); err != nil {
if err == ctx.Err() && ctx.Err() != c.ctx.Err() {
err = grpc.ErrClientConnTimeout
}
return nil, err return nil, err
} }
@ -351,6 +359,8 @@ func newClient(cfg *Config) (*Client, error) {
client.balancer = newSimpleBalancer(cfg.Endpoints) client.balancer = newSimpleBalancer(cfg.Endpoints)
conn, err := client.dial(cfg.Endpoints[0], grpc.WithBalancer(client.balancer)) conn, err := client.dial(cfg.Endpoints[0], grpc.WithBalancer(client.balancer))
if err != nil { if err != nil {
client.cancel()
client.balancer.Close()
return nil, err return nil, err
} }
client.conn = conn client.conn = conn
@ -374,6 +384,7 @@ func newClient(cfg *Config) (*Client, error) {
default: default:
} }
client.cancel() client.cancel()
client.balancer.Close()
conn.Close() conn.Close()
return nil, err return nil, err
} }

View File

@ -81,33 +81,45 @@ func TestDialCancel(t *testing.T) {
func TestDialTimeout(t *testing.T) { func TestDialTimeout(t *testing.T) {
defer testutil.AfterTest(t) defer testutil.AfterTest(t)
donec := make(chan error) testCfgs := []Config{
go func() { Config{
// without timeout, dial continues forever on ipv4 blackhole
cfg := Config{
Endpoints: []string{"http://254.0.0.1:12345"}, Endpoints: []string{"http://254.0.0.1:12345"},
DialTimeout: 2 * time.Second} DialTimeout: 2 * time.Second,
c, err := New(cfg) },
if c != nil || err == nil { Config{
t.Errorf("new client should fail") Endpoints: []string{"http://254.0.0.1:12345"},
} DialTimeout: time.Second,
donec <- err Username: "abc",
}() Password: "def",
},
time.Sleep(10 * time.Millisecond)
select {
case err := <-donec:
t.Errorf("dial didn't wait (%v)", err)
default:
} }
select { for i, cfg := range testCfgs {
case <-time.After(5 * time.Second): donec := make(chan error)
t.Errorf("failed to timeout dial on time") go func() {
case err := <-donec: // without timeout, dial continues forever on ipv4 blackhole
if err != grpc.ErrClientConnTimeout { c, err := New(cfg)
t.Errorf("unexpected error %v, want %v", err, grpc.ErrClientConnTimeout) if c != nil || err == nil {
t.Errorf("#%d: new client should fail", i)
}
donec <- err
}()
time.Sleep(10 * time.Millisecond)
select {
case err := <-donec:
t.Errorf("#%d: dial didn't wait (%v)", i, err)
default:
}
select {
case <-time.After(5 * time.Second):
t.Errorf("#%d: failed to timeout dial on time", i)
case err := <-donec:
if err != grpc.ErrClientConnTimeout {
t.Errorf("#%d: unexpected error %v, want %v", i, err, grpc.ErrClientConnTimeout)
}
} }
} }
} }