listDrivePeers returned every peer holding PeerCapabilityTaildriveSharer. That cap is an ACL grant usually given to a whole group or tag, so the result was most of the tailnet — including offline peers and peers with no reachable peerAPI — despite the doc comment claiming it mirrored LocalBackend.driveRemotesFromPeers.
It now applies the same conjunction as upstream (ipn/ipnlocal/drive.go): online, non-empty peerAPI base, sharer cap. buildPeerAPIURL was already called and its result discarded, so both new checks are free.
The doc comment also now states that the cap means a peer is allowed to share with us, not that it currently exposes a share.
Merging this is what lets webnet/webnet#165 point at webnet rather than this branch.
Verified by building the wasm (npm run build-go --workspace=packages/tsconnect in the consuming repo) and running that repo's tsconnect suite against a live headscale tailnet: 78 pass, 0 fail. Note that listDrivePeers returns [] on that tailnet — no node there carries the sharer cap — so the integration assertions do not exercise the filter itself; that was checked by reading it against upstream's Available closure.
Fork-side half of webnet/webnet#165 (fixes webnet/webnet#143).
`listDrivePeers` returned every peer holding `PeerCapabilityTaildriveSharer`. That cap is an ACL grant usually given to a whole group or tag, so the result was most of the tailnet — including offline peers and peers with no reachable peerAPI — despite the doc comment claiming it mirrored `LocalBackend.driveRemotesFromPeers`.
It now applies the same conjunction as upstream (`ipn/ipnlocal/drive.go`): online, non-empty peerAPI base, sharer cap. `buildPeerAPIURL` was already called and its result discarded, so both new checks are free.
The doc comment also now states that the cap means a peer is *allowed* to share with us, not that it currently exposes a share.
Merging this is what lets webnet/webnet#165 point at `webnet` rather than this branch.
Verified by building the wasm (`npm run build-go --workspace=packages/tsconnect` in the consuming repo) and running that repo's tsconnect suite against a live headscale tailnet: 78 pass, 0 fail. Note that `listDrivePeers` returns `[]` on that tailnet — no node there carries the sharer cap — so the integration assertions do not exercise the filter itself; that was checked by reading it against upstream's `Available` closure.
listDrivePeers only checked PeerCapabilityTaildriveSharer, which is
usually granted to a whole group or tag, so it returned most of the
tailnet including offline peers and peers with no reachable peerAPI.
Apply the same conjunction as LocalBackend.driveRemotesFromPeers.
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.
Fork-side half of webnet/webnet#165 (fixes webnet/webnet#143).
listDrivePeersreturned every peer holdingPeerCapabilityTaildriveSharer. That cap is an ACL grant usually given to a whole group or tag, so the result was most of the tailnet — including offline peers and peers with no reachable peerAPI — despite the doc comment claiming it mirroredLocalBackend.driveRemotesFromPeers.It now applies the same conjunction as upstream (
ipn/ipnlocal/drive.go): online, non-empty peerAPI base, sharer cap.buildPeerAPIURLwas already called and its result discarded, so both new checks are free.The doc comment also now states that the cap means a peer is allowed to share with us, not that it currently exposes a share.
Merging this is what lets webnet/webnet#165 point at
webnetrather than this branch.Verified by building the wasm (
npm run build-go --workspace=packages/tsconnectin the consuming repo) and running that repo's tsconnect suite against a live headscale tailnet: 78 pass, 0 fail. Note thatlistDrivePeersreturns[]on that tailnet — no node there carries the sharer cap — so the integration assertions do not exercise the filter itself; that was checked by reading it against upstream'sAvailableclosure.