mirror of
https://github.com/AvengeMedia/DankMaterialShell.git
synced 2026-10-21 18:54:01 -04:00
tailscale: handle profile switches and bus updates reactively (#3427)
* tailscale: handle profile switches and bus updates reactively
* tailscale: address review feedback on test coverage and dead code
(cherry picked from commit 218f7f752f)
This commit is contained in:
committed by
bbedward
parent
a5ffd18596
commit
fde2181c3b
@@ -33,6 +33,7 @@ func convertStatus(status *ipnstate.Status) *TailscaleState {
|
||||
|
||||
if status.Self != nil {
|
||||
state.Self = convertPeerStatus(status.Self, users)
|
||||
state.Self.Online = true
|
||||
}
|
||||
|
||||
if len(status.Peer) > 0 {
|
||||
|
||||
@@ -95,7 +95,7 @@ func newManager(client tailscaleClient) *Manager {
|
||||
func (m *Manager) watchLoop(ctx context.Context) {
|
||||
defer m.watchWG.Done()
|
||||
|
||||
mask := ipn.NotifyInitialState | ipn.NotifyInitialNetMap | ipn.NotifyRateLimit
|
||||
mask := ipn.NotifyInitialState | ipn.NotifyInitialPrefs | ipn.NotifyInitialNetMap | ipn.NotifyRateLimit
|
||||
backoff := time.Second
|
||||
unreachableSent := false
|
||||
|
||||
@@ -122,8 +122,13 @@ func (m *Manager) watchLoop(ctx context.Context) {
|
||||
log.Info("[Tailscale] Connected to IPN bus")
|
||||
m.markAvailable()
|
||||
|
||||
select {
|
||||
case m.dirty <- struct{}{}:
|
||||
default:
|
||||
}
|
||||
|
||||
for {
|
||||
notify, err := watcher.Next()
|
||||
_, err := watcher.Next()
|
||||
if err != nil {
|
||||
log.Warnf("[Tailscale] IPN bus error: %v", err)
|
||||
break
|
||||
@@ -131,9 +136,6 @@ func (m *Manager) watchLoop(ctx context.Context) {
|
||||
|
||||
backoff = time.Second
|
||||
|
||||
if notify.State == nil && notify.NetMap == nil { //nolint:staticcheck // NetMap is deprecated upstream but still the only activity signal on some platforms
|
||||
continue
|
||||
}
|
||||
select {
|
||||
case m.dirty <- struct{}{}:
|
||||
default:
|
||||
|
||||
@@ -418,3 +418,55 @@ func TestManager_Actions_PropagateError(t *testing.T) {
|
||||
assert.Error(t, m.SetExitNode("nABC123"))
|
||||
assert.Error(t, m.SetAllowLANAccess(true))
|
||||
}
|
||||
|
||||
type dynamicWatcher struct {
|
||||
ctx context.Context
|
||||
ch chan ipn.Notify
|
||||
}
|
||||
|
||||
func (w *dynamicWatcher) Next() (ipn.Notify, error) {
|
||||
select {
|
||||
case n, ok := <-w.ch:
|
||||
if !ok {
|
||||
return ipn.Notify{}, fmt.Errorf("watcher closed")
|
||||
}
|
||||
return n, nil
|
||||
case <-w.ctx.Done():
|
||||
return ipn.Notify{}, w.ctx.Err()
|
||||
}
|
||||
}
|
||||
|
||||
func (w *dynamicWatcher) Close() error {
|
||||
return nil
|
||||
}
|
||||
|
||||
func TestWatchLoop_NotifyWithoutStateOrNetMap(t *testing.T) {
|
||||
var statusCalls atomic.Int32
|
||||
notifyCh := make(chan ipn.Notify, 1)
|
||||
|
||||
client := &mockClient{
|
||||
watchFn: func(ctx context.Context, mask ipn.NotifyWatchOpt) (ipnBusWatcher, error) {
|
||||
return &dynamicWatcher{ctx: ctx, ch: notifyCh}, nil
|
||||
},
|
||||
statusFn: func(ctx context.Context) (*ipnstate.Status, error) {
|
||||
statusCalls.Add(1)
|
||||
return runningStatus(), nil
|
||||
},
|
||||
}
|
||||
|
||||
m := newManager(client)
|
||||
defer m.Close()
|
||||
|
||||
// Wait for the initial connect-time status call to complete.
|
||||
require.Eventually(t, func() bool {
|
||||
return statusCalls.Load() == 1
|
||||
}, 2*time.Second, 10*time.Millisecond)
|
||||
|
||||
// Send an event with State == nil and NetMap == nil.
|
||||
notifyCh <- ipn.Notify{Engine: &ipn.EngineStatus{}}
|
||||
|
||||
// Verify that the notification without State or NetMap triggers a second status call.
|
||||
require.Eventually(t, func() bool {
|
||||
return statusCalls.Load() >= 2
|
||||
}, 2*time.Second, 10*time.Millisecond)
|
||||
}
|
||||
|
||||
@@ -34,6 +34,10 @@ PluginComponent {
|
||||
TailscaleService.connectTailscale(null);
|
||||
}
|
||||
|
||||
onCcWidgetExpanded: {
|
||||
TailscaleService.refresh(null);
|
||||
}
|
||||
|
||||
ccDetailContent: Component {
|
||||
Rectangle {
|
||||
id: detailRoot
|
||||
|
||||
@@ -207,6 +207,10 @@ Singleton {
|
||||
}
|
||||
|
||||
function isMine(peer) {
|
||||
if (!peer)
|
||||
return false;
|
||||
if (selfNode && (peer === selfNode || peer.id === selfNode.id))
|
||||
return true;
|
||||
const myOwner = selfNode ? (selfNode.owner || "") : "";
|
||||
if (peer.owner === myOwner && myOwner !== "")
|
||||
return true;
|
||||
|
||||
Reference in New Issue
Block a user