diff options
| author | Mario Minardi <mario@tailscale.com> | 2026-01-13 13:11:19 -0700 |
|---|---|---|
| committer | Mario Minardi <mario@tailscale.com> | 2026-01-13 14:01:45 -0700 |
| commit | 7888d5a05d63c63ef7f18d2fa7677b002f5ba9a3 (patch) | |
| tree | dfc014d4b881f3aea3ae3c70564ef38bbd82065a | |
| parent | c5ec7d29ffa254c27d37cdf41842ec180d073d46 (diff) | |
| download | tailscale-mpminardi/tsnet-test.tar.xz tailscale-mpminardi/tsnet-test.zip | |
testingmpminardi/tsnet-test
| -rw-r--r-- | tsnet/tsnet.go | 31 |
1 files changed, 26 insertions, 5 deletions
diff --git a/tsnet/tsnet.go b/tsnet/tsnet.go index 595b052ab..aec6ae9ea 100644 --- a/tsnet/tsnet.go +++ b/tsnet/tsnet.go @@ -139,6 +139,14 @@ type Server struct { // field is not used. IDToken string + // Audience, if non-empty, is the audience to use when requesting + // an ID token from a well-known identity provider to exchange + // with the control server for workload identity federation. It + // will be preferred over the TS_AUDIENCE environment variable. If + // the node is already created (from state previously stored in Store), + // then this field is not used. + Audience string + // ControlURL optionally specifies the coordination server URL. // If empty, the Tailscale default is used. ControlURL string @@ -567,6 +575,13 @@ func (s *Server) getIDToken() string { return os.Getenv("TS_ID_TOKEN") } +func (s *Server) getAudience() string { + if v := s.Audience; v != "" { + return v + } + return os.Getenv("TS_AUDIENCE") +} + func (s *Server) start() (reterr error) { var closePool closeOnErrorPool defer closePool.closeAllIfError(&reterr) @@ -805,13 +820,19 @@ func (s *Server) resolveAuthKey() (string, error) { if wifOk && authKey == "" { clientID := s.getClientID() idToken := s.getIDToken() - if clientID != "" && idToken == "" { - return "", fmt.Errorf("client ID for workload identity federation found, but ID token is empty") + audience := s.getAudience() + if clientID != "" && idToken == "" && audience == "" { + return "", fmt.Errorf("client ID for workload identity federation found, but ID token and audience are empty") } - if clientID == "" && idToken != "" { - return "", fmt.Errorf("ID token for workload identity federation found, but client ID is empty") + if clientID == "" { + if idToken != "" { + return "", fmt.Errorf("ID token for workload identity federation found, but client ID is empty") + } + if audience != "" { + return "", fmt.Errorf("audience for workload identity federation found, but client ID is empty") + } } - authKey, err = resolveViaWIF(s.shutdownCtx, s.ControlURL, clientID, idToken, "", s.AdvertiseTags) + authKey, err = resolveViaWIF(s.shutdownCtx, s.ControlURL, clientID, idToken, audience, s.AdvertiseTags) if err != nil { return "", err } |
