Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
29 changes: 23 additions & 6 deletions cmd/cloud-init-server/peer_removal_queue.go
Original file line number Diff line number Diff line change
Expand Up @@ -9,11 +9,17 @@ const (

type peerRemover interface {
RemovePeer(peerName string) error
GetPublicKey(peerName string) (string, bool)
}

type PeerRemovalQueue struct {
remover peerRemover
jobs chan string
jobs chan removalJob
}

type removalJob struct {
name string
key string
}

func NewPeerRemovalQueue(remover peerRemover) *PeerRemovalQueue {
Expand All @@ -23,7 +29,7 @@ func NewPeerRemovalQueue(remover peerRemover) *PeerRemovalQueue {
func newPeerRemovalQueue(remover peerRemover, workers int, buffer int) *PeerRemovalQueue {
queue := &PeerRemovalQueue{
remover: remover,
jobs: make(chan string, buffer),
jobs: make(chan removalJob, buffer),
}
for range workers {
go queue.work()
Expand All @@ -35,18 +41,29 @@ func (q *PeerRemovalQueue) TryEnqueue(peerName string) bool {
if q == nil || q.remover == nil {
return true
}
// Capture the current public key for the peer (if any).
key, _ := q.remover.GetPublicKey(peerName)
job := removalJob{name: peerName, key: key}
select {
case q.jobs <- peerName:
case q.jobs <- job:
return true
default:
return false
}
}

func (q *PeerRemovalQueue) work() {
for peerName := range q.jobs {
if err := q.remover.RemovePeer(peerName); err != nil {
log.Error().Err(err).Str("peer", peerName).Msg("failed to remove WireGuard peer")
for job := range q.jobs {
// Verify that the public key hasn't changed since enqueue time.
currentKey, ok := q.remover.GetPublicKey(job.name)
if ok && job.key != "" && currentKey != job.key {
// Stale removal – skip and log.
log.Warn().Str("peer", job.name).Str("queuedKey", job.key).Str("currentKey", currentKey).
Msg("stale removal job skipped")
continue
}
if err := q.remover.RemovePeer(job.name); err != nil {
log.Error().Err(err).Str("peer", job.name).Msg("failed to remove WireGuard peer")
}
}
}
5 changes: 5 additions & 0 deletions cmd/cloud-init-server/peer_removal_queue_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,11 @@ func (r *blockingPeerRemover) RemovePeer(peerName string) error {
return nil
}

// GetPublicKey implements peerRemover but returns no key for tests.
func (r *blockingPeerRemover) GetPublicKey(peerName string) (string, bool) {
return "", false
}

type phoneHomeSMDClient struct {
smdclient.FakeSMDClient
}
Expand Down
Loading