ipn{,/local},cmd/tailscale: add "sync" flag and pref to disable control map poll

For manual (human) testing, this lets the user disable control plane
map polls with "tailscale set --sync=false" (which survives restarts)
and "tailscale set --sync" to restore.

A high severity health warning is shown while this is active.

Updates #12639
Updates #17945

Change-Id: I83668fa5de3b5e5e25444df0815ec2a859153a6d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
This commit is contained in:
Brad Fitzpatrick
2025-11-17 08:06:16 -08:00
committed by Brad Fitzpatrick
parent 165a24744e
commit f1cddc6ecf
10 changed files with 136 additions and 6 deletions
+3
View File
@@ -63,6 +63,7 @@ type setArgsT struct {
reportPosture bool
snat bool
statefulFiltering bool
sync bool
netfilterMode string
relayServerPort string
}
@@ -85,6 +86,7 @@ func newSetFlagSet(goos string, setArgs *setArgsT) *flag.FlagSet {
setf.BoolVar(&setArgs.updateApply, "auto-update", false, "automatically update to the latest available version")
setf.BoolVar(&setArgs.reportPosture, "report-posture", false, "allow management plane to gather device posture information")
setf.BoolVar(&setArgs.runWebClient, "webclient", false, "expose the web interface for managing this node over Tailscale at port 5252")
setf.BoolVar(&setArgs.sync, "sync", false, hidden+"actively sync configuration from the control plane (set to false only for network failure testing)")
setf.StringVar(&setArgs.relayServerPort, "relay-server-port", "", "UDP port number (0 will pick a random unused port) for the relay server to bind to, on all interfaces, or empty string to disable relay server functionality")
ffcomplete.Flag(setf, "exit-node", func(args []string) ([]string, ffcomplete.ShellCompDirective, error) {
@@ -149,6 +151,7 @@ func runSet(ctx context.Context, args []string) (retErr error) {
OperatorUser: setArgs.opUser,
NoSNAT: !setArgs.snat,
ForceDaemon: setArgs.forceDaemon,
Sync: opt.NewBool(setArgs.sync),
AutoUpdate: ipn.AutoUpdatePrefs{
Check: setArgs.updateCheck,
Apply: opt.NewBool(setArgs.updateApply),
+2 -1
View File
@@ -890,6 +890,7 @@ func init() {
addPrefFlagMapping("advertise-connector", "AppConnector")
addPrefFlagMapping("report-posture", "PostureChecking")
addPrefFlagMapping("relay-server-port", "RelayServerPort")
addPrefFlagMapping("sync", "Sync")
}
func addPrefFlagMapping(flagName string, prefNames ...string) {
@@ -925,7 +926,7 @@ func updateMaskedPrefsFromUpOrSetFlag(mp *ipn.MaskedPrefs, flagName string) {
if prefs, ok := prefsOfFlag[flagName]; ok {
for _, pref := range prefs {
f := reflect.ValueOf(mp).Elem()
for _, name := range strings.Split(pref, ".") {
for name := range strings.SplitSeq(pref, ".") {
f = f.FieldByName(name + "Set")
}
f.SetBool(true)