systemmin / wxdown

微信公众号文章离线保存
Apache License 2.0
63 stars 15 forks source link

并发下载应该加上go关键字 #2

Closed xylophonee closed 1 month ago

xylophonee commented 2 months ago

比如这里,DownloadHtml前应该加上go关键字

        for i, item := range results {
            log.Printf("当前下标:[%d]\n", i+1)
            log.Printf("当前资源:[%s]\n", item)
            wg.Add(1)
            biz.DownloadHtml(item, defaultDataPath, utils.Iif(len(folder) > 0, folder, album.Name), sem, &wg, filePaths, cfg.Thread.Image)
        }

下面是一个测试:

func Test_Con(t *testing.T) {
    results := []string{"1", "2", "3", "4", "5", "6", "7"}
    // 定义 goroutines 等待组
    var wg sync.WaitGroup
    // 并发数量
    maxConcurrency := 3
    // 创建 sem 通道
    sem := make(chan struct{}, maxConcurrency)
    // 用于存储文件地址的通道
    filePaths := make(chan string, len(results))
    for i, item := range results {
        log.Printf("当前下标:[%d]\n", i+1)
        log.Printf("当前资源:[%s]\n", item)
        wg.Add(1)
        go down(item, sem, &wg, filePaths)
    }
    // 等待所有下载完成
    go func() {
        wg.Wait()
        close(filePaths)
    }()
    for f := range filePaths {
        fmt.Println("处理file:", f)
    }
}

func down(urlStr string, sem chan struct{}, wg *sync.WaitGroup, filePaths chan string) {
    defer wg.Done()

    // 从信号量中获取一个令牌
    sem <- struct{}{}
    defer func() { <-sem }() // 确保在函数返回时释放信号量令牌

    fmt.Println("下载中", urlStr)
    time.Sleep(1 * time.Second)
    fmt.Println("下载完成", urlStr)

    // 发送文件路径到通道
    filePaths <- urlStr

}
systemmin commented 2 months ago

对 go 这个多线程不熟😂,我就说并行为什么下载还那么慢。之前加go存在重复下载问题,可能是代码写的有点问题,没处理好同步

xylophonee commented 2 months ago

我也初学者😂 重复下载?我测试没遇到呢

systemmin commented 2 months ago

现在应该没问题了

xylophonee commented 2 months ago

写了个自动获取历史文章的demo,有意合并吗

https://github.com/systemmin/wxdown/commit/f8e219fd295fd73d7285f863a1dba000e7738068

systemmin commented 2 months ago

写了个自动获取历史文章的demo,有意合并吗

f8e219f

好的我先看下,这种方式是可以获取到历史,同时也有几个问题

https://mp.weixin.qq.com/mp/profile_ext?action=home&__biz=微信公众号biz&scene=124

systemmin commented 2 months ago

还有一种方式就是使用go实现代理PC端,获取profile_ext所需要的参数,不借助第三方抓包工具