38 lines
809 B
Go
38 lines
809 B
Go
package transfer
|
|
|
|
import (
|
|
"io"
|
|
"time"
|
|
)
|
|
|
|
type ProgressCallback func(current int64, total int64, speed float64)
|
|
|
|
const (
|
|
ProgressInterval = 100 * time.Millisecond
|
|
)
|
|
|
|
// PassThroughReader 包装 io.Reader 以计算读取字节数
|
|
type PassThroughReader struct {
|
|
io.Reader
|
|
total int64
|
|
currentLen int64
|
|
lastTime time.Time
|
|
lastLen int64
|
|
callback ProgressCallback
|
|
}
|
|
|
|
func (pt *PassThroughReader) Read(p []byte) (int, error) {
|
|
n, err := pt.Reader.Read(p)
|
|
pt.currentLen += int64(n)
|
|
|
|
if time.Since(pt.lastTime) > ProgressInterval || err == io.EOF {
|
|
// 计算速度,单位为字节/秒
|
|
speed := float64(pt.currentLen-pt.lastLen) / time.Since(pt.lastTime).Seconds()
|
|
pt.callback(pt.currentLen, pt.total, speed)
|
|
pt.lastTime = time.Now()
|
|
pt.lastLen = pt.currentLen
|
|
}
|
|
|
|
return n, err
|
|
}
|