Propagate announce interval, particularly for UDP
This commit is contained in:
parent
cbea87aaf3
commit
87e64b3088
|
@ -74,22 +74,23 @@ func (me Handler) ServeHTTP(w http.ResponseWriter, r *http.Request) {
|
|||
}
|
||||
portU64, err := strconv.ParseUint(vs.Get("port"), 0, 16)
|
||||
addrPort := netip.AddrPortFrom(addr, uint16(portU64))
|
||||
peers, err := me.Announce.Serve(r.Context(), tracker.AnnounceRequest{
|
||||
res := me.Announce.Serve(r.Context(), tracker.AnnounceRequest{
|
||||
InfoHash: infoHash,
|
||||
PeerId: peerId,
|
||||
Event: event,
|
||||
Port: addrPort.Port(),
|
||||
NumWant: -1,
|
||||
}, addrPort, tracker.GetPeersOpts{generics.Some[uint](200)})
|
||||
}, addrPort, tracker.GetPeersOpts{MaxCount: generics.Some[uint](200)})
|
||||
err = res.Err
|
||||
if err != nil {
|
||||
log.Printf("error serving announce: %v", err)
|
||||
http.Error(w, "error handling announce", http.StatusInternalServerError)
|
||||
return
|
||||
}
|
||||
var resp httpTracker.HttpResponse
|
||||
resp.Interval = 5 * 60
|
||||
resp.Interval = res.Interval.UnwrapOr(5 * 60)
|
||||
resp.Peers.Compact = true
|
||||
for _, peer := range peers {
|
||||
for _, peer := range res.Peers {
|
||||
if peer.Addr().Is4() {
|
||||
resp.Peers.List = append(resp.Peers.List, tracker.Peer{
|
||||
IP: peer.Addr().AsSlice(),
|
||||
|
|
|
@ -34,7 +34,15 @@ type AnnounceAddr = netip.AddrPort
|
|||
type AnnounceTracker interface {
|
||||
TrackAnnounce(ctx context.Context, req udp.AnnounceRequest, addr AnnounceAddr) error
|
||||
Scrape(ctx context.Context, infoHashes []InfoHash) ([]udp.ScrapeInfohashResult, error)
|
||||
GetPeers(ctx context.Context, infoHash InfoHash, opts GetPeersOpts) ([]PeerInfo, error)
|
||||
GetPeers(ctx context.Context, infoHash InfoHash, opts GetPeersOpts) ServerAnnounceResult
|
||||
}
|
||||
|
||||
type ServerAnnounceResult struct {
|
||||
Err error
|
||||
Peers []PeerInfo
|
||||
Interval generics.Option[int32]
|
||||
Leechers generics.Option[int32]
|
||||
Seeders generics.Option[int32]
|
||||
}
|
||||
|
||||
type AnnounceHandler struct {
|
||||
|
@ -91,7 +99,7 @@ var tracer = otel.Tracer("torrent.tracker.udp")
|
|||
|
||||
func (me *AnnounceHandler) Serve(
|
||||
ctx context.Context, req AnnounceRequest, addr AnnounceAddr, opts GetPeersOpts,
|
||||
) (peers []PeerInfo, err error) {
|
||||
) (ret ServerAnnounceResult) {
|
||||
ctx, span := tracer.Start(
|
||||
ctx,
|
||||
"AnnounceHandler.Serve",
|
||||
|
@ -108,11 +116,11 @@ func (me *AnnounceHandler) Serve(
|
|||
)
|
||||
defer span.End()
|
||||
defer func() {
|
||||
span.SetAttributes(attribute.Int("announce.get_peers.len", len(peers)))
|
||||
span.SetAttributes(attribute.Int("announce.get_peers.len", len(ret.Peers)))
|
||||
}()
|
||||
|
||||
err = me.AnnounceTracker.TrackAnnounce(ctx, req, addr)
|
||||
if err != nil {
|
||||
ret.Err = me.AnnounceTracker.TrackAnnounce(ctx, req, addr)
|
||||
if ret.Err != nil {
|
||||
return
|
||||
}
|
||||
infoHash := req.InfoHash
|
||||
|
@ -133,15 +141,15 @@ func (me *AnnounceHandler) Serve(
|
|||
opts.MaxCount = generics.Some(newCount)
|
||||
}
|
||||
}
|
||||
peers, err = me.AnnounceTracker.GetPeers(ctx, infoHash, opts)
|
||||
if err != nil {
|
||||
ret = me.AnnounceTracker.GetPeers(ctx, infoHash, opts)
|
||||
if ret.Err != nil {
|
||||
return
|
||||
}
|
||||
// Take whatever peers it has ready. If it's finished, it doesn't matter if we do this inside
|
||||
// the mutex or not.
|
||||
if op.Ok {
|
||||
curPeers, done := op.Value.getCurPeersAndDone()
|
||||
addMissing(peers, curPeers)
|
||||
addMissing(ret.Peers, curPeers)
|
||||
if done {
|
||||
// It doesn't get any better with this operation. Forget it.
|
||||
op.Ok = false
|
||||
|
@ -152,7 +160,7 @@ func (me *AnnounceHandler) Serve(
|
|||
// assuming the announcing peer might be that one. Really we should record a value to prevent
|
||||
// duplicate announces. Also don't announce upstream if we got no peers because the caller asked
|
||||
// for none.
|
||||
if !op.Ok && len(peers) <= 1 && opts.MaxCount.UnwrapOr(1) > 0 {
|
||||
if !op.Ok && len(ret.Peers) <= 1 && opts.MaxCount.UnwrapOr(1) > 0 {
|
||||
op.Value, op.Ok = me.ongoingUpstreamAugmentations[infoHash]
|
||||
if !op.Ok {
|
||||
op.Set(me.augmentPeersFromUpstream(req.InfoHash))
|
||||
|
@ -170,7 +178,7 @@ func (me *AnnounceHandler) Serve(
|
|||
case <-op.Value.doneAnnouncing:
|
||||
}
|
||||
cancel()
|
||||
addMissing(peers, op.Value.getCurPeers())
|
||||
addMissing(ret.Peers, op.Value.getCurPeers())
|
||||
}
|
||||
return
|
||||
}
|
||||
|
|
|
@ -104,12 +104,12 @@ func (me *Server) handleAnnounce(
|
|||
if addrFamily == udp.AddrFamilyIpv4 {
|
||||
opts.MaxCount = generics.Some[uint](150)
|
||||
}
|
||||
peers, err := me.Announce.Serve(ctx, req, announceAddr, opts)
|
||||
if err != nil {
|
||||
return err
|
||||
res := me.Announce.Serve(ctx, req, announceAddr, opts)
|
||||
if res.Err != nil {
|
||||
return res.Err
|
||||
}
|
||||
nodeAddrs := make([]krpc.NodeAddr, 0, len(peers))
|
||||
for _, p := range peers {
|
||||
nodeAddrs := make([]krpc.NodeAddr, 0, len(res.Peers))
|
||||
for _, p := range res.Peers {
|
||||
var ip net.IP
|
||||
switch addrFamily {
|
||||
default:
|
||||
|
@ -137,7 +137,9 @@ func (me *Server) handleAnnounce(
|
|||
if err != nil {
|
||||
return err
|
||||
}
|
||||
err = udp.Write(&buf, udp.AnnounceResponseHeader{})
|
||||
err = udp.Write(&buf, udp.AnnounceResponseHeader{
|
||||
Interval: res.Interval.UnwrapOr(5 * 60),
|
||||
})
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue