diff options
Diffstat (limited to 'downloader/download_manager.go')
| -rw-r--r-- | downloader/download_manager.go | 84 |
1 files changed, 79 insertions, 5 deletions
diff --git a/downloader/download_manager.go b/downloader/download_manager.go index fb7e883..004efc1 100644 --- a/downloader/download_manager.go +++ b/downloader/download_manager.go @@ -1,15 +1,89 @@ package downloader +import ( + "time" +) + // DownloadManager handles a download for a particular song. type DownloadManager struct { Url string - dlChans []<-chan []byte + Start time.Duration + Duration time.Duration + End time.Duration + + pb chan (<-chan []byte) + + info videoInfo } -func NewDownload(url string) DownloadManager { - return DownloadManager{ - Url: url, - dlChans: []<-chan []byte{}, +const clipTime = 10 * time.Second +const preloadCount = 5 + +func NewDownload(url string, startTime, dur time.Duration) (*DownloadManager, error) { + vInfo, err := info(url) + if err != nil { + return nil, err + } + + if dur == 0 { + dur = vInfo.Duration - startTime } + + dl := &DownloadManager{ + Url: url, + + Start: startTime, + Duration: dur, + End: startTime + dur, + + pb: make(chan (<-chan []byte), preloadCount), + info: *vInfo, + } + + go dl.schedule() + + return dl, nil +} + +func (d *DownloadManager) SendOn(ch chan<- []byte) <-chan struct{} { + out := make(chan struct{}, 1) + + go func() { + defer close(out) + for c := range d.pb { + for b := range c { + ch <- b + } + } + }() + + return out +} + +func (d *DownloadManager) schedule() { + go func() { + defer close(d.pb) + for i := 0; ; i++ { + clipStart := time.Duration(i)*clipTime + d.Start + clipEnd := time.Duration(i+1)*clipTime + d.Start + + if clipStart >= d.End { + return + } + + dur := clipTime + if clipEnd > d.End { + dur = d.End - clipStart + } + + ch, err := d.download(clipStart, dur) + if err != nil { + log.Errorf("error setting up download: %q", err) + return + } + + d.pb <- ch + } + }() } |
