You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用anacrolix/torrent库创建种子并做种失败问题排查

问题排查:anacrolix/torrent生成磁力链接后无法下载/获取元数据

问题描述

我想用Go语言的anacrolix/torrent库创建种子、生成磁力链接并做种,但运行代码后,生成的磁力链接既无法下载内容,也获取不到元数据,请帮忙排查代码中的遗漏点。

原代码

package main

import (
    "log"
    "time"
    "github.com/anacrolix/torrent"
    "github.com/anacrolix/torrent/bencode"
    "github.com/anacrolix/torrent/metainfo"
)

var builtinAnnounceList = [][]string{
    {"http://p4p.arenabg.com:1337/announce"},
    {"udp://tracker.opentrackr.org:1337/announce"},
    {"udp://tracker.openbittorrent.com:6969/announce"},
}

func main() {

    tmpComment:="Cool torrent description"
    tmpCreatedBy:="coolboys"
    tmpInfoName:="CoolInfoName"
    mi := metainfo.MetaInfo{
        AnnounceList: builtinAnnounceList,
    }

    mi.SetDefaults()
    
        mi.Comment = tmpComment

        mi.CreatedBy = tmpCreatedBy
    //}
    //mi.UrlList = args.Url//???????????
    info := metainfo.Info{
        PieceLength: 256 * 1024,
    }
    err := info.BuildFromFilePath("./TorrentFiles")//args.Root)
    if err != nil {
        log.Fatal(err)
    }

        info.Name =tmpInfoName
    mi.InfoBytes, err = bencode.Marshal(info)
    if err != nil {
        log.Fatal(err)
    }

    tmpMagnet:=mi.Magnet(nil,nil)
    log.Println("****",tmpMagnet)

    //
    cfg := torrent.NewDefaultClientConfig()
    cfg.Seed = true
    mainclient, ncerr := torrent.NewClient(cfg)
    if ncerr != nil {
        log.Println("new torrent client:", ncerr)
        return
    }
    defer mainclient.Close()    
    t, _ := mainclient.AddMagnet(tmpMagnet.String())

    for {   
        log.Println("******", t.Seeding())
        time.Sleep(8 * time.Second)

    }
}

核心问题与修复方案

1. 错误使用磁力链接添加种子,未提供本地元数据

你当前通过AddMagnet将磁力链接添加到客户端,但此时客户端并没有本地的完整元数据,需要依赖tracker或DHT去获取——这个过程可能因为tracker失效、网络防火墙拦截等原因失败,导致无法获取元数据也无法做种。

正确做法:直接将本地生成的完整MetaInfo对象添加到客户端,而不是用磁力链接,这样客户端立刻拥有所有元数据,能直接开始做种。

2. Info.Name覆盖时机不当

你在info.BuildFromFilePath之后才设置info.Name,但BuildFromFilePath会根据传入的路径自动生成Name字段,后续覆盖可能导致元数据内部不一致(虽然影响较小,但建议提前设置)。

3. 缺少元数据加载等待逻辑(若坚持用AddMagnet)

如果一定要用磁力链接添加,必须等待客户端获取到元数据后再做种,否则服务根本无法正常启动。需要添加t.WaitForInfo()或监听t.GotInfo()通道。

4. 未显式启用DHT

默认配置可能未启用DHT,导致无法通过DHT网络获取元数据或连接对等节点,建议显式开启。

修正后的代码

package main

import (
    "log"
    "time"
    "github.com/anacrolix/torrent"
    "github.com/anacrolix/torrent/bencode"
    "github.com/anacrolix/torrent/metainfo"
)

var builtinAnnounceList = [][]string{
    {"http://p4p.arenabg.com:1337/announce"},
    {"udp://tracker.opentrackr.org:1337/announce"},
    {"udp://tracker.openbittorrent.com:6969/announce"},
}

func main() {
    tmpComment := "Cool torrent description"
    tmpCreatedBy := "coolboys"
    tmpInfoName := "CoolInfoName"

    // 提前设置Info的Name,避免后续覆盖问题
    info := metainfo.Info{
        PieceLength: 256 * 1024,
        Name:        tmpInfoName,
    }
    // 从本地路径构建文件信息
    err := info.BuildFromFilePath("./TorrentFiles")
    if err != nil {
        log.Fatal(err)
    }

    // 构建完整的MetaInfo
    mi := metainfo.MetaInfo{
        AnnounceList: builtinAnnounceList,
        Comment:      tmpComment,
        CreatedBy:    tmpCreatedBy,
    }
    mi.SetDefaults()

    // 序列化Info到MetaInfo
    mi.InfoBytes, err = bencode.Marshal(info)
    if err != nil {
        log.Fatal(err)
    }

    // 生成并打印磁力链接
    tmpMagnet := mi.Magnet(nil, nil)
    log.Println("生成的磁力链接:", tmpMagnet)

    // 配置客户端,显式启用DHT
    cfg := torrent.NewDefaultClientConfig()
    cfg.Seed = true
    cfg.DHT = true
    cfg.DHTPort = 6881

    mainclient, ncerr := torrent.NewClient(cfg)
    if ncerr != nil {
        log.Println("创建客户端失败:", ncerr)
        return
    }
    defer mainclient.Close()

    // 直接添加完整的MetaInfo,确保客户端拥有所有元数据
    t, err := mainclient.AddTorrent(&mi)
    if err != nil {
        log.Println("添加种子失败:", err)
        return
    }

    // 等待种子元数据加载完成,确认可以开始做种
    select {
    case <-t.GotInfo():
        log.Println("种子准备完成,开始做种")
    case <-time.After(30 * time.Second):
        log.Println("等待种子准备超时")
        return
    }

    // 持续输出做种状态
    for {
        log.Println("当前做种状态:", t.Seeding())
        log.Println("已连接对等节点数:", len(t.Peers()))
        time.Sleep(8 * time.Second)
    }
}

内容的提问来源于stack exchange,提问作者Andrea Jung

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.03 09:06:39