func WithTimeout(parent Context, timeout time.Duration) (Context, CancelFunc) {
return WithDeadline(parent, time.Now().Add(timeout))
}
查看代码,WithTimeout其实就是调用了WithDeadline
func WithDeadline(parent Context, d time.Time) (Context, CancelFunc) {
//1. 判断传入的Context是否为空
if parent == nil {
panic("cannot create context from nil parent")
}
//2.
if cur, ok := parent.Deadline(); ok && cur.Before(d) {
// The current deadline is already sooner than the new one.
return WithCancel(parent)
}
c := &timerCtx{
cancelCtx: newCancelCtx(parent),
deadline: d,
}
propagateCancel(parent, c)
dur := time.Until(d)
if dur <= 0 {
c.cancel(true, DeadlineExceeded) // deadline has already passed
return c, func() { c.cancel(false, Canceled) }
}
c.mu.Lock()
defer c.mu.Unlock()
if c.err == nil {
c.timer = time.AfterFunc(dur, func() {
c.cancel(true, DeadlineExceeded)
})
}
return c, func() { c.cancel(true, Canceled) }
}
WithDeadline
// 1.判断父context是否已经超时
// 2.创建一个timerCtx
// 3. 传播 timerCtx到所有子Context
// 4.判断距离deadline还剩多少时间
// 5.