mirror of
https://github.com/netbirdio/netbird.git
synced 2026-09-21 22:29:08 +02:00
Merge branch 'main' into fix/ice-handshake
This commit is contained in:
+15
-15
@@ -17,7 +17,7 @@ import (
|
||||
"github.com/netbirdio/netbird/client/proto"
|
||||
"github.com/netbirdio/netbird/client/server"
|
||||
nbstatus "github.com/netbirdio/netbird/client/status"
|
||||
mgmProto "github.com/netbirdio/netbird/management/proto"
|
||||
mgmProto "github.com/netbirdio/netbird/shared/management/proto"
|
||||
"github.com/netbirdio/netbird/upload-server/types"
|
||||
)
|
||||
|
||||
@@ -77,11 +77,11 @@ var forCmd = &cobra.Command{
|
||||
|
||||
var persistenceCmd = &cobra.Command{
|
||||
Use: "persistence [on|off]",
|
||||
Short: "Set network map memory persistence",
|
||||
Long: `Configure whether the latest network map should persist in memory. When enabled, the last known network map will be kept in memory.`,
|
||||
Short: "Set sync response memory persistence",
|
||||
Long: `Configure whether the latest sync response should persist in memory. When enabled, the last known sync response will be kept in memory.`,
|
||||
Example: " netbird debug persistence on",
|
||||
Args: cobra.ExactArgs(1),
|
||||
RunE: setNetworkMapPersistence,
|
||||
RunE: setSyncResponsePersistence,
|
||||
}
|
||||
|
||||
func debugBundle(cmd *cobra.Command, _ []string) error {
|
||||
@@ -206,11 +206,11 @@ func runForDuration(cmd *cobra.Command, args []string) error {
|
||||
|
||||
time.Sleep(1 * time.Second)
|
||||
|
||||
// Enable network map persistence before bringing the service up
|
||||
if _, err := client.SetNetworkMapPersistence(cmd.Context(), &proto.SetNetworkMapPersistenceRequest{
|
||||
// Enable sync response persistence before bringing the service up
|
||||
if _, err := client.SetSyncResponsePersistence(cmd.Context(), &proto.SetSyncResponsePersistenceRequest{
|
||||
Enabled: true,
|
||||
}); err != nil {
|
||||
return fmt.Errorf("failed to enable network map persistence: %v", status.Convert(err).Message())
|
||||
return fmt.Errorf("failed to enable sync response persistence: %v", status.Convert(err).Message())
|
||||
}
|
||||
|
||||
if _, err := client.Up(cmd.Context(), &proto.UpRequest{}); err != nil {
|
||||
@@ -273,7 +273,7 @@ func runForDuration(cmd *cobra.Command, args []string) error {
|
||||
return nil
|
||||
}
|
||||
|
||||
func setNetworkMapPersistence(cmd *cobra.Command, args []string) error {
|
||||
func setSyncResponsePersistence(cmd *cobra.Command, args []string) error {
|
||||
conn, err := getClient(cmd)
|
||||
if err != nil {
|
||||
return err
|
||||
@@ -290,14 +290,14 @@ func setNetworkMapPersistence(cmd *cobra.Command, args []string) error {
|
||||
}
|
||||
|
||||
client := proto.NewDaemonServiceClient(conn)
|
||||
_, err = client.SetNetworkMapPersistence(cmd.Context(), &proto.SetNetworkMapPersistenceRequest{
|
||||
_, err = client.SetSyncResponsePersistence(cmd.Context(), &proto.SetSyncResponsePersistenceRequest{
|
||||
Enabled: persistence == "on",
|
||||
})
|
||||
if err != nil {
|
||||
return fmt.Errorf("failed to set network map persistence: %v", status.Convert(err).Message())
|
||||
return fmt.Errorf("failed to set sync response persistence: %v", status.Convert(err).Message())
|
||||
}
|
||||
|
||||
cmd.Printf("Network map persistence set to: %s\n", persistence)
|
||||
cmd.Printf("Sync response persistence set to: %s\n", persistence)
|
||||
return nil
|
||||
}
|
||||
|
||||
@@ -357,13 +357,13 @@ func formatDuration(d time.Duration) string {
|
||||
}
|
||||
|
||||
func generateDebugBundle(config *profilemanager.Config, recorder *peer.Status, connectClient *internal.ConnectClient, logFilePath string) {
|
||||
var networkMap *mgmProto.NetworkMap
|
||||
var syncResponse *mgmProto.SyncResponse
|
||||
var err error
|
||||
|
||||
if connectClient != nil {
|
||||
networkMap, err = connectClient.GetLatestNetworkMap()
|
||||
syncResponse, err = connectClient.GetLatestSyncResponse()
|
||||
if err != nil {
|
||||
log.Warnf("Failed to get latest network map: %v", err)
|
||||
log.Warnf("Failed to get latest sync response: %v", err)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -371,7 +371,7 @@ func generateDebugBundle(config *profilemanager.Config, recorder *peer.Status, c
|
||||
debug.GeneratorDependencies{
|
||||
InternalConfig: config,
|
||||
StatusRecorder: recorder,
|
||||
NetworkMap: networkMap,
|
||||
SyncResponse: syncResponse,
|
||||
LogFile: logFilePath,
|
||||
},
|
||||
debug.BundleConfig{
|
||||
|
||||
@@ -0,0 +1,57 @@
|
||||
package cmd
|
||||
|
||||
import (
|
||||
"context"
|
||||
"fmt"
|
||||
"os/user"
|
||||
"time"
|
||||
|
||||
"github.com/spf13/cobra"
|
||||
|
||||
"github.com/netbirdio/netbird/client/proto"
|
||||
)
|
||||
|
||||
var logoutCmd = &cobra.Command{
|
||||
Use: "logout",
|
||||
Short: "logout from the Netbird Management Service and delete peer",
|
||||
RunE: func(cmd *cobra.Command, args []string) error {
|
||||
SetFlagsFromEnvVars(rootCmd)
|
||||
|
||||
cmd.SetOut(cmd.OutOrStdout())
|
||||
|
||||
ctx, cancel := context.WithTimeout(context.Background(), time.Second*7)
|
||||
defer cancel()
|
||||
|
||||
conn, err := DialClientGRPCServer(ctx, daemonAddr)
|
||||
if err != nil {
|
||||
return fmt.Errorf("connect to daemon: %v", err)
|
||||
}
|
||||
defer conn.Close()
|
||||
|
||||
daemonClient := proto.NewDaemonServiceClient(conn)
|
||||
|
||||
req := &proto.LogoutRequest{}
|
||||
|
||||
if profileName != "" {
|
||||
req.ProfileName = &profileName
|
||||
|
||||
currUser, err := user.Current()
|
||||
if err != nil {
|
||||
return fmt.Errorf("get current user: %v", err)
|
||||
}
|
||||
username := currUser.Username
|
||||
req.Username = &username
|
||||
}
|
||||
|
||||
if _, err := daemonClient.Logout(ctx, req); err != nil {
|
||||
return fmt.Errorf("logout: %v", err)
|
||||
}
|
||||
|
||||
cmd.Println("Logged out successfully")
|
||||
return nil
|
||||
},
|
||||
}
|
||||
|
||||
func init() {
|
||||
logoutCmd.PersistentFlags().StringVar(&profileName, profileNameFlag, "", profileNameDesc)
|
||||
}
|
||||
@@ -3,9 +3,8 @@ package cmd
|
||||
import (
|
||||
"context"
|
||||
"fmt"
|
||||
"time"
|
||||
|
||||
"os/user"
|
||||
"time"
|
||||
|
||||
"github.com/spf13/cobra"
|
||||
|
||||
@@ -22,10 +21,11 @@ var profileCmd = &cobra.Command{
|
||||
}
|
||||
|
||||
var profileListCmd = &cobra.Command{
|
||||
Use: "list",
|
||||
Short: "list all profiles",
|
||||
Long: `List all available profiles in the Netbird client.`,
|
||||
RunE: listProfilesFunc,
|
||||
Use: "list",
|
||||
Short: "list all profiles",
|
||||
Long: `List all available profiles in the Netbird client.`,
|
||||
Aliases: []string{"ls"},
|
||||
RunE: listProfilesFunc,
|
||||
}
|
||||
|
||||
var profileAddCmd = &cobra.Command{
|
||||
|
||||
+2
-1
@@ -127,12 +127,13 @@ func init() {
|
||||
rootCmd.PersistentFlags().StringVar(&preSharedKey, preSharedKeyFlag, "", "Sets Wireguard PreSharedKey property. If set, then only peers that have the same key can communicate.")
|
||||
rootCmd.PersistentFlags().StringVarP(&hostName, "hostname", "n", "", "Sets a custom hostname for the device")
|
||||
rootCmd.PersistentFlags().BoolVarP(&anonymizeFlag, "anonymize", "A", false, "anonymize IP addresses and non-netbird.io domains in logs and status output")
|
||||
rootCmd.PersistentFlags().StringVarP(&configPath, "config", "c", defaultConfigPath, "(DEPRECATED) Netbird config file location")
|
||||
rootCmd.PersistentFlags().StringVarP(&configPath, "config", "c", defaultConfigPath, "Overrides the default profile file location")
|
||||
|
||||
rootCmd.AddCommand(upCmd)
|
||||
rootCmd.AddCommand(downCmd)
|
||||
rootCmd.AddCommand(statusCmd)
|
||||
rootCmd.AddCommand(loginCmd)
|
||||
rootCmd.AddCommand(logoutCmd)
|
||||
rootCmd.AddCommand(versionCmd)
|
||||
rootCmd.AddCommand(sshCmd)
|
||||
rootCmd.AddCommand(networksCMD)
|
||||
|
||||
@@ -61,7 +61,7 @@ func (p *program) Start(svc service.Service) error {
|
||||
}
|
||||
}
|
||||
|
||||
serverInstance := server.New(p.ctx, util.FindFirstLogPath(logFiles), profilesDisabled)
|
||||
serverInstance := server.New(p.ctx, util.FindFirstLogPath(logFiles), configPath, profilesDisabled)
|
||||
if err := serverInstance.Start(); err != nil {
|
||||
log.Fatalf("failed to start daemon: %v", err)
|
||||
}
|
||||
|
||||
@@ -41,6 +41,10 @@ func buildServiceArguments() []string {
|
||||
args = append(args, "--management-url", managementURL)
|
||||
}
|
||||
|
||||
if configPath != "" {
|
||||
args = append(args, "--config", configPath)
|
||||
}
|
||||
|
||||
for _, logFile := range logFiles {
|
||||
args = append(args, "--log-file", logFile)
|
||||
}
|
||||
|
||||
@@ -26,9 +26,9 @@ import (
|
||||
|
||||
clientProto "github.com/netbirdio/netbird/client/proto"
|
||||
client "github.com/netbirdio/netbird/client/server"
|
||||
mgmtProto "github.com/netbirdio/netbird/management/proto"
|
||||
mgmtProto "github.com/netbirdio/netbird/shared/management/proto"
|
||||
mgmt "github.com/netbirdio/netbird/management/server"
|
||||
sigProto "github.com/netbirdio/netbird/signal/proto"
|
||||
sigProto "github.com/netbirdio/netbird/shared/signal/proto"
|
||||
sig "github.com/netbirdio/netbird/signal/server"
|
||||
)
|
||||
|
||||
@@ -134,7 +134,7 @@ func startClientDaemon(
|
||||
s := grpc.NewServer()
|
||||
|
||||
server := client.New(ctx,
|
||||
"", false)
|
||||
"", "", false)
|
||||
if err := server.Start(); err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
|
||||
+12
-2
@@ -23,7 +23,7 @@ import (
|
||||
"github.com/netbirdio/netbird/client/internal/profilemanager"
|
||||
"github.com/netbirdio/netbird/client/proto"
|
||||
"github.com/netbirdio/netbird/client/system"
|
||||
"github.com/netbirdio/netbird/management/domain"
|
||||
"github.com/netbirdio/netbird/shared/management/domain"
|
||||
"github.com/netbirdio/netbird/util"
|
||||
)
|
||||
|
||||
@@ -79,7 +79,7 @@ func init() {
|
||||
|
||||
upCmd.PersistentFlags().BoolVar(&noBrowser, noBrowserFlag, false, noBrowserDesc)
|
||||
upCmd.PersistentFlags().StringVar(&profileName, profileNameFlag, "", profileNameDesc)
|
||||
upCmd.PersistentFlags().StringVarP(&configPath, "config", "c", "", "(DEPRECATED) Netbird config file location")
|
||||
upCmd.PersistentFlags().StringVarP(&configPath, "config", "c", "", "(DEPRECATED) Netbird config file location. ")
|
||||
|
||||
}
|
||||
|
||||
@@ -146,6 +146,11 @@ func upFunc(cmd *cobra.Command, args []string) error {
|
||||
}
|
||||
|
||||
func runInForegroundMode(ctx context.Context, cmd *cobra.Command, activeProf *profilemanager.Profile) error {
|
||||
// override the default profile filepath if provided
|
||||
if configPath != "" {
|
||||
_ = profilemanager.NewServiceManager(configPath)
|
||||
}
|
||||
|
||||
err := handleRebrand(cmd)
|
||||
if err != nil {
|
||||
return err
|
||||
@@ -197,6 +202,11 @@ func runInForegroundMode(ctx context.Context, cmd *cobra.Command, activeProf *pr
|
||||
}
|
||||
|
||||
func runInDaemonMode(ctx context.Context, cmd *cobra.Command, pm *profilemanager.ProfileManager, activeProf *profilemanager.Profile, profileSwitched bool) error {
|
||||
// Check if deprecated config flag is set and show warning
|
||||
if cmd.Flag("config").Changed && configPath != "" {
|
||||
cmd.PrintErrf("Warning: Config flag is deprecated on up command, it should be set as a service argument with $NB_CONFIG environment or with \"-config\" flag; netbird service reconfigure --service-env=\"NB_CONFIG=<file_path>\" or netbird service run --config=<file_path>\n")
|
||||
}
|
||||
|
||||
customDNSAddressConverted, err := parseCustomDNSAddress(cmd.Flag(dnsResolverAddress).Changed)
|
||||
if err != nil {
|
||||
return fmt.Errorf("parse custom DNS address: %v", err)
|
||||
|
||||
@@ -9,7 +9,7 @@ import (
|
||||
|
||||
log "github.com/sirupsen/logrus"
|
||||
|
||||
"github.com/netbirdio/netbird/management/domain"
|
||||
"github.com/netbirdio/netbird/shared/management/domain"
|
||||
)
|
||||
|
||||
type Set struct {
|
||||
|
||||
@@ -15,7 +15,7 @@ import (
|
||||
"github.com/netbirdio/netbird/client/iface/device"
|
||||
"github.com/netbirdio/netbird/client/iface/mocks"
|
||||
"github.com/netbirdio/netbird/client/iface/wgaddr"
|
||||
"github.com/netbirdio/netbird/management/domain"
|
||||
"github.com/netbirdio/netbird/shared/management/domain"
|
||||
)
|
||||
|
||||
func TestPeerACLFiltering(t *testing.T) {
|
||||
|
||||
@@ -20,7 +20,7 @@ import (
|
||||
"github.com/netbirdio/netbird/client/iface/device"
|
||||
"github.com/netbirdio/netbird/client/iface/wgaddr"
|
||||
"github.com/netbirdio/netbird/client/internal/netflow"
|
||||
"github.com/netbirdio/netbird/management/domain"
|
||||
"github.com/netbirdio/netbird/shared/management/domain"
|
||||
)
|
||||
|
||||
var logger = log.NewFromLogrus(logrus.StandardLogger())
|
||||
|
||||
@@ -171,7 +171,7 @@ func fakeAddress(peerAddress *net.UDPAddr) (*netip.AddrPort, error) {
|
||||
|
||||
fakeIP, err := netip.ParseAddr(fmt.Sprintf("127.1.%s.%s", octets[2], octets[3]))
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("failed to parse new IP: %w", err)
|
||||
return nil, fmt.Errorf("parse new IP: %w", err)
|
||||
}
|
||||
|
||||
netipAddr := netip.AddrPortFrom(fakeIP, uint16(peerAddress.Port))
|
||||
|
||||
@@ -95,7 +95,7 @@ func (e *ProxyWrapper) CloseConn() error {
|
||||
e.closeListener.SetCloseListener(nil)
|
||||
|
||||
if err := e.remoteConn.Close(); err != nil && !errors.Is(err, net.ErrClosed) {
|
||||
return fmt.Errorf("failed to close remote conn: %w", err)
|
||||
return fmt.Errorf("close remote conn: %w", err)
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
@@ -18,8 +18,8 @@ import (
|
||||
firewall "github.com/netbirdio/netbird/client/firewall/manager"
|
||||
"github.com/netbirdio/netbird/client/internal/acl/id"
|
||||
"github.com/netbirdio/netbird/client/ssh"
|
||||
"github.com/netbirdio/netbird/management/domain"
|
||||
mgmProto "github.com/netbirdio/netbird/management/proto"
|
||||
"github.com/netbirdio/netbird/shared/management/domain"
|
||||
mgmProto "github.com/netbirdio/netbird/shared/management/proto"
|
||||
)
|
||||
|
||||
var ErrSourceRangesEmpty = errors.New("sources range is empty")
|
||||
|
||||
@@ -12,7 +12,7 @@ import (
|
||||
"github.com/netbirdio/netbird/client/iface/wgaddr"
|
||||
"github.com/netbirdio/netbird/client/internal/acl/mocks"
|
||||
"github.com/netbirdio/netbird/client/internal/netflow"
|
||||
mgmProto "github.com/netbirdio/netbird/management/proto"
|
||||
mgmProto "github.com/netbirdio/netbird/shared/management/proto"
|
||||
)
|
||||
|
||||
var flowLogger = netflow.NewManager(nil, []byte{}, nil).GetLogger()
|
||||
|
||||
@@ -7,7 +7,7 @@ import (
|
||||
"github.com/stretchr/testify/require"
|
||||
|
||||
"github.com/netbirdio/netbird/client/internal"
|
||||
mgm "github.com/netbirdio/netbird/management/client/common"
|
||||
mgm "github.com/netbirdio/netbird/shared/management/client/common"
|
||||
)
|
||||
|
||||
func TestPromptLogin(t *testing.T) {
|
||||
|
||||
+21
-21
@@ -26,11 +26,11 @@ import (
|
||||
cProto "github.com/netbirdio/netbird/client/proto"
|
||||
"github.com/netbirdio/netbird/client/ssh"
|
||||
"github.com/netbirdio/netbird/client/system"
|
||||
mgm "github.com/netbirdio/netbird/management/client"
|
||||
mgmProto "github.com/netbirdio/netbird/management/proto"
|
||||
"github.com/netbirdio/netbird/relay/auth/hmac"
|
||||
relayClient "github.com/netbirdio/netbird/relay/client"
|
||||
signal "github.com/netbirdio/netbird/signal/client"
|
||||
mgm "github.com/netbirdio/netbird/shared/management/client"
|
||||
mgmProto "github.com/netbirdio/netbird/shared/management/proto"
|
||||
"github.com/netbirdio/netbird/shared/relay/auth/hmac"
|
||||
relayClient "github.com/netbirdio/netbird/shared/relay/client"
|
||||
signal "github.com/netbirdio/netbird/shared/signal/client"
|
||||
"github.com/netbirdio/netbird/util"
|
||||
nbnet "github.com/netbirdio/netbird/util/net"
|
||||
"github.com/netbirdio/netbird/version"
|
||||
@@ -43,7 +43,7 @@ type ConnectClient struct {
|
||||
engine *Engine
|
||||
engineMutex sync.Mutex
|
||||
|
||||
persistNetworkMap bool
|
||||
persistSyncResponse bool
|
||||
}
|
||||
|
||||
func NewConnectClient(
|
||||
@@ -270,7 +270,7 @@ func (c *ConnectClient) run(mobileDependency MobileDependency, runningChan chan
|
||||
|
||||
c.engineMutex.Lock()
|
||||
c.engine = NewEngine(engineCtx, cancel, signalClient, mgmClient, relayManager, engineConfig, mobileDependency, c.statusRecorder, checks)
|
||||
c.engine.SetNetworkMapPersistence(c.persistNetworkMap)
|
||||
c.engine.SetSyncResponsePersistence(c.persistSyncResponse)
|
||||
c.engineMutex.Unlock()
|
||||
|
||||
if err := c.engine.Start(); err != nil {
|
||||
@@ -349,23 +349,23 @@ func (c *ConnectClient) Engine() *Engine {
|
||||
return e
|
||||
}
|
||||
|
||||
// GetLatestNetworkMap returns the latest network map from the engine.
|
||||
func (c *ConnectClient) GetLatestNetworkMap() (*mgmProto.NetworkMap, error) {
|
||||
// GetLatestSyncResponse returns the latest sync response from the engine.
|
||||
func (c *ConnectClient) GetLatestSyncResponse() (*mgmProto.SyncResponse, error) {
|
||||
engine := c.Engine()
|
||||
if engine == nil {
|
||||
return nil, errors.New("engine is not initialized")
|
||||
}
|
||||
|
||||
networkMap, err := engine.GetLatestNetworkMap()
|
||||
syncResponse, err := engine.GetLatestSyncResponse()
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("get latest network map: %w", err)
|
||||
return nil, fmt.Errorf("get latest sync response: %w", err)
|
||||
}
|
||||
|
||||
if networkMap == nil {
|
||||
return nil, errors.New("network map is not available")
|
||||
if syncResponse == nil {
|
||||
return nil, errors.New("sync response is not available")
|
||||
}
|
||||
|
||||
return networkMap, nil
|
||||
return syncResponse, nil
|
||||
}
|
||||
|
||||
// Status returns the current client status
|
||||
@@ -398,18 +398,18 @@ func (c *ConnectClient) Stop() error {
|
||||
return nil
|
||||
}
|
||||
|
||||
// SetNetworkMapPersistence enables or disables network map persistence.
|
||||
// When enabled, the last received network map will be stored and can be retrieved
|
||||
// through the Engine's getLatestNetworkMap method. When disabled, any stored
|
||||
// network map will be cleared.
|
||||
func (c *ConnectClient) SetNetworkMapPersistence(enabled bool) {
|
||||
// SetSyncResponsePersistence enables or disables sync response persistence.
|
||||
// When enabled, the last received sync response will be stored and can be retrieved
|
||||
// through the Engine's GetLatestSyncResponse method. When disabled, any stored
|
||||
// sync response will be cleared.
|
||||
func (c *ConnectClient) SetSyncResponsePersistence(enabled bool) {
|
||||
c.engineMutex.Lock()
|
||||
c.persistNetworkMap = enabled
|
||||
c.persistSyncResponse = enabled
|
||||
c.engineMutex.Unlock()
|
||||
|
||||
engine := c.Engine()
|
||||
if engine != nil {
|
||||
engine.SetNetworkMapPersistence(enabled)
|
||||
engine.SetSyncResponsePersistence(enabled)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
+102
-24
@@ -27,7 +27,7 @@ import (
|
||||
"github.com/netbirdio/netbird/client/anonymize"
|
||||
"github.com/netbirdio/netbird/client/internal/peer"
|
||||
"github.com/netbirdio/netbird/client/internal/profilemanager"
|
||||
mgmProto "github.com/netbirdio/netbird/management/proto"
|
||||
mgmProto "github.com/netbirdio/netbird/shared/management/proto"
|
||||
"github.com/netbirdio/netbird/util"
|
||||
)
|
||||
|
||||
@@ -46,7 +46,7 @@ iptables.txt: Anonymized iptables rules with packet counters, if --system-info f
|
||||
nftables.txt: Anonymized nftables rules with packet counters, if --system-info flag was provided.
|
||||
resolved_domains.txt: Anonymized resolved domain IP addresses from the status recorder.
|
||||
config.txt: Anonymized configuration information of the NetBird client.
|
||||
network_map.json: Anonymized network map containing peer configurations, routes, DNS settings, and firewall rules.
|
||||
network_map.json: Anonymized sync response containing peer configurations, routes, DNS settings, and firewall rules.
|
||||
state.json: Anonymized client state dump containing netbird states.
|
||||
mutex.prof: Mutex profiling information.
|
||||
goroutine.prof: Goroutine profiling information.
|
||||
@@ -73,7 +73,7 @@ Domains
|
||||
All domain names (except for the netbird domains) are replaced with randomly generated strings ending in ".domain". Anonymized domains are consistent across all files in the bundle.
|
||||
Reoccuring domain names are replaced with the same anonymized domain.
|
||||
|
||||
Network Map
|
||||
Sync Response
|
||||
The network_map.json file contains the following anonymized information:
|
||||
- Peer configurations (addresses, FQDNs, DNS settings)
|
||||
- Remote and offline peer information (allowed IPs, FQDNs)
|
||||
@@ -81,7 +81,7 @@ The network_map.json file contains the following anonymized information:
|
||||
- DNS configuration (nameservers, domains, custom zones)
|
||||
- Firewall rules (peer IPs, source/destination ranges)
|
||||
|
||||
SSH keys in the network map are replaced with a placeholder value. All IP addresses and domains in the network map follow the same anonymization rules as described above.
|
||||
SSH keys in the sync response are replaced with a placeholder value. All IP addresses and domains in the sync response follow the same anonymization rules as described above.
|
||||
|
||||
State File
|
||||
The state.json file contains anonymized internal state information of the NetBird client, including:
|
||||
@@ -201,7 +201,7 @@ type BundleGenerator struct {
|
||||
// deps
|
||||
internalConfig *profilemanager.Config
|
||||
statusRecorder *peer.Status
|
||||
networkMap *mgmProto.NetworkMap
|
||||
syncResponse *mgmProto.SyncResponse
|
||||
logFile string
|
||||
|
||||
anonymize bool
|
||||
@@ -222,7 +222,7 @@ type BundleConfig struct {
|
||||
type GeneratorDependencies struct {
|
||||
InternalConfig *profilemanager.Config
|
||||
StatusRecorder *peer.Status
|
||||
NetworkMap *mgmProto.NetworkMap
|
||||
SyncResponse *mgmProto.SyncResponse
|
||||
LogFile string
|
||||
}
|
||||
|
||||
@@ -238,7 +238,7 @@ func NewBundleGenerator(deps GeneratorDependencies, cfg BundleConfig) *BundleGen
|
||||
|
||||
internalConfig: deps.InternalConfig,
|
||||
statusRecorder: deps.StatusRecorder,
|
||||
networkMap: deps.NetworkMap,
|
||||
syncResponse: deps.SyncResponse,
|
||||
logFile: deps.LogFile,
|
||||
|
||||
anonymize: cfg.Anonymize,
|
||||
@@ -311,8 +311,8 @@ func (g *BundleGenerator) createArchive() error {
|
||||
log.Errorf("failed to add profiles to debug bundle: %v", err)
|
||||
}
|
||||
|
||||
if err := g.addNetworkMap(); err != nil {
|
||||
return fmt.Errorf("add network map: %w", err)
|
||||
if err := g.addSyncResponse(); err != nil {
|
||||
return fmt.Errorf("add sync response: %w", err)
|
||||
}
|
||||
|
||||
if err := g.addStateFile(); err != nil {
|
||||
@@ -526,15 +526,15 @@ func (g *BundleGenerator) addResolvedDomains() error {
|
||||
return nil
|
||||
}
|
||||
|
||||
func (g *BundleGenerator) addNetworkMap() error {
|
||||
if g.networkMap == nil {
|
||||
log.Debugf("skipping empty network map in debug bundle")
|
||||
func (g *BundleGenerator) addSyncResponse() error {
|
||||
if g.syncResponse == nil {
|
||||
log.Debugf("skipping empty sync response in debug bundle")
|
||||
return nil
|
||||
}
|
||||
|
||||
if g.anonymize {
|
||||
if err := anonymizeNetworkMap(g.networkMap, g.anonymizer); err != nil {
|
||||
return fmt.Errorf("anonymize network map: %w", err)
|
||||
if err := anonymizeSyncResponse(g.syncResponse, g.anonymizer); err != nil {
|
||||
return fmt.Errorf("anonymize sync response: %w", err)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -545,20 +545,20 @@ func (g *BundleGenerator) addNetworkMap() error {
|
||||
AllowPartial: true,
|
||||
}
|
||||
|
||||
jsonBytes, err := options.Marshal(g.networkMap)
|
||||
jsonBytes, err := options.Marshal(g.syncResponse)
|
||||
if err != nil {
|
||||
return fmt.Errorf("generate json: %w", err)
|
||||
}
|
||||
|
||||
if err := g.addFileToZip(bytes.NewReader(jsonBytes), "network_map.json"); err != nil {
|
||||
return fmt.Errorf("add network map to zip: %w", err)
|
||||
return fmt.Errorf("add sync response to zip: %w", err)
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func (g *BundleGenerator) addStateFile() error {
|
||||
sm := profilemanager.ServiceManager{}
|
||||
sm := profilemanager.NewServiceManager("")
|
||||
path := sm.GetStatePath()
|
||||
if path == "" {
|
||||
return nil
|
||||
@@ -597,7 +597,7 @@ func (g *BundleGenerator) addStateFile() error {
|
||||
}
|
||||
|
||||
func (g *BundleGenerator) addCorruptedStateFiles() error {
|
||||
sm := profilemanager.ServiceManager{}
|
||||
sm := profilemanager.NewServiceManager("")
|
||||
pattern := sm.GetStatePath()
|
||||
if pattern == "" {
|
||||
return nil
|
||||
@@ -921,6 +921,88 @@ func anonymizeNetworkMap(networkMap *mgmProto.NetworkMap, anonymizer *anonymize.
|
||||
return nil
|
||||
}
|
||||
|
||||
func anonymizeNetbirdConfig(config *mgmProto.NetbirdConfig, anonymizer *anonymize.Anonymizer) {
|
||||
for _, stun := range config.Stuns {
|
||||
if stun.Uri != "" {
|
||||
stun.Uri = anonymizer.AnonymizeURI(stun.Uri)
|
||||
}
|
||||
}
|
||||
|
||||
for _, turn := range config.Turns {
|
||||
if turn.HostConfig != nil && turn.HostConfig.Uri != "" {
|
||||
turn.HostConfig.Uri = anonymizer.AnonymizeURI(turn.HostConfig.Uri)
|
||||
}
|
||||
if turn.User != "" {
|
||||
turn.User = "turn-user-placeholder"
|
||||
}
|
||||
if turn.Password != "" {
|
||||
turn.Password = "turn-password-placeholder"
|
||||
}
|
||||
}
|
||||
|
||||
if config.Signal != nil && config.Signal.Uri != "" {
|
||||
config.Signal.Uri = anonymizer.AnonymizeURI(config.Signal.Uri)
|
||||
}
|
||||
|
||||
if config.Relay != nil {
|
||||
for i, url := range config.Relay.Urls {
|
||||
config.Relay.Urls[i] = anonymizer.AnonymizeURI(url)
|
||||
}
|
||||
if config.Relay.TokenPayload != "" {
|
||||
config.Relay.TokenPayload = "relay-token-payload-placeholder"
|
||||
}
|
||||
if config.Relay.TokenSignature != "" {
|
||||
config.Relay.TokenSignature = "relay-token-signature-placeholder"
|
||||
}
|
||||
}
|
||||
|
||||
if config.Flow != nil {
|
||||
if config.Flow.Url != "" {
|
||||
config.Flow.Url = anonymizer.AnonymizeURI(config.Flow.Url)
|
||||
}
|
||||
if config.Flow.TokenPayload != "" {
|
||||
config.Flow.TokenPayload = "flow-token-payload-placeholder"
|
||||
}
|
||||
if config.Flow.TokenSignature != "" {
|
||||
config.Flow.TokenSignature = "flow-token-signature-placeholder"
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func anonymizeSyncResponse(syncResponse *mgmProto.SyncResponse, anonymizer *anonymize.Anonymizer) error {
|
||||
if syncResponse.NetbirdConfig != nil {
|
||||
anonymizeNetbirdConfig(syncResponse.NetbirdConfig, anonymizer)
|
||||
}
|
||||
|
||||
if syncResponse.PeerConfig != nil {
|
||||
anonymizePeerConfig(syncResponse.PeerConfig, anonymizer)
|
||||
}
|
||||
|
||||
for _, p := range syncResponse.RemotePeers {
|
||||
anonymizeRemotePeer(p, anonymizer)
|
||||
}
|
||||
|
||||
if syncResponse.NetworkMap != nil {
|
||||
if err := anonymizeNetworkMap(syncResponse.NetworkMap, anonymizer); err != nil {
|
||||
return err
|
||||
}
|
||||
}
|
||||
|
||||
for _, check := range syncResponse.Checks {
|
||||
for i, file := range check.Files {
|
||||
check.Files[i] = anonymizer.AnonymizeString(file)
|
||||
}
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func anonymizeSSHConfig(sshConfig *mgmProto.SSHConfig) {
|
||||
if sshConfig != nil && len(sshConfig.SshPubKey) > 0 {
|
||||
sshConfig.SshPubKey = []byte("ssh-placeholder-key")
|
||||
}
|
||||
}
|
||||
|
||||
func anonymizePeerConfig(config *mgmProto.PeerConfig, anonymizer *anonymize.Anonymizer) {
|
||||
if config == nil {
|
||||
return
|
||||
@@ -930,9 +1012,7 @@ func anonymizePeerConfig(config *mgmProto.PeerConfig, anonymizer *anonymize.Anon
|
||||
config.Address = anonymizer.AnonymizeIP(addr).String()
|
||||
}
|
||||
|
||||
if config.SshConfig != nil && len(config.SshConfig.SshPubKey) > 0 {
|
||||
config.SshConfig.SshPubKey = []byte("ssh-placeholder-key")
|
||||
}
|
||||
anonymizeSSHConfig(config.SshConfig)
|
||||
|
||||
config.Dns = anonymizer.AnonymizeString(config.Dns)
|
||||
config.Fqdn = anonymizer.AnonymizeDomain(config.Fqdn)
|
||||
@@ -954,9 +1034,7 @@ func anonymizeRemotePeer(peer *mgmProto.RemotePeerConfig, anonymizer *anonymize.
|
||||
|
||||
peer.Fqdn = anonymizer.AnonymizeDomain(peer.Fqdn)
|
||||
|
||||
if peer.SshConfig != nil && len(peer.SshConfig.SshPubKey) > 0 {
|
||||
peer.SshConfig.SshPubKey = []byte("ssh-placeholder-key")
|
||||
}
|
||||
anonymizeSSHConfig(peer.SshConfig)
|
||||
}
|
||||
|
||||
func anonymizeRoute(route *mgmProto.Route, anonymizer *anonymize.Anonymizer) {
|
||||
|
||||
@@ -10,7 +10,7 @@ import (
|
||||
"github.com/stretchr/testify/require"
|
||||
|
||||
"github.com/netbirdio/netbird/client/anonymize"
|
||||
mgmProto "github.com/netbirdio/netbird/management/proto"
|
||||
mgmProto "github.com/netbirdio/netbird/shared/management/proto"
|
||||
)
|
||||
|
||||
func TestAnonymizeStateFile(t *testing.T) {
|
||||
|
||||
@@ -10,7 +10,7 @@ import (
|
||||
"github.com/netbirdio/netbird/client/anonymize"
|
||||
"github.com/netbirdio/netbird/client/internal/peer"
|
||||
"github.com/netbirdio/netbird/client/internal/routemanager/systemops"
|
||||
"github.com/netbirdio/netbird/management/domain"
|
||||
"github.com/netbirdio/netbird/shared/management/domain"
|
||||
)
|
||||
|
||||
func formatInterfaces(interfaces []net.Interface, anonymize bool, anonymizer *anonymize.Anonymizer) string {
|
||||
|
||||
@@ -10,7 +10,7 @@ import (
|
||||
"google.golang.org/grpc/codes"
|
||||
"google.golang.org/grpc/status"
|
||||
|
||||
mgm "github.com/netbirdio/netbird/management/client"
|
||||
mgm "github.com/netbirdio/netbird/shared/management/client"
|
||||
)
|
||||
|
||||
// DeviceAuthorizationFlow represents Device Authorization Flow information
|
||||
|
||||
@@ -12,7 +12,7 @@ import (
|
||||
|
||||
"github.com/netbirdio/netbird/client/internal/dns/types"
|
||||
nbdns "github.com/netbirdio/netbird/dns"
|
||||
"github.com/netbirdio/netbird/management/domain"
|
||||
"github.com/netbirdio/netbird/shared/management/domain"
|
||||
)
|
||||
|
||||
type Resolver struct {
|
||||
|
||||
@@ -7,7 +7,7 @@ import (
|
||||
"github.com/miekg/dns"
|
||||
|
||||
nbdns "github.com/netbirdio/netbird/dns"
|
||||
"github.com/netbirdio/netbird/management/domain"
|
||||
"github.com/netbirdio/netbird/shared/management/domain"
|
||||
)
|
||||
|
||||
// MockServer is the mock instance of a dns server
|
||||
|
||||
@@ -21,7 +21,7 @@ import (
|
||||
"github.com/netbirdio/netbird/client/internal/peer"
|
||||
"github.com/netbirdio/netbird/client/internal/statemanager"
|
||||
nbdns "github.com/netbirdio/netbird/dns"
|
||||
"github.com/netbirdio/netbird/management/domain"
|
||||
"github.com/netbirdio/netbird/shared/management/domain"
|
||||
)
|
||||
|
||||
// ReadyListener is a notification mechanism what indicate the server is ready to handle host dns address changes
|
||||
|
||||
@@ -32,7 +32,7 @@ import (
|
||||
"github.com/netbirdio/netbird/client/internal/stdnet"
|
||||
nbdns "github.com/netbirdio/netbird/dns"
|
||||
"github.com/netbirdio/netbird/formatter"
|
||||
"github.com/netbirdio/netbird/management/domain"
|
||||
"github.com/netbirdio/netbird/shared/management/domain"
|
||||
)
|
||||
|
||||
var flowLogger = netflow.NewManager(nil, []byte{}, nil).GetLogger()
|
||||
|
||||
@@ -16,7 +16,7 @@ import (
|
||||
firewall "github.com/netbirdio/netbird/client/firewall/manager"
|
||||
"github.com/netbirdio/netbird/client/internal/dns/test"
|
||||
"github.com/netbirdio/netbird/client/internal/peer"
|
||||
"github.com/netbirdio/netbird/management/domain"
|
||||
"github.com/netbirdio/netbird/shared/management/domain"
|
||||
"github.com/netbirdio/netbird/route"
|
||||
)
|
||||
|
||||
|
||||
@@ -11,7 +11,7 @@ import (
|
||||
nberrors "github.com/netbirdio/netbird/client/errors"
|
||||
firewall "github.com/netbirdio/netbird/client/firewall/manager"
|
||||
"github.com/netbirdio/netbird/client/internal/peer"
|
||||
"github.com/netbirdio/netbird/management/domain"
|
||||
"github.com/netbirdio/netbird/shared/management/domain"
|
||||
"github.com/netbirdio/netbird/route"
|
||||
)
|
||||
|
||||
|
||||
+36
-42
@@ -49,19 +49,19 @@ import (
|
||||
"github.com/netbirdio/netbird/client/internal/routemanager/systemops"
|
||||
"github.com/netbirdio/netbird/client/internal/statemanager"
|
||||
cProto "github.com/netbirdio/netbird/client/proto"
|
||||
"github.com/netbirdio/netbird/management/domain"
|
||||
"github.com/netbirdio/netbird/shared/management/domain"
|
||||
semaphoregroup "github.com/netbirdio/netbird/util/semaphore-group"
|
||||
|
||||
nbssh "github.com/netbirdio/netbird/client/ssh"
|
||||
"github.com/netbirdio/netbird/client/system"
|
||||
nbdns "github.com/netbirdio/netbird/dns"
|
||||
mgm "github.com/netbirdio/netbird/management/client"
|
||||
mgmProto "github.com/netbirdio/netbird/management/proto"
|
||||
auth "github.com/netbirdio/netbird/relay/auth/hmac"
|
||||
relayClient "github.com/netbirdio/netbird/relay/client"
|
||||
mgm "github.com/netbirdio/netbird/shared/management/client"
|
||||
mgmProto "github.com/netbirdio/netbird/shared/management/proto"
|
||||
auth "github.com/netbirdio/netbird/shared/relay/auth/hmac"
|
||||
relayClient "github.com/netbirdio/netbird/shared/relay/client"
|
||||
"github.com/netbirdio/netbird/route"
|
||||
signal "github.com/netbirdio/netbird/signal/client"
|
||||
sProto "github.com/netbirdio/netbird/signal/proto"
|
||||
signal "github.com/netbirdio/netbird/shared/signal/client"
|
||||
sProto "github.com/netbirdio/netbird/shared/signal/proto"
|
||||
"github.com/netbirdio/netbird/util"
|
||||
)
|
||||
|
||||
@@ -189,11 +189,11 @@ type Engine struct {
|
||||
stateManager *statemanager.Manager
|
||||
srWatcher *guard.SRWatcher
|
||||
|
||||
// Network map persistence
|
||||
persistNetworkMap bool
|
||||
latestNetworkMap *mgmProto.NetworkMap
|
||||
connSemaphore *semaphoregroup.SemaphoreGroup
|
||||
flowManager nftypes.FlowManager
|
||||
// Sync response persistence
|
||||
persistSyncResponse bool
|
||||
latestSyncResponse *mgmProto.SyncResponse
|
||||
connSemaphore *semaphoregroup.SemaphoreGroup
|
||||
flowManager nftypes.FlowManager
|
||||
}
|
||||
|
||||
// Peer is an instance of the Connection Peer
|
||||
@@ -238,7 +238,7 @@ func NewEngine(
|
||||
connSemaphore: semaphoregroup.NewSemaphoreGroup(connInitLimit),
|
||||
}
|
||||
|
||||
sm := profilemanager.ServiceManager{}
|
||||
sm := profilemanager.NewServiceManager("")
|
||||
|
||||
path := sm.GetStatePath()
|
||||
if runtime.GOOS == "ios" {
|
||||
@@ -698,10 +698,10 @@ func (e *Engine) handleSync(update *mgmProto.SyncResponse) error {
|
||||
return nil
|
||||
}
|
||||
|
||||
// Store network map if persistence is enabled
|
||||
if e.persistNetworkMap {
|
||||
e.latestNetworkMap = nm
|
||||
log.Debugf("network map persisted with serial %d", nm.GetSerial())
|
||||
// Store sync response if persistence is enabled
|
||||
if e.persistSyncResponse {
|
||||
e.latestSyncResponse = update
|
||||
log.Debugf("sync response persisted with serial %d", nm.GetSerial())
|
||||
}
|
||||
|
||||
// only apply new changes and ignore old ones
|
||||
@@ -862,15 +862,10 @@ func (e *Engine) updateConfig(conf *mgmProto.PeerConfig) error {
|
||||
return errors.New("wireguard interface is not initialized")
|
||||
}
|
||||
|
||||
// Cannot update the IP address without restarting the engine because
|
||||
// the firewall, route manager, and other components cache the old address
|
||||
if e.wgInterface.Address().String() != conf.Address {
|
||||
oldAddr := e.wgInterface.Address().String()
|
||||
log.Debugf("updating peer address from %s to %s", oldAddr, conf.Address)
|
||||
err := e.wgInterface.UpdateAddr(conf.Address)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
e.config.WgAddr = conf.Address
|
||||
log.Infof("updated peer address from %s to %s", oldAddr, conf.Address)
|
||||
log.Infof("peer IP address has changed from %s to %s", e.wgInterface.Address().String(), conf.Address)
|
||||
}
|
||||
|
||||
if conf.GetSshConfig() != nil {
|
||||
@@ -881,7 +876,7 @@ func (e *Engine) updateConfig(conf *mgmProto.PeerConfig) error {
|
||||
}
|
||||
|
||||
state := e.statusRecorder.GetLocalPeerState()
|
||||
state.IP = e.config.WgAddr
|
||||
state.IP = e.wgInterface.Address().String()
|
||||
state.PubKey = e.config.WgPrivateKey.PublicKey().String()
|
||||
state.KernelInterface = device.WireGuardModuleIsLoaded()
|
||||
state.FQDN = conf.GetFqdn()
|
||||
@@ -1757,44 +1752,43 @@ func (e *Engine) stopDNSServer() {
|
||||
e.statusRecorder.UpdateDNSStates(nsGroupStates)
|
||||
}
|
||||
|
||||
// SetNetworkMapPersistence enables or disables network map persistence
|
||||
func (e *Engine) SetNetworkMapPersistence(enabled bool) {
|
||||
// SetSyncResponsePersistence enables or disables sync response persistence
|
||||
func (e *Engine) SetSyncResponsePersistence(enabled bool) {
|
||||
e.syncMsgMux.Lock()
|
||||
defer e.syncMsgMux.Unlock()
|
||||
|
||||
if enabled == e.persistNetworkMap {
|
||||
if enabled == e.persistSyncResponse {
|
||||
return
|
||||
}
|
||||
e.persistNetworkMap = enabled
|
||||
log.Debugf("Network map persistence is set to %t", enabled)
|
||||
e.persistSyncResponse = enabled
|
||||
log.Debugf("Sync response persistence is set to %t", enabled)
|
||||
|
||||
if !enabled {
|
||||
e.latestNetworkMap = nil
|
||||
e.latestSyncResponse = nil
|
||||
}
|
||||
}
|
||||
|
||||
// GetLatestNetworkMap returns the stored network map if persistence is enabled
|
||||
func (e *Engine) GetLatestNetworkMap() (*mgmProto.NetworkMap, error) {
|
||||
// GetLatestSyncResponse returns the stored sync response if persistence is enabled
|
||||
func (e *Engine) GetLatestSyncResponse() (*mgmProto.SyncResponse, error) {
|
||||
e.syncMsgMux.Lock()
|
||||
defer e.syncMsgMux.Unlock()
|
||||
|
||||
if !e.persistNetworkMap {
|
||||
return nil, errors.New("network map persistence is disabled")
|
||||
if !e.persistSyncResponse {
|
||||
return nil, errors.New("sync response persistence is disabled")
|
||||
}
|
||||
|
||||
if e.latestNetworkMap == nil {
|
||||
if e.latestSyncResponse == nil {
|
||||
//nolint:nilnil
|
||||
return nil, nil
|
||||
}
|
||||
|
||||
log.Debugf("Retrieving latest network map with size %d bytes", proto.Size(e.latestNetworkMap))
|
||||
nm, ok := proto.Clone(e.latestNetworkMap).(*mgmProto.NetworkMap)
|
||||
log.Debugf("Retrieving latest sync response with size %d bytes", proto.Size(e.latestSyncResponse))
|
||||
sr, ok := proto.Clone(e.latestSyncResponse).(*mgmProto.SyncResponse)
|
||||
if !ok {
|
||||
|
||||
return nil, fmt.Errorf("failed to clone network map")
|
||||
return nil, fmt.Errorf("failed to clone sync response")
|
||||
}
|
||||
|
||||
return nm, nil
|
||||
return sr, nil
|
||||
}
|
||||
|
||||
// GetWgAddr returns the wireguard address
|
||||
|
||||
@@ -43,8 +43,8 @@ import (
|
||||
"github.com/netbirdio/netbird/client/ssh"
|
||||
"github.com/netbirdio/netbird/client/system"
|
||||
nbdns "github.com/netbirdio/netbird/dns"
|
||||
mgmt "github.com/netbirdio/netbird/management/client"
|
||||
mgmtProto "github.com/netbirdio/netbird/management/proto"
|
||||
mgmt "github.com/netbirdio/netbird/shared/management/client"
|
||||
mgmtProto "github.com/netbirdio/netbird/shared/management/proto"
|
||||
"github.com/netbirdio/netbird/management/server"
|
||||
"github.com/netbirdio/netbird/management/server/activity"
|
||||
"github.com/netbirdio/netbird/management/server/integrations/port_forwarding"
|
||||
@@ -54,10 +54,10 @@ import (
|
||||
"github.com/netbirdio/netbird/management/server/telemetry"
|
||||
"github.com/netbirdio/netbird/management/server/types"
|
||||
"github.com/netbirdio/netbird/monotime"
|
||||
relayClient "github.com/netbirdio/netbird/relay/client"
|
||||
relayClient "github.com/netbirdio/netbird/shared/relay/client"
|
||||
"github.com/netbirdio/netbird/route"
|
||||
signal "github.com/netbirdio/netbird/signal/client"
|
||||
"github.com/netbirdio/netbird/signal/proto"
|
||||
signal "github.com/netbirdio/netbird/shared/signal/client"
|
||||
"github.com/netbirdio/netbird/shared/signal/proto"
|
||||
signalServer "github.com/netbirdio/netbird/signal/server"
|
||||
"github.com/netbirdio/netbird/util"
|
||||
)
|
||||
|
||||
@@ -13,8 +13,8 @@ import (
|
||||
"github.com/netbirdio/netbird/client/internal/profilemanager"
|
||||
"github.com/netbirdio/netbird/client/ssh"
|
||||
"github.com/netbirdio/netbird/client/system"
|
||||
mgm "github.com/netbirdio/netbird/management/client"
|
||||
mgmProto "github.com/netbirdio/netbird/management/proto"
|
||||
mgm "github.com/netbirdio/netbird/shared/management/client"
|
||||
mgmProto "github.com/netbirdio/netbird/shared/management/proto"
|
||||
)
|
||||
|
||||
// IsLoginRequired check that the server is support SSO or not
|
||||
|
||||
@@ -7,7 +7,7 @@ import (
|
||||
"net/netip"
|
||||
|
||||
firewallManager "github.com/netbirdio/netbird/client/firewall/manager"
|
||||
mgmProto "github.com/netbirdio/netbird/management/proto"
|
||||
mgmProto "github.com/netbirdio/netbird/shared/management/proto"
|
||||
)
|
||||
|
||||
func convertToFirewallProtocol(protocol mgmProto.RuleProtocol) (firewallManager.Protocol, error) {
|
||||
|
||||
@@ -24,7 +24,7 @@ import (
|
||||
"github.com/netbirdio/netbird/client/internal/peer/id"
|
||||
"github.com/netbirdio/netbird/client/internal/peer/worker"
|
||||
"github.com/netbirdio/netbird/client/internal/stdnet"
|
||||
relayClient "github.com/netbirdio/netbird/relay/client"
|
||||
relayClient "github.com/netbirdio/netbird/shared/relay/client"
|
||||
"github.com/netbirdio/netbird/route"
|
||||
semaphoregroup "github.com/netbirdio/netbird/util/semaphore-group"
|
||||
)
|
||||
|
||||
@@ -4,8 +4,8 @@ import (
|
||||
"github.com/pion/ice/v3"
|
||||
"golang.zx2c4.com/wireguard/wgctrl/wgtypes"
|
||||
|
||||
signal "github.com/netbirdio/netbird/signal/client"
|
||||
sProto "github.com/netbirdio/netbird/signal/proto"
|
||||
signal "github.com/netbirdio/netbird/shared/signal/client"
|
||||
sProto "github.com/netbirdio/netbird/shared/signal/proto"
|
||||
)
|
||||
|
||||
type Signaler struct {
|
||||
|
||||
@@ -21,8 +21,8 @@ import (
|
||||
"github.com/netbirdio/netbird/client/internal/ingressgw"
|
||||
"github.com/netbirdio/netbird/client/internal/relay"
|
||||
"github.com/netbirdio/netbird/client/proto"
|
||||
"github.com/netbirdio/netbird/management/domain"
|
||||
relayClient "github.com/netbirdio/netbird/relay/client"
|
||||
"github.com/netbirdio/netbird/shared/management/domain"
|
||||
relayClient "github.com/netbirdio/netbird/shared/relay/client"
|
||||
"github.com/netbirdio/netbird/route"
|
||||
)
|
||||
|
||||
|
||||
@@ -9,7 +9,7 @@ import (
|
||||
|
||||
log "github.com/sirupsen/logrus"
|
||||
|
||||
relayClient "github.com/netbirdio/netbird/relay/client"
|
||||
relayClient "github.com/netbirdio/netbird/shared/relay/client"
|
||||
)
|
||||
|
||||
type RelayConnInfo struct {
|
||||
|
||||
@@ -11,8 +11,8 @@ import (
|
||||
"google.golang.org/grpc/codes"
|
||||
"google.golang.org/grpc/status"
|
||||
|
||||
mgm "github.com/netbirdio/netbird/management/client"
|
||||
"github.com/netbirdio/netbird/management/client/common"
|
||||
mgm "github.com/netbirdio/netbird/shared/management/client"
|
||||
"github.com/netbirdio/netbird/shared/management/client/common"
|
||||
)
|
||||
|
||||
// PKCEAuthorizationFlow represents PKCE Authorization Flow information
|
||||
|
||||
@@ -20,15 +20,14 @@ import (
|
||||
"github.com/netbirdio/netbird/client/iface"
|
||||
"github.com/netbirdio/netbird/client/internal/routemanager/dynamic"
|
||||
"github.com/netbirdio/netbird/client/ssh"
|
||||
mgm "github.com/netbirdio/netbird/management/client"
|
||||
"github.com/netbirdio/netbird/management/domain"
|
||||
mgm "github.com/netbirdio/netbird/shared/management/client"
|
||||
"github.com/netbirdio/netbird/shared/management/domain"
|
||||
"github.com/netbirdio/netbird/util"
|
||||
)
|
||||
|
||||
const (
|
||||
// managementLegacyPortString is the port that was used before by the Management gRPC server.
|
||||
// It is used for backward compatibility now.
|
||||
// NB: hardcoded from github.com/netbirdio/netbird/management/cmd to avoid import
|
||||
managementLegacyPortString = "33073"
|
||||
// DefaultManagementURL points to the NetBird's cloud management endpoint
|
||||
DefaultManagementURL = "https://api.netbird.io:443"
|
||||
|
||||
@@ -13,7 +13,8 @@ import (
|
||||
)
|
||||
|
||||
const (
|
||||
defaultProfileName = "default"
|
||||
DefaultProfileName = "default"
|
||||
defaultProfileName = DefaultProfileName // Keep for backward compatibility
|
||||
activeProfileStateFilename = "active_profile.txt"
|
||||
)
|
||||
|
||||
|
||||
@@ -75,7 +75,15 @@ func (a *ActiveProfileState) FilePath() (string, error) {
|
||||
return filepath.Join(configDir, a.Name+".json"), nil
|
||||
}
|
||||
|
||||
type ServiceManager struct{}
|
||||
type ServiceManager struct {
|
||||
}
|
||||
|
||||
func NewServiceManager(defaultConfigPath string) *ServiceManager {
|
||||
if defaultConfigPath != "" {
|
||||
DefaultConfigPath = defaultConfigPath
|
||||
}
|
||||
return &ServiceManager{}
|
||||
}
|
||||
|
||||
func (s *ServiceManager) CopyDefaultProfileIfNotExists() (bool, error) {
|
||||
|
||||
|
||||
@@ -22,7 +22,7 @@ import (
|
||||
"github.com/netbirdio/netbird/client/internal/routemanager/common"
|
||||
"github.com/netbirdio/netbird/client/internal/routemanager/fakeip"
|
||||
"github.com/netbirdio/netbird/client/internal/routemanager/refcounter"
|
||||
"github.com/netbirdio/netbird/management/domain"
|
||||
"github.com/netbirdio/netbird/shared/management/domain"
|
||||
"github.com/netbirdio/netbird/route"
|
||||
)
|
||||
|
||||
|
||||
@@ -18,7 +18,7 @@ import (
|
||||
"github.com/netbirdio/netbird/client/internal/routemanager/iface"
|
||||
"github.com/netbirdio/netbird/client/internal/routemanager/refcounter"
|
||||
"github.com/netbirdio/netbird/client/internal/routemanager/util"
|
||||
"github.com/netbirdio/netbird/management/domain"
|
||||
"github.com/netbirdio/netbird/shared/management/domain"
|
||||
"github.com/netbirdio/netbird/route"
|
||||
)
|
||||
|
||||
|
||||
@@ -5,7 +5,7 @@ package dynamic
|
||||
import (
|
||||
"net"
|
||||
|
||||
"github.com/netbirdio/netbird/management/domain"
|
||||
"github.com/netbirdio/netbird/shared/management/domain"
|
||||
)
|
||||
|
||||
func (r *Route) getIPsFromResolver(domain domain.Domain) ([]net.IP, error) {
|
||||
|
||||
@@ -11,7 +11,7 @@ import (
|
||||
|
||||
nbdns "github.com/netbirdio/netbird/client/internal/dns"
|
||||
|
||||
"github.com/netbirdio/netbird/management/domain"
|
||||
"github.com/netbirdio/netbird/shared/management/domain"
|
||||
)
|
||||
|
||||
const dialTimeout = 10 * time.Second
|
||||
|
||||
@@ -36,7 +36,7 @@ import (
|
||||
"github.com/netbirdio/netbird/client/internal/routemanager/vars"
|
||||
"github.com/netbirdio/netbird/client/internal/routeselector"
|
||||
"github.com/netbirdio/netbird/client/internal/statemanager"
|
||||
relayClient "github.com/netbirdio/netbird/relay/client"
|
||||
relayClient "github.com/netbirdio/netbird/shared/relay/client"
|
||||
"github.com/netbirdio/netbird/route"
|
||||
nbnet "github.com/netbirdio/netbird/util/net"
|
||||
"github.com/netbirdio/netbird/version"
|
||||
|
||||
@@ -77,8 +77,8 @@ type ruleParams struct {
|
||||
|
||||
func getSetupRules() []ruleParams {
|
||||
return []ruleParams{
|
||||
{100, 0, syscall.RT_TABLE_MAIN, netlink.FAMILY_V4, false, 0, "rule with suppress prefixlen v4"},
|
||||
{100, 0, syscall.RT_TABLE_MAIN, netlink.FAMILY_V6, false, 0, "rule with suppress prefixlen v6"},
|
||||
{105, 0, syscall.RT_TABLE_MAIN, netlink.FAMILY_V4, false, 0, "rule with suppress prefixlen v4"},
|
||||
{105, 0, syscall.RT_TABLE_MAIN, netlink.FAMILY_V6, false, 0, "rule with suppress prefixlen v6"},
|
||||
{110, nbnet.ControlPlaneMark, NetbirdVPNTableID, netlink.FAMILY_V4, true, -1, "rule v4 netbird"},
|
||||
{110, nbnet.ControlPlaneMark, NetbirdVPNTableID, netlink.FAMILY_V6, true, -1, "rule v6 netbird"},
|
||||
}
|
||||
|
||||
@@ -20,7 +20,7 @@ import (
|
||||
"github.com/netbirdio/netbird/client/internal/profilemanager"
|
||||
"github.com/netbirdio/netbird/client/system"
|
||||
"github.com/netbirdio/netbird/formatter"
|
||||
"github.com/netbirdio/netbird/management/domain"
|
||||
"github.com/netbirdio/netbird/shared/management/domain"
|
||||
"github.com/netbirdio/netbird/route"
|
||||
)
|
||||
|
||||
|
||||
+241
-141
@@ -2959,27 +2959,27 @@ func (x *DeleteStateResponse) GetDeletedStates() int32 {
|
||||
return 0
|
||||
}
|
||||
|
||||
type SetNetworkMapPersistenceRequest struct {
|
||||
type SetSyncResponsePersistenceRequest struct {
|
||||
state protoimpl.MessageState `protogen:"open.v1"`
|
||||
Enabled bool `protobuf:"varint,1,opt,name=enabled,proto3" json:"enabled,omitempty"`
|
||||
unknownFields protoimpl.UnknownFields
|
||||
sizeCache protoimpl.SizeCache
|
||||
}
|
||||
|
||||
func (x *SetNetworkMapPersistenceRequest) Reset() {
|
||||
*x = SetNetworkMapPersistenceRequest{}
|
||||
func (x *SetSyncResponsePersistenceRequest) Reset() {
|
||||
*x = SetSyncResponsePersistenceRequest{}
|
||||
mi := &file_daemon_proto_msgTypes[42]
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
ms.StoreMessageInfo(mi)
|
||||
}
|
||||
|
||||
func (x *SetNetworkMapPersistenceRequest) String() string {
|
||||
func (x *SetSyncResponsePersistenceRequest) String() string {
|
||||
return protoimpl.X.MessageStringOf(x)
|
||||
}
|
||||
|
||||
func (*SetNetworkMapPersistenceRequest) ProtoMessage() {}
|
||||
func (*SetSyncResponsePersistenceRequest) ProtoMessage() {}
|
||||
|
||||
func (x *SetNetworkMapPersistenceRequest) ProtoReflect() protoreflect.Message {
|
||||
func (x *SetSyncResponsePersistenceRequest) ProtoReflect() protoreflect.Message {
|
||||
mi := &file_daemon_proto_msgTypes[42]
|
||||
if x != nil {
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
@@ -2991,38 +2991,38 @@ func (x *SetNetworkMapPersistenceRequest) ProtoReflect() protoreflect.Message {
|
||||
return mi.MessageOf(x)
|
||||
}
|
||||
|
||||
// Deprecated: Use SetNetworkMapPersistenceRequest.ProtoReflect.Descriptor instead.
|
||||
func (*SetNetworkMapPersistenceRequest) Descriptor() ([]byte, []int) {
|
||||
// Deprecated: Use SetSyncResponsePersistenceRequest.ProtoReflect.Descriptor instead.
|
||||
func (*SetSyncResponsePersistenceRequest) Descriptor() ([]byte, []int) {
|
||||
return file_daemon_proto_rawDescGZIP(), []int{42}
|
||||
}
|
||||
|
||||
func (x *SetNetworkMapPersistenceRequest) GetEnabled() bool {
|
||||
func (x *SetSyncResponsePersistenceRequest) GetEnabled() bool {
|
||||
if x != nil {
|
||||
return x.Enabled
|
||||
}
|
||||
return false
|
||||
}
|
||||
|
||||
type SetNetworkMapPersistenceResponse struct {
|
||||
type SetSyncResponsePersistenceResponse struct {
|
||||
state protoimpl.MessageState `protogen:"open.v1"`
|
||||
unknownFields protoimpl.UnknownFields
|
||||
sizeCache protoimpl.SizeCache
|
||||
}
|
||||
|
||||
func (x *SetNetworkMapPersistenceResponse) Reset() {
|
||||
*x = SetNetworkMapPersistenceResponse{}
|
||||
func (x *SetSyncResponsePersistenceResponse) Reset() {
|
||||
*x = SetSyncResponsePersistenceResponse{}
|
||||
mi := &file_daemon_proto_msgTypes[43]
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
ms.StoreMessageInfo(mi)
|
||||
}
|
||||
|
||||
func (x *SetNetworkMapPersistenceResponse) String() string {
|
||||
func (x *SetSyncResponsePersistenceResponse) String() string {
|
||||
return protoimpl.X.MessageStringOf(x)
|
||||
}
|
||||
|
||||
func (*SetNetworkMapPersistenceResponse) ProtoMessage() {}
|
||||
func (*SetSyncResponsePersistenceResponse) ProtoMessage() {}
|
||||
|
||||
func (x *SetNetworkMapPersistenceResponse) ProtoReflect() protoreflect.Message {
|
||||
func (x *SetSyncResponsePersistenceResponse) ProtoReflect() protoreflect.Message {
|
||||
mi := &file_daemon_proto_msgTypes[43]
|
||||
if x != nil {
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
@@ -3034,8 +3034,8 @@ func (x *SetNetworkMapPersistenceResponse) ProtoReflect() protoreflect.Message {
|
||||
return mi.MessageOf(x)
|
||||
}
|
||||
|
||||
// Deprecated: Use SetNetworkMapPersistenceResponse.ProtoReflect.Descriptor instead.
|
||||
func (*SetNetworkMapPersistenceResponse) Descriptor() ([]byte, []int) {
|
||||
// Deprecated: Use SetSyncResponsePersistenceResponse.ProtoReflect.Descriptor instead.
|
||||
func (*SetSyncResponsePersistenceResponse) Descriptor() ([]byte, []int) {
|
||||
return file_daemon_proto_rawDescGZIP(), []int{43}
|
||||
}
|
||||
|
||||
@@ -4342,6 +4342,94 @@ func (x *GetActiveProfileResponse) GetUsername() string {
|
||||
return ""
|
||||
}
|
||||
|
||||
type LogoutRequest struct {
|
||||
state protoimpl.MessageState `protogen:"open.v1"`
|
||||
ProfileName *string `protobuf:"bytes,1,opt,name=profileName,proto3,oneof" json:"profileName,omitempty"`
|
||||
Username *string `protobuf:"bytes,2,opt,name=username,proto3,oneof" json:"username,omitempty"`
|
||||
unknownFields protoimpl.UnknownFields
|
||||
sizeCache protoimpl.SizeCache
|
||||
}
|
||||
|
||||
func (x *LogoutRequest) Reset() {
|
||||
*x = LogoutRequest{}
|
||||
mi := &file_daemon_proto_msgTypes[65]
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
ms.StoreMessageInfo(mi)
|
||||
}
|
||||
|
||||
func (x *LogoutRequest) String() string {
|
||||
return protoimpl.X.MessageStringOf(x)
|
||||
}
|
||||
|
||||
func (*LogoutRequest) ProtoMessage() {}
|
||||
|
||||
func (x *LogoutRequest) ProtoReflect() protoreflect.Message {
|
||||
mi := &file_daemon_proto_msgTypes[65]
|
||||
if x != nil {
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
if ms.LoadMessageInfo() == nil {
|
||||
ms.StoreMessageInfo(mi)
|
||||
}
|
||||
return ms
|
||||
}
|
||||
return mi.MessageOf(x)
|
||||
}
|
||||
|
||||
// Deprecated: Use LogoutRequest.ProtoReflect.Descriptor instead.
|
||||
func (*LogoutRequest) Descriptor() ([]byte, []int) {
|
||||
return file_daemon_proto_rawDescGZIP(), []int{65}
|
||||
}
|
||||
|
||||
func (x *LogoutRequest) GetProfileName() string {
|
||||
if x != nil && x.ProfileName != nil {
|
||||
return *x.ProfileName
|
||||
}
|
||||
return ""
|
||||
}
|
||||
|
||||
func (x *LogoutRequest) GetUsername() string {
|
||||
if x != nil && x.Username != nil {
|
||||
return *x.Username
|
||||
}
|
||||
return ""
|
||||
}
|
||||
|
||||
type LogoutResponse struct {
|
||||
state protoimpl.MessageState `protogen:"open.v1"`
|
||||
unknownFields protoimpl.UnknownFields
|
||||
sizeCache protoimpl.SizeCache
|
||||
}
|
||||
|
||||
func (x *LogoutResponse) Reset() {
|
||||
*x = LogoutResponse{}
|
||||
mi := &file_daemon_proto_msgTypes[66]
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
ms.StoreMessageInfo(mi)
|
||||
}
|
||||
|
||||
func (x *LogoutResponse) String() string {
|
||||
return protoimpl.X.MessageStringOf(x)
|
||||
}
|
||||
|
||||
func (*LogoutResponse) ProtoMessage() {}
|
||||
|
||||
func (x *LogoutResponse) ProtoReflect() protoreflect.Message {
|
||||
mi := &file_daemon_proto_msgTypes[66]
|
||||
if x != nil {
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
if ms.LoadMessageInfo() == nil {
|
||||
ms.StoreMessageInfo(mi)
|
||||
}
|
||||
return ms
|
||||
}
|
||||
return mi.MessageOf(x)
|
||||
}
|
||||
|
||||
// Deprecated: Use LogoutResponse.ProtoReflect.Descriptor instead.
|
||||
func (*LogoutResponse) Descriptor() ([]byte, []int) {
|
||||
return file_daemon_proto_rawDescGZIP(), []int{66}
|
||||
}
|
||||
|
||||
type PortInfo_Range struct {
|
||||
state protoimpl.MessageState `protogen:"open.v1"`
|
||||
Start uint32 `protobuf:"varint,1,opt,name=start,proto3" json:"start,omitempty"`
|
||||
@@ -4352,7 +4440,7 @@ type PortInfo_Range struct {
|
||||
|
||||
func (x *PortInfo_Range) Reset() {
|
||||
*x = PortInfo_Range{}
|
||||
mi := &file_daemon_proto_msgTypes[66]
|
||||
mi := &file_daemon_proto_msgTypes[68]
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
ms.StoreMessageInfo(mi)
|
||||
}
|
||||
@@ -4364,7 +4452,7 @@ func (x *PortInfo_Range) String() string {
|
||||
func (*PortInfo_Range) ProtoMessage() {}
|
||||
|
||||
func (x *PortInfo_Range) ProtoReflect() protoreflect.Message {
|
||||
mi := &file_daemon_proto_msgTypes[66]
|
||||
mi := &file_daemon_proto_msgTypes[68]
|
||||
if x != nil {
|
||||
ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x))
|
||||
if ms.LoadMessageInfo() == nil {
|
||||
@@ -4639,10 +4727,10 @@ const file_daemon_proto_rawDesc = "" +
|
||||
"state_name\x18\x01 \x01(\tR\tstateName\x12\x10\n" +
|
||||
"\x03all\x18\x02 \x01(\bR\x03all\"<\n" +
|
||||
"\x13DeleteStateResponse\x12%\n" +
|
||||
"\x0edeleted_states\x18\x01 \x01(\x05R\rdeletedStates\";\n" +
|
||||
"\x1fSetNetworkMapPersistenceRequest\x12\x18\n" +
|
||||
"\aenabled\x18\x01 \x01(\bR\aenabled\"\"\n" +
|
||||
" SetNetworkMapPersistenceResponse\"v\n" +
|
||||
"\x0edeleted_states\x18\x01 \x01(\x05R\rdeletedStates\"=\n" +
|
||||
"!SetSyncResponsePersistenceRequest\x12\x18\n" +
|
||||
"\aenabled\x18\x01 \x01(\bR\aenabled\"$\n" +
|
||||
"\"SetSyncResponsePersistenceResponse\"v\n" +
|
||||
"\bTCPFlags\x12\x10\n" +
|
||||
"\x03syn\x18\x01 \x01(\bR\x03syn\x12\x10\n" +
|
||||
"\x03ack\x18\x02 \x01(\bR\x03ack\x12\x10\n" +
|
||||
@@ -4778,7 +4866,13 @@ const file_daemon_proto_rawDesc = "" +
|
||||
"\x17GetActiveProfileRequest\"X\n" +
|
||||
"\x18GetActiveProfileResponse\x12 \n" +
|
||||
"\vprofileName\x18\x01 \x01(\tR\vprofileName\x12\x1a\n" +
|
||||
"\busername\x18\x02 \x01(\tR\busername*b\n" +
|
||||
"\busername\x18\x02 \x01(\tR\busername\"t\n" +
|
||||
"\rLogoutRequest\x12%\n" +
|
||||
"\vprofileName\x18\x01 \x01(\tH\x00R\vprofileName\x88\x01\x01\x12\x1f\n" +
|
||||
"\busername\x18\x02 \x01(\tH\x01R\busername\x88\x01\x01B\x0e\n" +
|
||||
"\f_profileNameB\v\n" +
|
||||
"\t_username\"\x10\n" +
|
||||
"\x0eLogoutResponse*b\n" +
|
||||
"\bLogLevel\x12\v\n" +
|
||||
"\aUNKNOWN\x10\x00\x12\t\n" +
|
||||
"\x05PANIC\x10\x01\x12\t\n" +
|
||||
@@ -4787,7 +4881,7 @@ const file_daemon_proto_rawDesc = "" +
|
||||
"\x04WARN\x10\x04\x12\b\n" +
|
||||
"\x04INFO\x10\x05\x12\t\n" +
|
||||
"\x05DEBUG\x10\x06\x12\t\n" +
|
||||
"\x05TRACE\x10\a2\x84\x0f\n" +
|
||||
"\x05TRACE\x10\a2\xc5\x0f\n" +
|
||||
"\rDaemonService\x126\n" +
|
||||
"\x05Login\x12\x14.daemon.LoginRequest\x1a\x15.daemon.LoginResponse\"\x00\x12K\n" +
|
||||
"\fWaitSSOLogin\x12\x1b.daemon.WaitSSOLoginRequest\x1a\x1c.daemon.WaitSSOLoginResponse\"\x00\x12-\n" +
|
||||
@@ -4806,8 +4900,8 @@ const file_daemon_proto_rawDesc = "" +
|
||||
"ListStates\x12\x19.daemon.ListStatesRequest\x1a\x1a.daemon.ListStatesResponse\"\x00\x12E\n" +
|
||||
"\n" +
|
||||
"CleanState\x12\x19.daemon.CleanStateRequest\x1a\x1a.daemon.CleanStateResponse\"\x00\x12H\n" +
|
||||
"\vDeleteState\x12\x1a.daemon.DeleteStateRequest\x1a\x1b.daemon.DeleteStateResponse\"\x00\x12o\n" +
|
||||
"\x18SetNetworkMapPersistence\x12'.daemon.SetNetworkMapPersistenceRequest\x1a(.daemon.SetNetworkMapPersistenceResponse\"\x00\x12H\n" +
|
||||
"\vDeleteState\x12\x1a.daemon.DeleteStateRequest\x1a\x1b.daemon.DeleteStateResponse\"\x00\x12u\n" +
|
||||
"\x1aSetSyncResponsePersistence\x12).daemon.SetSyncResponsePersistenceRequest\x1a*.daemon.SetSyncResponsePersistenceResponse\"\x00\x12H\n" +
|
||||
"\vTracePacket\x12\x1a.daemon.TracePacketRequest\x1a\x1b.daemon.TracePacketResponse\"\x00\x12D\n" +
|
||||
"\x0fSubscribeEvents\x12\x18.daemon.SubscribeRequest\x1a\x13.daemon.SystemEvent\"\x000\x01\x12B\n" +
|
||||
"\tGetEvents\x12\x18.daemon.GetEventsRequest\x1a\x19.daemon.GetEventsResponse\"\x00\x12N\n" +
|
||||
@@ -4817,7 +4911,8 @@ const file_daemon_proto_rawDesc = "" +
|
||||
"AddProfile\x12\x19.daemon.AddProfileRequest\x1a\x1a.daemon.AddProfileResponse\"\x00\x12N\n" +
|
||||
"\rRemoveProfile\x12\x1c.daemon.RemoveProfileRequest\x1a\x1d.daemon.RemoveProfileResponse\"\x00\x12K\n" +
|
||||
"\fListProfiles\x12\x1b.daemon.ListProfilesRequest\x1a\x1c.daemon.ListProfilesResponse\"\x00\x12W\n" +
|
||||
"\x10GetActiveProfile\x12\x1f.daemon.GetActiveProfileRequest\x1a .daemon.GetActiveProfileResponse\"\x00B\bZ\x06/protob\x06proto3"
|
||||
"\x10GetActiveProfile\x12\x1f.daemon.GetActiveProfileRequest\x1a .daemon.GetActiveProfileResponse\"\x00\x129\n" +
|
||||
"\x06Logout\x12\x15.daemon.LogoutRequest\x1a\x16.daemon.LogoutResponse\"\x00B\bZ\x06/protob\x06proto3"
|
||||
|
||||
var (
|
||||
file_daemon_proto_rawDescOnce sync.Once
|
||||
@@ -4832,88 +4927,90 @@ func file_daemon_proto_rawDescGZIP() []byte {
|
||||
}
|
||||
|
||||
var file_daemon_proto_enumTypes = make([]protoimpl.EnumInfo, 3)
|
||||
var file_daemon_proto_msgTypes = make([]protoimpl.MessageInfo, 68)
|
||||
var file_daemon_proto_msgTypes = make([]protoimpl.MessageInfo, 70)
|
||||
var file_daemon_proto_goTypes = []any{
|
||||
(LogLevel)(0), // 0: daemon.LogLevel
|
||||
(SystemEvent_Severity)(0), // 1: daemon.SystemEvent.Severity
|
||||
(SystemEvent_Category)(0), // 2: daemon.SystemEvent.Category
|
||||
(*EmptyRequest)(nil), // 3: daemon.EmptyRequest
|
||||
(*LoginRequest)(nil), // 4: daemon.LoginRequest
|
||||
(*LoginResponse)(nil), // 5: daemon.LoginResponse
|
||||
(*WaitSSOLoginRequest)(nil), // 6: daemon.WaitSSOLoginRequest
|
||||
(*WaitSSOLoginResponse)(nil), // 7: daemon.WaitSSOLoginResponse
|
||||
(*UpRequest)(nil), // 8: daemon.UpRequest
|
||||
(*UpResponse)(nil), // 9: daemon.UpResponse
|
||||
(*StatusRequest)(nil), // 10: daemon.StatusRequest
|
||||
(*StatusResponse)(nil), // 11: daemon.StatusResponse
|
||||
(*DownRequest)(nil), // 12: daemon.DownRequest
|
||||
(*DownResponse)(nil), // 13: daemon.DownResponse
|
||||
(*GetConfigRequest)(nil), // 14: daemon.GetConfigRequest
|
||||
(*GetConfigResponse)(nil), // 15: daemon.GetConfigResponse
|
||||
(*PeerState)(nil), // 16: daemon.PeerState
|
||||
(*LocalPeerState)(nil), // 17: daemon.LocalPeerState
|
||||
(*SignalState)(nil), // 18: daemon.SignalState
|
||||
(*ManagementState)(nil), // 19: daemon.ManagementState
|
||||
(*RelayState)(nil), // 20: daemon.RelayState
|
||||
(*NSGroupState)(nil), // 21: daemon.NSGroupState
|
||||
(*FullStatus)(nil), // 22: daemon.FullStatus
|
||||
(*ListNetworksRequest)(nil), // 23: daemon.ListNetworksRequest
|
||||
(*ListNetworksResponse)(nil), // 24: daemon.ListNetworksResponse
|
||||
(*SelectNetworksRequest)(nil), // 25: daemon.SelectNetworksRequest
|
||||
(*SelectNetworksResponse)(nil), // 26: daemon.SelectNetworksResponse
|
||||
(*IPList)(nil), // 27: daemon.IPList
|
||||
(*Network)(nil), // 28: daemon.Network
|
||||
(*PortInfo)(nil), // 29: daemon.PortInfo
|
||||
(*ForwardingRule)(nil), // 30: daemon.ForwardingRule
|
||||
(*ForwardingRulesResponse)(nil), // 31: daemon.ForwardingRulesResponse
|
||||
(*DebugBundleRequest)(nil), // 32: daemon.DebugBundleRequest
|
||||
(*DebugBundleResponse)(nil), // 33: daemon.DebugBundleResponse
|
||||
(*GetLogLevelRequest)(nil), // 34: daemon.GetLogLevelRequest
|
||||
(*GetLogLevelResponse)(nil), // 35: daemon.GetLogLevelResponse
|
||||
(*SetLogLevelRequest)(nil), // 36: daemon.SetLogLevelRequest
|
||||
(*SetLogLevelResponse)(nil), // 37: daemon.SetLogLevelResponse
|
||||
(*State)(nil), // 38: daemon.State
|
||||
(*ListStatesRequest)(nil), // 39: daemon.ListStatesRequest
|
||||
(*ListStatesResponse)(nil), // 40: daemon.ListStatesResponse
|
||||
(*CleanStateRequest)(nil), // 41: daemon.CleanStateRequest
|
||||
(*CleanStateResponse)(nil), // 42: daemon.CleanStateResponse
|
||||
(*DeleteStateRequest)(nil), // 43: daemon.DeleteStateRequest
|
||||
(*DeleteStateResponse)(nil), // 44: daemon.DeleteStateResponse
|
||||
(*SetNetworkMapPersistenceRequest)(nil), // 45: daemon.SetNetworkMapPersistenceRequest
|
||||
(*SetNetworkMapPersistenceResponse)(nil), // 46: daemon.SetNetworkMapPersistenceResponse
|
||||
(*TCPFlags)(nil), // 47: daemon.TCPFlags
|
||||
(*TracePacketRequest)(nil), // 48: daemon.TracePacketRequest
|
||||
(*TraceStage)(nil), // 49: daemon.TraceStage
|
||||
(*TracePacketResponse)(nil), // 50: daemon.TracePacketResponse
|
||||
(*SubscribeRequest)(nil), // 51: daemon.SubscribeRequest
|
||||
(*SystemEvent)(nil), // 52: daemon.SystemEvent
|
||||
(*GetEventsRequest)(nil), // 53: daemon.GetEventsRequest
|
||||
(*GetEventsResponse)(nil), // 54: daemon.GetEventsResponse
|
||||
(*SwitchProfileRequest)(nil), // 55: daemon.SwitchProfileRequest
|
||||
(*SwitchProfileResponse)(nil), // 56: daemon.SwitchProfileResponse
|
||||
(*SetConfigRequest)(nil), // 57: daemon.SetConfigRequest
|
||||
(*SetConfigResponse)(nil), // 58: daemon.SetConfigResponse
|
||||
(*AddProfileRequest)(nil), // 59: daemon.AddProfileRequest
|
||||
(*AddProfileResponse)(nil), // 60: daemon.AddProfileResponse
|
||||
(*RemoveProfileRequest)(nil), // 61: daemon.RemoveProfileRequest
|
||||
(*RemoveProfileResponse)(nil), // 62: daemon.RemoveProfileResponse
|
||||
(*ListProfilesRequest)(nil), // 63: daemon.ListProfilesRequest
|
||||
(*ListProfilesResponse)(nil), // 64: daemon.ListProfilesResponse
|
||||
(*Profile)(nil), // 65: daemon.Profile
|
||||
(*GetActiveProfileRequest)(nil), // 66: daemon.GetActiveProfileRequest
|
||||
(*GetActiveProfileResponse)(nil), // 67: daemon.GetActiveProfileResponse
|
||||
nil, // 68: daemon.Network.ResolvedIPsEntry
|
||||
(*PortInfo_Range)(nil), // 69: daemon.PortInfo.Range
|
||||
nil, // 70: daemon.SystemEvent.MetadataEntry
|
||||
(*durationpb.Duration)(nil), // 71: google.protobuf.Duration
|
||||
(*timestamppb.Timestamp)(nil), // 72: google.protobuf.Timestamp
|
||||
(LogLevel)(0), // 0: daemon.LogLevel
|
||||
(SystemEvent_Severity)(0), // 1: daemon.SystemEvent.Severity
|
||||
(SystemEvent_Category)(0), // 2: daemon.SystemEvent.Category
|
||||
(*EmptyRequest)(nil), // 3: daemon.EmptyRequest
|
||||
(*LoginRequest)(nil), // 4: daemon.LoginRequest
|
||||
(*LoginResponse)(nil), // 5: daemon.LoginResponse
|
||||
(*WaitSSOLoginRequest)(nil), // 6: daemon.WaitSSOLoginRequest
|
||||
(*WaitSSOLoginResponse)(nil), // 7: daemon.WaitSSOLoginResponse
|
||||
(*UpRequest)(nil), // 8: daemon.UpRequest
|
||||
(*UpResponse)(nil), // 9: daemon.UpResponse
|
||||
(*StatusRequest)(nil), // 10: daemon.StatusRequest
|
||||
(*StatusResponse)(nil), // 11: daemon.StatusResponse
|
||||
(*DownRequest)(nil), // 12: daemon.DownRequest
|
||||
(*DownResponse)(nil), // 13: daemon.DownResponse
|
||||
(*GetConfigRequest)(nil), // 14: daemon.GetConfigRequest
|
||||
(*GetConfigResponse)(nil), // 15: daemon.GetConfigResponse
|
||||
(*PeerState)(nil), // 16: daemon.PeerState
|
||||
(*LocalPeerState)(nil), // 17: daemon.LocalPeerState
|
||||
(*SignalState)(nil), // 18: daemon.SignalState
|
||||
(*ManagementState)(nil), // 19: daemon.ManagementState
|
||||
(*RelayState)(nil), // 20: daemon.RelayState
|
||||
(*NSGroupState)(nil), // 21: daemon.NSGroupState
|
||||
(*FullStatus)(nil), // 22: daemon.FullStatus
|
||||
(*ListNetworksRequest)(nil), // 23: daemon.ListNetworksRequest
|
||||
(*ListNetworksResponse)(nil), // 24: daemon.ListNetworksResponse
|
||||
(*SelectNetworksRequest)(nil), // 25: daemon.SelectNetworksRequest
|
||||
(*SelectNetworksResponse)(nil), // 26: daemon.SelectNetworksResponse
|
||||
(*IPList)(nil), // 27: daemon.IPList
|
||||
(*Network)(nil), // 28: daemon.Network
|
||||
(*PortInfo)(nil), // 29: daemon.PortInfo
|
||||
(*ForwardingRule)(nil), // 30: daemon.ForwardingRule
|
||||
(*ForwardingRulesResponse)(nil), // 31: daemon.ForwardingRulesResponse
|
||||
(*DebugBundleRequest)(nil), // 32: daemon.DebugBundleRequest
|
||||
(*DebugBundleResponse)(nil), // 33: daemon.DebugBundleResponse
|
||||
(*GetLogLevelRequest)(nil), // 34: daemon.GetLogLevelRequest
|
||||
(*GetLogLevelResponse)(nil), // 35: daemon.GetLogLevelResponse
|
||||
(*SetLogLevelRequest)(nil), // 36: daemon.SetLogLevelRequest
|
||||
(*SetLogLevelResponse)(nil), // 37: daemon.SetLogLevelResponse
|
||||
(*State)(nil), // 38: daemon.State
|
||||
(*ListStatesRequest)(nil), // 39: daemon.ListStatesRequest
|
||||
(*ListStatesResponse)(nil), // 40: daemon.ListStatesResponse
|
||||
(*CleanStateRequest)(nil), // 41: daemon.CleanStateRequest
|
||||
(*CleanStateResponse)(nil), // 42: daemon.CleanStateResponse
|
||||
(*DeleteStateRequest)(nil), // 43: daemon.DeleteStateRequest
|
||||
(*DeleteStateResponse)(nil), // 44: daemon.DeleteStateResponse
|
||||
(*SetSyncResponsePersistenceRequest)(nil), // 45: daemon.SetSyncResponsePersistenceRequest
|
||||
(*SetSyncResponsePersistenceResponse)(nil), // 46: daemon.SetSyncResponsePersistenceResponse
|
||||
(*TCPFlags)(nil), // 47: daemon.TCPFlags
|
||||
(*TracePacketRequest)(nil), // 48: daemon.TracePacketRequest
|
||||
(*TraceStage)(nil), // 49: daemon.TraceStage
|
||||
(*TracePacketResponse)(nil), // 50: daemon.TracePacketResponse
|
||||
(*SubscribeRequest)(nil), // 51: daemon.SubscribeRequest
|
||||
(*SystemEvent)(nil), // 52: daemon.SystemEvent
|
||||
(*GetEventsRequest)(nil), // 53: daemon.GetEventsRequest
|
||||
(*GetEventsResponse)(nil), // 54: daemon.GetEventsResponse
|
||||
(*SwitchProfileRequest)(nil), // 55: daemon.SwitchProfileRequest
|
||||
(*SwitchProfileResponse)(nil), // 56: daemon.SwitchProfileResponse
|
||||
(*SetConfigRequest)(nil), // 57: daemon.SetConfigRequest
|
||||
(*SetConfigResponse)(nil), // 58: daemon.SetConfigResponse
|
||||
(*AddProfileRequest)(nil), // 59: daemon.AddProfileRequest
|
||||
(*AddProfileResponse)(nil), // 60: daemon.AddProfileResponse
|
||||
(*RemoveProfileRequest)(nil), // 61: daemon.RemoveProfileRequest
|
||||
(*RemoveProfileResponse)(nil), // 62: daemon.RemoveProfileResponse
|
||||
(*ListProfilesRequest)(nil), // 63: daemon.ListProfilesRequest
|
||||
(*ListProfilesResponse)(nil), // 64: daemon.ListProfilesResponse
|
||||
(*Profile)(nil), // 65: daemon.Profile
|
||||
(*GetActiveProfileRequest)(nil), // 66: daemon.GetActiveProfileRequest
|
||||
(*GetActiveProfileResponse)(nil), // 67: daemon.GetActiveProfileResponse
|
||||
(*LogoutRequest)(nil), // 68: daemon.LogoutRequest
|
||||
(*LogoutResponse)(nil), // 69: daemon.LogoutResponse
|
||||
nil, // 70: daemon.Network.ResolvedIPsEntry
|
||||
(*PortInfo_Range)(nil), // 71: daemon.PortInfo.Range
|
||||
nil, // 72: daemon.SystemEvent.MetadataEntry
|
||||
(*durationpb.Duration)(nil), // 73: google.protobuf.Duration
|
||||
(*timestamppb.Timestamp)(nil), // 74: google.protobuf.Timestamp
|
||||
}
|
||||
var file_daemon_proto_depIdxs = []int32{
|
||||
71, // 0: daemon.LoginRequest.dnsRouteInterval:type_name -> google.protobuf.Duration
|
||||
73, // 0: daemon.LoginRequest.dnsRouteInterval:type_name -> google.protobuf.Duration
|
||||
22, // 1: daemon.StatusResponse.fullStatus:type_name -> daemon.FullStatus
|
||||
72, // 2: daemon.PeerState.connStatusUpdate:type_name -> google.protobuf.Timestamp
|
||||
72, // 3: daemon.PeerState.lastWireguardHandshake:type_name -> google.protobuf.Timestamp
|
||||
71, // 4: daemon.PeerState.latency:type_name -> google.protobuf.Duration
|
||||
74, // 2: daemon.PeerState.connStatusUpdate:type_name -> google.protobuf.Timestamp
|
||||
74, // 3: daemon.PeerState.lastWireguardHandshake:type_name -> google.protobuf.Timestamp
|
||||
73, // 4: daemon.PeerState.latency:type_name -> google.protobuf.Duration
|
||||
19, // 5: daemon.FullStatus.managementState:type_name -> daemon.ManagementState
|
||||
18, // 6: daemon.FullStatus.signalState:type_name -> daemon.SignalState
|
||||
17, // 7: daemon.FullStatus.localPeerState:type_name -> daemon.LocalPeerState
|
||||
@@ -4922,8 +5019,8 @@ var file_daemon_proto_depIdxs = []int32{
|
||||
21, // 10: daemon.FullStatus.dns_servers:type_name -> daemon.NSGroupState
|
||||
52, // 11: daemon.FullStatus.events:type_name -> daemon.SystemEvent
|
||||
28, // 12: daemon.ListNetworksResponse.routes:type_name -> daemon.Network
|
||||
68, // 13: daemon.Network.resolvedIPs:type_name -> daemon.Network.ResolvedIPsEntry
|
||||
69, // 14: daemon.PortInfo.range:type_name -> daemon.PortInfo.Range
|
||||
70, // 13: daemon.Network.resolvedIPs:type_name -> daemon.Network.ResolvedIPsEntry
|
||||
71, // 14: daemon.PortInfo.range:type_name -> daemon.PortInfo.Range
|
||||
29, // 15: daemon.ForwardingRule.destinationPort:type_name -> daemon.PortInfo
|
||||
29, // 16: daemon.ForwardingRule.translatedPort:type_name -> daemon.PortInfo
|
||||
30, // 17: daemon.ForwardingRulesResponse.rules:type_name -> daemon.ForwardingRule
|
||||
@@ -4934,10 +5031,10 @@ var file_daemon_proto_depIdxs = []int32{
|
||||
49, // 22: daemon.TracePacketResponse.stages:type_name -> daemon.TraceStage
|
||||
1, // 23: daemon.SystemEvent.severity:type_name -> daemon.SystemEvent.Severity
|
||||
2, // 24: daemon.SystemEvent.category:type_name -> daemon.SystemEvent.Category
|
||||
72, // 25: daemon.SystemEvent.timestamp:type_name -> google.protobuf.Timestamp
|
||||
70, // 26: daemon.SystemEvent.metadata:type_name -> daemon.SystemEvent.MetadataEntry
|
||||
74, // 25: daemon.SystemEvent.timestamp:type_name -> google.protobuf.Timestamp
|
||||
72, // 26: daemon.SystemEvent.metadata:type_name -> daemon.SystemEvent.MetadataEntry
|
||||
52, // 27: daemon.GetEventsResponse.events:type_name -> daemon.SystemEvent
|
||||
71, // 28: daemon.SetConfigRequest.dnsRouteInterval:type_name -> google.protobuf.Duration
|
||||
73, // 28: daemon.SetConfigRequest.dnsRouteInterval:type_name -> google.protobuf.Duration
|
||||
65, // 29: daemon.ListProfilesResponse.profiles:type_name -> daemon.Profile
|
||||
27, // 30: daemon.Network.ResolvedIPsEntry.value:type_name -> daemon.IPList
|
||||
4, // 31: daemon.DaemonService.Login:input_type -> daemon.LoginRequest
|
||||
@@ -4956,7 +5053,7 @@ var file_daemon_proto_depIdxs = []int32{
|
||||
39, // 44: daemon.DaemonService.ListStates:input_type -> daemon.ListStatesRequest
|
||||
41, // 45: daemon.DaemonService.CleanState:input_type -> daemon.CleanStateRequest
|
||||
43, // 46: daemon.DaemonService.DeleteState:input_type -> daemon.DeleteStateRequest
|
||||
45, // 47: daemon.DaemonService.SetNetworkMapPersistence:input_type -> daemon.SetNetworkMapPersistenceRequest
|
||||
45, // 47: daemon.DaemonService.SetSyncResponsePersistence:input_type -> daemon.SetSyncResponsePersistenceRequest
|
||||
48, // 48: daemon.DaemonService.TracePacket:input_type -> daemon.TracePacketRequest
|
||||
51, // 49: daemon.DaemonService.SubscribeEvents:input_type -> daemon.SubscribeRequest
|
||||
53, // 50: daemon.DaemonService.GetEvents:input_type -> daemon.GetEventsRequest
|
||||
@@ -4966,34 +5063,36 @@ var file_daemon_proto_depIdxs = []int32{
|
||||
61, // 54: daemon.DaemonService.RemoveProfile:input_type -> daemon.RemoveProfileRequest
|
||||
63, // 55: daemon.DaemonService.ListProfiles:input_type -> daemon.ListProfilesRequest
|
||||
66, // 56: daemon.DaemonService.GetActiveProfile:input_type -> daemon.GetActiveProfileRequest
|
||||
5, // 57: daemon.DaemonService.Login:output_type -> daemon.LoginResponse
|
||||
7, // 58: daemon.DaemonService.WaitSSOLogin:output_type -> daemon.WaitSSOLoginResponse
|
||||
9, // 59: daemon.DaemonService.Up:output_type -> daemon.UpResponse
|
||||
11, // 60: daemon.DaemonService.Status:output_type -> daemon.StatusResponse
|
||||
13, // 61: daemon.DaemonService.Down:output_type -> daemon.DownResponse
|
||||
15, // 62: daemon.DaemonService.GetConfig:output_type -> daemon.GetConfigResponse
|
||||
24, // 63: daemon.DaemonService.ListNetworks:output_type -> daemon.ListNetworksResponse
|
||||
26, // 64: daemon.DaemonService.SelectNetworks:output_type -> daemon.SelectNetworksResponse
|
||||
26, // 65: daemon.DaemonService.DeselectNetworks:output_type -> daemon.SelectNetworksResponse
|
||||
31, // 66: daemon.DaemonService.ForwardingRules:output_type -> daemon.ForwardingRulesResponse
|
||||
33, // 67: daemon.DaemonService.DebugBundle:output_type -> daemon.DebugBundleResponse
|
||||
35, // 68: daemon.DaemonService.GetLogLevel:output_type -> daemon.GetLogLevelResponse
|
||||
37, // 69: daemon.DaemonService.SetLogLevel:output_type -> daemon.SetLogLevelResponse
|
||||
40, // 70: daemon.DaemonService.ListStates:output_type -> daemon.ListStatesResponse
|
||||
42, // 71: daemon.DaemonService.CleanState:output_type -> daemon.CleanStateResponse
|
||||
44, // 72: daemon.DaemonService.DeleteState:output_type -> daemon.DeleteStateResponse
|
||||
46, // 73: daemon.DaemonService.SetNetworkMapPersistence:output_type -> daemon.SetNetworkMapPersistenceResponse
|
||||
50, // 74: daemon.DaemonService.TracePacket:output_type -> daemon.TracePacketResponse
|
||||
52, // 75: daemon.DaemonService.SubscribeEvents:output_type -> daemon.SystemEvent
|
||||
54, // 76: daemon.DaemonService.GetEvents:output_type -> daemon.GetEventsResponse
|
||||
56, // 77: daemon.DaemonService.SwitchProfile:output_type -> daemon.SwitchProfileResponse
|
||||
58, // 78: daemon.DaemonService.SetConfig:output_type -> daemon.SetConfigResponse
|
||||
60, // 79: daemon.DaemonService.AddProfile:output_type -> daemon.AddProfileResponse
|
||||
62, // 80: daemon.DaemonService.RemoveProfile:output_type -> daemon.RemoveProfileResponse
|
||||
64, // 81: daemon.DaemonService.ListProfiles:output_type -> daemon.ListProfilesResponse
|
||||
67, // 82: daemon.DaemonService.GetActiveProfile:output_type -> daemon.GetActiveProfileResponse
|
||||
57, // [57:83] is the sub-list for method output_type
|
||||
31, // [31:57] is the sub-list for method input_type
|
||||
68, // 57: daemon.DaemonService.Logout:input_type -> daemon.LogoutRequest
|
||||
5, // 58: daemon.DaemonService.Login:output_type -> daemon.LoginResponse
|
||||
7, // 59: daemon.DaemonService.WaitSSOLogin:output_type -> daemon.WaitSSOLoginResponse
|
||||
9, // 60: daemon.DaemonService.Up:output_type -> daemon.UpResponse
|
||||
11, // 61: daemon.DaemonService.Status:output_type -> daemon.StatusResponse
|
||||
13, // 62: daemon.DaemonService.Down:output_type -> daemon.DownResponse
|
||||
15, // 63: daemon.DaemonService.GetConfig:output_type -> daemon.GetConfigResponse
|
||||
24, // 64: daemon.DaemonService.ListNetworks:output_type -> daemon.ListNetworksResponse
|
||||
26, // 65: daemon.DaemonService.SelectNetworks:output_type -> daemon.SelectNetworksResponse
|
||||
26, // 66: daemon.DaemonService.DeselectNetworks:output_type -> daemon.SelectNetworksResponse
|
||||
31, // 67: daemon.DaemonService.ForwardingRules:output_type -> daemon.ForwardingRulesResponse
|
||||
33, // 68: daemon.DaemonService.DebugBundle:output_type -> daemon.DebugBundleResponse
|
||||
35, // 69: daemon.DaemonService.GetLogLevel:output_type -> daemon.GetLogLevelResponse
|
||||
37, // 70: daemon.DaemonService.SetLogLevel:output_type -> daemon.SetLogLevelResponse
|
||||
40, // 71: daemon.DaemonService.ListStates:output_type -> daemon.ListStatesResponse
|
||||
42, // 72: daemon.DaemonService.CleanState:output_type -> daemon.CleanStateResponse
|
||||
44, // 73: daemon.DaemonService.DeleteState:output_type -> daemon.DeleteStateResponse
|
||||
46, // 74: daemon.DaemonService.SetSyncResponsePersistence:output_type -> daemon.SetSyncResponsePersistenceResponse
|
||||
50, // 75: daemon.DaemonService.TracePacket:output_type -> daemon.TracePacketResponse
|
||||
52, // 76: daemon.DaemonService.SubscribeEvents:output_type -> daemon.SystemEvent
|
||||
54, // 77: daemon.DaemonService.GetEvents:output_type -> daemon.GetEventsResponse
|
||||
56, // 78: daemon.DaemonService.SwitchProfile:output_type -> daemon.SwitchProfileResponse
|
||||
58, // 79: daemon.DaemonService.SetConfig:output_type -> daemon.SetConfigResponse
|
||||
60, // 80: daemon.DaemonService.AddProfile:output_type -> daemon.AddProfileResponse
|
||||
62, // 81: daemon.DaemonService.RemoveProfile:output_type -> daemon.RemoveProfileResponse
|
||||
64, // 82: daemon.DaemonService.ListProfiles:output_type -> daemon.ListProfilesResponse
|
||||
67, // 83: daemon.DaemonService.GetActiveProfile:output_type -> daemon.GetActiveProfileResponse
|
||||
69, // 84: daemon.DaemonService.Logout:output_type -> daemon.LogoutResponse
|
||||
58, // [58:85] is the sub-list for method output_type
|
||||
31, // [31:58] is the sub-list for method input_type
|
||||
31, // [31:31] is the sub-list for extension type_name
|
||||
31, // [31:31] is the sub-list for extension extendee
|
||||
0, // [0:31] is the sub-list for field type_name
|
||||
@@ -5014,13 +5113,14 @@ func file_daemon_proto_init() {
|
||||
file_daemon_proto_msgTypes[46].OneofWrappers = []any{}
|
||||
file_daemon_proto_msgTypes[52].OneofWrappers = []any{}
|
||||
file_daemon_proto_msgTypes[54].OneofWrappers = []any{}
|
||||
file_daemon_proto_msgTypes[65].OneofWrappers = []any{}
|
||||
type x struct{}
|
||||
out := protoimpl.TypeBuilder{
|
||||
File: protoimpl.DescBuilder{
|
||||
GoPackagePath: reflect.TypeOf(x{}).PkgPath(),
|
||||
RawDescriptor: unsafe.Slice(unsafe.StringData(file_daemon_proto_rawDesc), len(file_daemon_proto_rawDesc)),
|
||||
NumEnums: 3,
|
||||
NumMessages: 68,
|
||||
NumMessages: 70,
|
||||
NumExtensions: 0,
|
||||
NumServices: 1,
|
||||
},
|
||||
|
||||
@@ -59,8 +59,8 @@ service DaemonService {
|
||||
// Delete specific state or all states
|
||||
rpc DeleteState(DeleteStateRequest) returns (DeleteStateResponse) {}
|
||||
|
||||
// SetNetworkMapPersistence enables or disables network map persistence
|
||||
rpc SetNetworkMapPersistence(SetNetworkMapPersistenceRequest) returns (SetNetworkMapPersistenceResponse) {}
|
||||
// SetSyncResponsePersistence enables or disables sync response persistence
|
||||
rpc SetSyncResponsePersistence(SetSyncResponsePersistenceRequest) returns (SetSyncResponsePersistenceResponse) {}
|
||||
|
||||
rpc TracePacket(TracePacketRequest) returns (TracePacketResponse) {}
|
||||
|
||||
@@ -79,6 +79,9 @@ service DaemonService {
|
||||
rpc ListProfiles(ListProfilesRequest) returns (ListProfilesResponse) {}
|
||||
|
||||
rpc GetActiveProfile(GetActiveProfileRequest) returns (GetActiveProfileResponse) {}
|
||||
|
||||
// Logout disconnects from the network and deletes the peer from the management server
|
||||
rpc Logout(LogoutRequest) returns (LogoutResponse) {}
|
||||
}
|
||||
|
||||
|
||||
@@ -449,11 +452,11 @@ message DeleteStateResponse {
|
||||
}
|
||||
|
||||
|
||||
message SetNetworkMapPersistenceRequest {
|
||||
message SetSyncResponsePersistenceRequest {
|
||||
bool enabled = 1;
|
||||
}
|
||||
|
||||
message SetNetworkMapPersistenceResponse {}
|
||||
message SetSyncResponsePersistenceResponse {}
|
||||
|
||||
message TCPFlags {
|
||||
bool syn = 1;
|
||||
@@ -614,4 +617,11 @@ message GetActiveProfileRequest {}
|
||||
message GetActiveProfileResponse {
|
||||
string profileName = 1;
|
||||
string username = 2;
|
||||
}
|
||||
}
|
||||
|
||||
message LogoutRequest {
|
||||
optional string profileName = 1;
|
||||
optional string username = 2;
|
||||
}
|
||||
|
||||
message LogoutResponse {}
|
||||
@@ -50,8 +50,8 @@ type DaemonServiceClient interface {
|
||||
CleanState(ctx context.Context, in *CleanStateRequest, opts ...grpc.CallOption) (*CleanStateResponse, error)
|
||||
// Delete specific state or all states
|
||||
DeleteState(ctx context.Context, in *DeleteStateRequest, opts ...grpc.CallOption) (*DeleteStateResponse, error)
|
||||
// SetNetworkMapPersistence enables or disables network map persistence
|
||||
SetNetworkMapPersistence(ctx context.Context, in *SetNetworkMapPersistenceRequest, opts ...grpc.CallOption) (*SetNetworkMapPersistenceResponse, error)
|
||||
// SetSyncResponsePersistence enables or disables sync response persistence
|
||||
SetSyncResponsePersistence(ctx context.Context, in *SetSyncResponsePersistenceRequest, opts ...grpc.CallOption) (*SetSyncResponsePersistenceResponse, error)
|
||||
TracePacket(ctx context.Context, in *TracePacketRequest, opts ...grpc.CallOption) (*TracePacketResponse, error)
|
||||
SubscribeEvents(ctx context.Context, in *SubscribeRequest, opts ...grpc.CallOption) (DaemonService_SubscribeEventsClient, error)
|
||||
GetEvents(ctx context.Context, in *GetEventsRequest, opts ...grpc.CallOption) (*GetEventsResponse, error)
|
||||
@@ -61,6 +61,8 @@ type DaemonServiceClient interface {
|
||||
RemoveProfile(ctx context.Context, in *RemoveProfileRequest, opts ...grpc.CallOption) (*RemoveProfileResponse, error)
|
||||
ListProfiles(ctx context.Context, in *ListProfilesRequest, opts ...grpc.CallOption) (*ListProfilesResponse, error)
|
||||
GetActiveProfile(ctx context.Context, in *GetActiveProfileRequest, opts ...grpc.CallOption) (*GetActiveProfileResponse, error)
|
||||
// Logout disconnects from the network and deletes the peer from the management server
|
||||
Logout(ctx context.Context, in *LogoutRequest, opts ...grpc.CallOption) (*LogoutResponse, error)
|
||||
}
|
||||
|
||||
type daemonServiceClient struct {
|
||||
@@ -215,9 +217,9 @@ func (c *daemonServiceClient) DeleteState(ctx context.Context, in *DeleteStateRe
|
||||
return out, nil
|
||||
}
|
||||
|
||||
func (c *daemonServiceClient) SetNetworkMapPersistence(ctx context.Context, in *SetNetworkMapPersistenceRequest, opts ...grpc.CallOption) (*SetNetworkMapPersistenceResponse, error) {
|
||||
out := new(SetNetworkMapPersistenceResponse)
|
||||
err := c.cc.Invoke(ctx, "/daemon.DaemonService/SetNetworkMapPersistence", in, out, opts...)
|
||||
func (c *daemonServiceClient) SetSyncResponsePersistence(ctx context.Context, in *SetSyncResponsePersistenceRequest, opts ...grpc.CallOption) (*SetSyncResponsePersistenceResponse, error) {
|
||||
out := new(SetSyncResponsePersistenceResponse)
|
||||
err := c.cc.Invoke(ctx, "/daemon.DaemonService/SetSyncResponsePersistence", in, out, opts...)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
@@ -328,6 +330,15 @@ func (c *daemonServiceClient) GetActiveProfile(ctx context.Context, in *GetActiv
|
||||
return out, nil
|
||||
}
|
||||
|
||||
func (c *daemonServiceClient) Logout(ctx context.Context, in *LogoutRequest, opts ...grpc.CallOption) (*LogoutResponse, error) {
|
||||
out := new(LogoutResponse)
|
||||
err := c.cc.Invoke(ctx, "/daemon.DaemonService/Logout", in, out, opts...)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
return out, nil
|
||||
}
|
||||
|
||||
// DaemonServiceServer is the server API for DaemonService service.
|
||||
// All implementations must embed UnimplementedDaemonServiceServer
|
||||
// for forward compatibility
|
||||
@@ -364,8 +375,8 @@ type DaemonServiceServer interface {
|
||||
CleanState(context.Context, *CleanStateRequest) (*CleanStateResponse, error)
|
||||
// Delete specific state or all states
|
||||
DeleteState(context.Context, *DeleteStateRequest) (*DeleteStateResponse, error)
|
||||
// SetNetworkMapPersistence enables or disables network map persistence
|
||||
SetNetworkMapPersistence(context.Context, *SetNetworkMapPersistenceRequest) (*SetNetworkMapPersistenceResponse, error)
|
||||
// SetSyncResponsePersistence enables or disables sync response persistence
|
||||
SetSyncResponsePersistence(context.Context, *SetSyncResponsePersistenceRequest) (*SetSyncResponsePersistenceResponse, error)
|
||||
TracePacket(context.Context, *TracePacketRequest) (*TracePacketResponse, error)
|
||||
SubscribeEvents(*SubscribeRequest, DaemonService_SubscribeEventsServer) error
|
||||
GetEvents(context.Context, *GetEventsRequest) (*GetEventsResponse, error)
|
||||
@@ -375,6 +386,8 @@ type DaemonServiceServer interface {
|
||||
RemoveProfile(context.Context, *RemoveProfileRequest) (*RemoveProfileResponse, error)
|
||||
ListProfiles(context.Context, *ListProfilesRequest) (*ListProfilesResponse, error)
|
||||
GetActiveProfile(context.Context, *GetActiveProfileRequest) (*GetActiveProfileResponse, error)
|
||||
// Logout disconnects from the network and deletes the peer from the management server
|
||||
Logout(context.Context, *LogoutRequest) (*LogoutResponse, error)
|
||||
mustEmbedUnimplementedDaemonServiceServer()
|
||||
}
|
||||
|
||||
@@ -430,8 +443,8 @@ func (UnimplementedDaemonServiceServer) CleanState(context.Context, *CleanStateR
|
||||
func (UnimplementedDaemonServiceServer) DeleteState(context.Context, *DeleteStateRequest) (*DeleteStateResponse, error) {
|
||||
return nil, status.Errorf(codes.Unimplemented, "method DeleteState not implemented")
|
||||
}
|
||||
func (UnimplementedDaemonServiceServer) SetNetworkMapPersistence(context.Context, *SetNetworkMapPersistenceRequest) (*SetNetworkMapPersistenceResponse, error) {
|
||||
return nil, status.Errorf(codes.Unimplemented, "method SetNetworkMapPersistence not implemented")
|
||||
func (UnimplementedDaemonServiceServer) SetSyncResponsePersistence(context.Context, *SetSyncResponsePersistenceRequest) (*SetSyncResponsePersistenceResponse, error) {
|
||||
return nil, status.Errorf(codes.Unimplemented, "method SetSyncResponsePersistence not implemented")
|
||||
}
|
||||
func (UnimplementedDaemonServiceServer) TracePacket(context.Context, *TracePacketRequest) (*TracePacketResponse, error) {
|
||||
return nil, status.Errorf(codes.Unimplemented, "method TracePacket not implemented")
|
||||
@@ -460,6 +473,9 @@ func (UnimplementedDaemonServiceServer) ListProfiles(context.Context, *ListProfi
|
||||
func (UnimplementedDaemonServiceServer) GetActiveProfile(context.Context, *GetActiveProfileRequest) (*GetActiveProfileResponse, error) {
|
||||
return nil, status.Errorf(codes.Unimplemented, "method GetActiveProfile not implemented")
|
||||
}
|
||||
func (UnimplementedDaemonServiceServer) Logout(context.Context, *LogoutRequest) (*LogoutResponse, error) {
|
||||
return nil, status.Errorf(codes.Unimplemented, "method Logout not implemented")
|
||||
}
|
||||
func (UnimplementedDaemonServiceServer) mustEmbedUnimplementedDaemonServiceServer() {}
|
||||
|
||||
// UnsafeDaemonServiceServer may be embedded to opt out of forward compatibility for this service.
|
||||
@@ -761,20 +777,20 @@ func _DaemonService_DeleteState_Handler(srv interface{}, ctx context.Context, de
|
||||
return interceptor(ctx, in, info, handler)
|
||||
}
|
||||
|
||||
func _DaemonService_SetNetworkMapPersistence_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
|
||||
in := new(SetNetworkMapPersistenceRequest)
|
||||
func _DaemonService_SetSyncResponsePersistence_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
|
||||
in := new(SetSyncResponsePersistenceRequest)
|
||||
if err := dec(in); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
if interceptor == nil {
|
||||
return srv.(DaemonServiceServer).SetNetworkMapPersistence(ctx, in)
|
||||
return srv.(DaemonServiceServer).SetSyncResponsePersistence(ctx, in)
|
||||
}
|
||||
info := &grpc.UnaryServerInfo{
|
||||
Server: srv,
|
||||
FullMethod: "/daemon.DaemonService/SetNetworkMapPersistence",
|
||||
FullMethod: "/daemon.DaemonService/SetSyncResponsePersistence",
|
||||
}
|
||||
handler := func(ctx context.Context, req interface{}) (interface{}, error) {
|
||||
return srv.(DaemonServiceServer).SetNetworkMapPersistence(ctx, req.(*SetNetworkMapPersistenceRequest))
|
||||
return srv.(DaemonServiceServer).SetSyncResponsePersistence(ctx, req.(*SetSyncResponsePersistenceRequest))
|
||||
}
|
||||
return interceptor(ctx, in, info, handler)
|
||||
}
|
||||
@@ -944,6 +960,24 @@ func _DaemonService_GetActiveProfile_Handler(srv interface{}, ctx context.Contex
|
||||
return interceptor(ctx, in, info, handler)
|
||||
}
|
||||
|
||||
func _DaemonService_Logout_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) {
|
||||
in := new(LogoutRequest)
|
||||
if err := dec(in); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
if interceptor == nil {
|
||||
return srv.(DaemonServiceServer).Logout(ctx, in)
|
||||
}
|
||||
info := &grpc.UnaryServerInfo{
|
||||
Server: srv,
|
||||
FullMethod: "/daemon.DaemonService/Logout",
|
||||
}
|
||||
handler := func(ctx context.Context, req interface{}) (interface{}, error) {
|
||||
return srv.(DaemonServiceServer).Logout(ctx, req.(*LogoutRequest))
|
||||
}
|
||||
return interceptor(ctx, in, info, handler)
|
||||
}
|
||||
|
||||
// DaemonService_ServiceDesc is the grpc.ServiceDesc for DaemonService service.
|
||||
// It's only intended for direct use with grpc.RegisterService,
|
||||
// and not to be introspected or modified (even as a copy)
|
||||
@@ -1016,8 +1050,8 @@ var DaemonService_ServiceDesc = grpc.ServiceDesc{
|
||||
Handler: _DaemonService_DeleteState_Handler,
|
||||
},
|
||||
{
|
||||
MethodName: "SetNetworkMapPersistence",
|
||||
Handler: _DaemonService_SetNetworkMapPersistence_Handler,
|
||||
MethodName: "SetSyncResponsePersistence",
|
||||
Handler: _DaemonService_SetSyncResponsePersistence_Handler,
|
||||
},
|
||||
{
|
||||
MethodName: "TracePacket",
|
||||
@@ -1051,6 +1085,10 @@ var DaemonService_ServiceDesc = grpc.ServiceDesc{
|
||||
MethodName: "GetActiveProfile",
|
||||
Handler: _DaemonService_GetActiveProfile_Handler,
|
||||
},
|
||||
{
|
||||
MethodName: "Logout",
|
||||
Handler: _DaemonService_Logout_Handler,
|
||||
},
|
||||
},
|
||||
Streams: []grpc.StreamDesc{
|
||||
{
|
||||
|
||||
+12
-12
@@ -16,7 +16,7 @@ import (
|
||||
|
||||
"github.com/netbirdio/netbird/client/internal/debug"
|
||||
"github.com/netbirdio/netbird/client/proto"
|
||||
mgmProto "github.com/netbirdio/netbird/management/proto"
|
||||
mgmProto "github.com/netbirdio/netbird/shared/management/proto"
|
||||
"github.com/netbirdio/netbird/upload-server/types"
|
||||
)
|
||||
|
||||
@@ -27,15 +27,16 @@ func (s *Server) DebugBundle(_ context.Context, req *proto.DebugBundleRequest) (
|
||||
s.mutex.Lock()
|
||||
defer s.mutex.Unlock()
|
||||
|
||||
networkMap, err := s.getLatestNetworkMap()
|
||||
syncResponse, err := s.getLatestSyncResponse()
|
||||
if err != nil {
|
||||
log.Warnf("failed to get latest network map: %v", err)
|
||||
log.Warnf("failed to get latest sync response: %v", err)
|
||||
}
|
||||
|
||||
bundleGenerator := debug.NewBundleGenerator(
|
||||
debug.GeneratorDependencies{
|
||||
InternalConfig: s.config,
|
||||
StatusRecorder: s.statusRecorder,
|
||||
NetworkMap: networkMap,
|
||||
SyncResponse: syncResponse,
|
||||
LogFile: s.logFile,
|
||||
},
|
||||
debug.BundleConfig{
|
||||
@@ -192,26 +193,25 @@ func (s *Server) SetLogLevel(_ context.Context, req *proto.SetLogLevelRequest) (
|
||||
return &proto.SetLogLevelResponse{}, nil
|
||||
}
|
||||
|
||||
// SetNetworkMapPersistence sets the network map persistence for the server.
|
||||
func (s *Server) SetNetworkMapPersistence(_ context.Context, req *proto.SetNetworkMapPersistenceRequest) (*proto.SetNetworkMapPersistenceResponse, error) {
|
||||
// SetSyncResponsePersistence sets the sync response persistence for the server.
|
||||
func (s *Server) SetSyncResponsePersistence(_ context.Context, req *proto.SetSyncResponsePersistenceRequest) (*proto.SetSyncResponsePersistenceResponse, error) {
|
||||
s.mutex.Lock()
|
||||
defer s.mutex.Unlock()
|
||||
|
||||
enabled := req.GetEnabled()
|
||||
s.persistNetworkMap = enabled
|
||||
s.persistSyncResponse = enabled
|
||||
if s.connectClient != nil {
|
||||
s.connectClient.SetNetworkMapPersistence(enabled)
|
||||
s.connectClient.SetSyncResponsePersistence(enabled)
|
||||
}
|
||||
|
||||
return &proto.SetNetworkMapPersistenceResponse{}, nil
|
||||
return &proto.SetSyncResponsePersistenceResponse{}, nil
|
||||
}
|
||||
|
||||
// getLatestNetworkMap returns the latest network map from the engine if network map persistence is enabled
|
||||
func (s *Server) getLatestNetworkMap() (*mgmProto.NetworkMap, error) {
|
||||
func (s *Server) getLatestSyncResponse() (*mgmProto.SyncResponse, error) {
|
||||
cClient := s.connectClient
|
||||
if cClient == nil {
|
||||
return nil, errors.New("connect client is not initialized")
|
||||
}
|
||||
|
||||
return cClient.GetLatestNetworkMap()
|
||||
return cClient.GetLatestSyncResponse()
|
||||
}
|
||||
|
||||
@@ -11,7 +11,7 @@ import (
|
||||
"golang.org/x/exp/maps"
|
||||
|
||||
"github.com/netbirdio/netbird/client/proto"
|
||||
"github.com/netbirdio/netbird/management/domain"
|
||||
"github.com/netbirdio/netbird/shared/management/domain"
|
||||
"github.com/netbirdio/netbird/route"
|
||||
)
|
||||
|
||||
|
||||
+212
-56
@@ -2,6 +2,7 @@ package server
|
||||
|
||||
import (
|
||||
"context"
|
||||
"errors"
|
||||
"fmt"
|
||||
"os"
|
||||
"os/exec"
|
||||
@@ -13,6 +14,7 @@ import (
|
||||
|
||||
"github.com/cenkalti/backoff/v4"
|
||||
"golang.org/x/exp/maps"
|
||||
"golang.zx2c4.com/wireguard/wgctrl/wgtypes"
|
||||
"google.golang.org/protobuf/types/known/durationpb"
|
||||
|
||||
log "github.com/sirupsen/logrus"
|
||||
@@ -24,7 +26,8 @@ import (
|
||||
"github.com/netbirdio/netbird/client/internal/auth"
|
||||
"github.com/netbirdio/netbird/client/internal/profilemanager"
|
||||
"github.com/netbirdio/netbird/client/system"
|
||||
"github.com/netbirdio/netbird/management/domain"
|
||||
mgm "github.com/netbirdio/netbird/shared/management/client"
|
||||
"github.com/netbirdio/netbird/shared/management/domain"
|
||||
|
||||
"github.com/netbirdio/netbird/client/internal"
|
||||
"github.com/netbirdio/netbird/client/internal/peer"
|
||||
@@ -47,6 +50,8 @@ const (
|
||||
errProfilesDisabled = "profiles are disabled, you cannot use this feature without profiles enabled"
|
||||
)
|
||||
|
||||
var ErrServiceNotUp = errors.New("service is not up")
|
||||
|
||||
// Server for service control.
|
||||
type Server struct {
|
||||
rootCtx context.Context
|
||||
@@ -65,11 +70,11 @@ type Server struct {
|
||||
statusRecorder *peer.Status
|
||||
sessionWatcher *internal.SessionWatcher
|
||||
|
||||
lastProbe time.Time
|
||||
persistNetworkMap bool
|
||||
isSessionActive atomic.Bool
|
||||
lastProbe time.Time
|
||||
persistSyncResponse bool
|
||||
isSessionActive atomic.Bool
|
||||
|
||||
profileManager profilemanager.ServiceManager
|
||||
profileManager *profilemanager.ServiceManager
|
||||
profilesDisabled bool
|
||||
}
|
||||
|
||||
@@ -81,14 +86,14 @@ type oauthAuthFlow struct {
|
||||
}
|
||||
|
||||
// New server instance constructor.
|
||||
func New(ctx context.Context, logFile string, profilesDisabled bool) *Server {
|
||||
func New(ctx context.Context, logFile string, configFile string, profilesDisabled bool) *Server {
|
||||
return &Server{
|
||||
rootCtx: ctx,
|
||||
logFile: logFile,
|
||||
persistNetworkMap: true,
|
||||
statusRecorder: peer.NewRecorder(""),
|
||||
profileManager: profilemanager.ServiceManager{},
|
||||
profilesDisabled: profilesDisabled,
|
||||
rootCtx: ctx,
|
||||
logFile: logFile,
|
||||
persistSyncResponse: true,
|
||||
statusRecorder: peer.NewRecorder(""),
|
||||
profileManager: profilemanager.NewServiceManager(configFile),
|
||||
profilesDisabled: profilesDisabled,
|
||||
}
|
||||
}
|
||||
|
||||
@@ -131,13 +136,7 @@ func (s *Server) Start() error {
|
||||
return fmt.Errorf("failed to get active profile state: %w", err)
|
||||
}
|
||||
|
||||
cfgPath, err := activeProf.FilePath()
|
||||
if err != nil {
|
||||
log.Errorf("failed to get active profile file path: %v", err)
|
||||
return fmt.Errorf("failed to get active profile file path: %w", err)
|
||||
}
|
||||
|
||||
config, err := profilemanager.GetConfig(cfgPath)
|
||||
config, err := s.getConfig(activeProf)
|
||||
if err != nil {
|
||||
log.Errorf("failed to get active profile config: %v", err)
|
||||
|
||||
@@ -234,7 +233,7 @@ func (s *Server) connectWithRetryRuns(ctx context.Context, config *profilemanage
|
||||
runOperation := func() error {
|
||||
log.Tracef("running client connection")
|
||||
s.connectClient = internal.NewConnectClient(ctx, config, statusRecorder)
|
||||
s.connectClient.SetNetworkMapPersistence(s.persistNetworkMap)
|
||||
s.connectClient.SetSyncResponsePersistence(s.persistSyncResponse)
|
||||
|
||||
err := s.connectClient.Run(runningChan)
|
||||
if err != nil {
|
||||
@@ -484,13 +483,7 @@ func (s *Server) Login(callerCtx context.Context, msg *proto.LoginRequest) (*pro
|
||||
}
|
||||
s.mutex.Unlock()
|
||||
|
||||
cfgPath, err := activeProf.FilePath()
|
||||
if err != nil {
|
||||
log.Errorf("failed to get active profile file path: %v", err)
|
||||
return nil, fmt.Errorf("failed to get active profile file path: %w", err)
|
||||
}
|
||||
|
||||
config, err := profilemanager.GetConfig(cfgPath)
|
||||
config, err := s.getConfig(activeProf)
|
||||
if err != nil {
|
||||
log.Errorf("failed to get active profile config: %v", err)
|
||||
return nil, fmt.Errorf("failed to get active profile config: %w", err)
|
||||
@@ -701,13 +694,7 @@ func (s *Server) Up(callerCtx context.Context, msg *proto.UpRequest) (*proto.UpR
|
||||
|
||||
log.Infof("active profile: %s for %s", activeProf.Name, activeProf.Username)
|
||||
|
||||
cfgPath, err := activeProf.FilePath()
|
||||
if err != nil {
|
||||
log.Errorf("failed to get active profile file path: %v", err)
|
||||
return nil, fmt.Errorf("failed to get active profile file path: %w", err)
|
||||
}
|
||||
|
||||
config, err := profilemanager.GetConfig(cfgPath)
|
||||
config, err := s.getConfig(activeProf)
|
||||
if err != nil {
|
||||
log.Errorf("failed to get active profile config: %v", err)
|
||||
return nil, fmt.Errorf("failed to get active profile config: %w", err)
|
||||
@@ -789,13 +776,7 @@ func (s *Server) SwitchProfile(callerCtx context.Context, msg *proto.SwitchProfi
|
||||
log.Errorf("failed to get active profile state: %v", err)
|
||||
return nil, fmt.Errorf("failed to get active profile state: %w", err)
|
||||
}
|
||||
cfgPath, err := activeProf.FilePath()
|
||||
if err != nil {
|
||||
log.Errorf("failed to get active profile file path: %v", err)
|
||||
return nil, fmt.Errorf("failed to get active profile file path: %w", err)
|
||||
}
|
||||
|
||||
config, err := profilemanager.GetConfig(cfgPath)
|
||||
config, err := s.getConfig(activeProf)
|
||||
if err != nil {
|
||||
log.Errorf("failed to get default profile config: %v", err)
|
||||
return nil, fmt.Errorf("failed to get default profile config: %w", err)
|
||||
@@ -811,26 +792,201 @@ func (s *Server) Down(ctx context.Context, _ *proto.DownRequest) (*proto.DownRes
|
||||
s.mutex.Lock()
|
||||
defer s.mutex.Unlock()
|
||||
|
||||
s.oauthAuthFlow = oauthAuthFlow{}
|
||||
|
||||
if s.actCancel == nil {
|
||||
return nil, fmt.Errorf("service is not up")
|
||||
}
|
||||
s.actCancel()
|
||||
|
||||
err := s.connectClient.Stop()
|
||||
if err != nil {
|
||||
if err := s.cleanupConnection(); err != nil {
|
||||
log.Errorf("failed to shut down properly: %v", err)
|
||||
return nil, err
|
||||
}
|
||||
s.isSessionActive.Store(false)
|
||||
|
||||
state := internal.CtxGetState(s.rootCtx)
|
||||
state.Set(internal.StatusIdle)
|
||||
|
||||
return &proto.DownResponse{}, nil
|
||||
}
|
||||
|
||||
func (s *Server) cleanupConnection() error {
|
||||
s.oauthAuthFlow = oauthAuthFlow{}
|
||||
|
||||
if s.actCancel == nil {
|
||||
return ErrServiceNotUp
|
||||
}
|
||||
s.actCancel()
|
||||
|
||||
if s.connectClient == nil {
|
||||
return nil
|
||||
}
|
||||
|
||||
if err := s.connectClient.Stop(); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
s.connectClient = nil
|
||||
s.isSessionActive.Store(false)
|
||||
|
||||
log.Infof("service is down")
|
||||
|
||||
return &proto.DownResponse{}, nil
|
||||
return nil
|
||||
}
|
||||
|
||||
func (s *Server) Logout(ctx context.Context, msg *proto.LogoutRequest) (*proto.LogoutResponse, error) {
|
||||
s.mutex.Lock()
|
||||
defer s.mutex.Unlock()
|
||||
|
||||
if msg.ProfileName != nil && *msg.ProfileName != "" {
|
||||
return s.handleProfileLogout(ctx, msg)
|
||||
}
|
||||
|
||||
return s.handleActiveProfileLogout(ctx)
|
||||
}
|
||||
|
||||
func (s *Server) handleProfileLogout(ctx context.Context, msg *proto.LogoutRequest) (*proto.LogoutResponse, error) {
|
||||
if err := s.validateProfileOperation(*msg.ProfileName, true); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
if msg.Username == nil || *msg.Username == "" {
|
||||
return nil, gstatus.Errorf(codes.InvalidArgument, "username must be provided when profile name is specified")
|
||||
}
|
||||
username := *msg.Username
|
||||
|
||||
if err := s.logoutFromProfile(ctx, *msg.ProfileName, username); err != nil {
|
||||
log.Errorf("failed to logout from profile %s: %v", *msg.ProfileName, err)
|
||||
return nil, gstatus.Errorf(codes.Internal, "logout: %v", err)
|
||||
}
|
||||
|
||||
activeProf, _ := s.profileManager.GetActiveProfileState()
|
||||
if activeProf != nil && activeProf.Name == *msg.ProfileName {
|
||||
if err := s.cleanupConnection(); err != nil && !errors.Is(err, ErrServiceNotUp) {
|
||||
log.Errorf("failed to cleanup connection: %v", err)
|
||||
}
|
||||
state := internal.CtxGetState(s.rootCtx)
|
||||
state.Set(internal.StatusNeedsLogin)
|
||||
}
|
||||
|
||||
return &proto.LogoutResponse{}, nil
|
||||
}
|
||||
|
||||
func (s *Server) handleActiveProfileLogout(ctx context.Context) (*proto.LogoutResponse, error) {
|
||||
if s.config == nil {
|
||||
activeProf, err := s.profileManager.GetActiveProfileState()
|
||||
if err != nil {
|
||||
return nil, gstatus.Errorf(codes.FailedPrecondition, "failed to get active profile state: %v", err)
|
||||
}
|
||||
|
||||
config, err := s.getConfig(activeProf)
|
||||
if err != nil {
|
||||
return nil, gstatus.Errorf(codes.FailedPrecondition, "not logged in")
|
||||
}
|
||||
s.config = config
|
||||
}
|
||||
|
||||
if err := s.sendLogoutRequest(ctx); err != nil {
|
||||
log.Errorf("failed to send logout request: %v", err)
|
||||
return nil, err
|
||||
}
|
||||
|
||||
if err := s.cleanupConnection(); err != nil && !errors.Is(err, ErrServiceNotUp) {
|
||||
log.Errorf("failed to cleanup connection: %v", err)
|
||||
return nil, err
|
||||
}
|
||||
|
||||
state := internal.CtxGetState(s.rootCtx)
|
||||
state.Set(internal.StatusNeedsLogin)
|
||||
|
||||
return &proto.LogoutResponse{}, nil
|
||||
}
|
||||
|
||||
// getConfig loads the config from the active profile
|
||||
func (s *Server) getConfig(activeProf *profilemanager.ActiveProfileState) (*profilemanager.Config, error) {
|
||||
cfgPath, err := activeProf.FilePath()
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("failed to get active profile file path: %w", err)
|
||||
}
|
||||
|
||||
config, err := profilemanager.GetConfig(cfgPath)
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("failed to get config: %w", err)
|
||||
}
|
||||
|
||||
return config, nil
|
||||
}
|
||||
|
||||
func (s *Server) canRemoveProfile(profileName string) error {
|
||||
if profileName == profilemanager.DefaultProfileName {
|
||||
return fmt.Errorf("remove profile with reserved name: %s", profilemanager.DefaultProfileName)
|
||||
}
|
||||
|
||||
activeProf, err := s.profileManager.GetActiveProfileState()
|
||||
if err == nil && activeProf.Name == profileName {
|
||||
return fmt.Errorf("remove active profile: %s", profileName)
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func (s *Server) validateProfileOperation(profileName string, allowActiveProfile bool) error {
|
||||
if s.checkProfilesDisabled() {
|
||||
return gstatus.Errorf(codes.Unavailable, errProfilesDisabled)
|
||||
}
|
||||
|
||||
if profileName == "" {
|
||||
return gstatus.Errorf(codes.InvalidArgument, "profile name must be provided")
|
||||
}
|
||||
|
||||
if !allowActiveProfile {
|
||||
if err := s.canRemoveProfile(profileName); err != nil {
|
||||
return gstatus.Errorf(codes.InvalidArgument, "%v", err)
|
||||
}
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
// logoutFromProfile logs out from a specific profile by loading its config and sending logout request
|
||||
func (s *Server) logoutFromProfile(ctx context.Context, profileName, username string) error {
|
||||
activeProf, err := s.profileManager.GetActiveProfileState()
|
||||
if err == nil && activeProf.Name == profileName && s.connectClient != nil {
|
||||
return s.sendLogoutRequest(ctx)
|
||||
}
|
||||
|
||||
profileState := &profilemanager.ActiveProfileState{
|
||||
Name: profileName,
|
||||
Username: username,
|
||||
}
|
||||
profilePath, err := profileState.FilePath()
|
||||
if err != nil {
|
||||
return fmt.Errorf("get profile path: %w", err)
|
||||
}
|
||||
|
||||
config, err := profilemanager.GetConfig(profilePath)
|
||||
if err != nil {
|
||||
return fmt.Errorf("profile '%s' not found", profileName)
|
||||
}
|
||||
|
||||
return s.sendLogoutRequestWithConfig(ctx, config)
|
||||
}
|
||||
|
||||
func (s *Server) sendLogoutRequest(ctx context.Context) error {
|
||||
return s.sendLogoutRequestWithConfig(ctx, s.config)
|
||||
}
|
||||
|
||||
func (s *Server) sendLogoutRequestWithConfig(ctx context.Context, config *profilemanager.Config) error {
|
||||
key, err := wgtypes.ParseKey(config.PrivateKey)
|
||||
if err != nil {
|
||||
return fmt.Errorf("parse private key: %w", err)
|
||||
}
|
||||
|
||||
mgmTlsEnabled := config.ManagementURL.Scheme == "https"
|
||||
mgmClient, err := mgm.NewClient(ctx, config.ManagementURL.Host, key, mgmTlsEnabled)
|
||||
if err != nil {
|
||||
return fmt.Errorf("connect to management server: %w", err)
|
||||
}
|
||||
defer func() {
|
||||
if err := mgmClient.Close(); err != nil {
|
||||
log.Errorf("close management client: %v", err)
|
||||
}
|
||||
}()
|
||||
|
||||
return mgmClient.Logout()
|
||||
}
|
||||
|
||||
// Status returns the daemon status
|
||||
@@ -1107,12 +1263,12 @@ func (s *Server) RemoveProfile(ctx context.Context, msg *proto.RemoveProfileRequ
|
||||
s.mutex.Lock()
|
||||
defer s.mutex.Unlock()
|
||||
|
||||
if s.checkProfilesDisabled() {
|
||||
return nil, gstatus.Errorf(codes.Unavailable, errProfilesDisabled)
|
||||
if err := s.validateProfileOperation(msg.ProfileName, false); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
if msg.ProfileName == "" {
|
||||
return nil, gstatus.Errorf(codes.InvalidArgument, "profile name must be provided")
|
||||
if err := s.logoutFromProfile(ctx, msg.ProfileName, msg.Username); err != nil {
|
||||
log.Warnf("failed to logout from profile %s before removal: %v", msg.ProfileName, err)
|
||||
}
|
||||
|
||||
if err := s.profileManager.RemoveProfile(msg.ProfileName, msg.Username); err != nil {
|
||||
|
||||
@@ -24,7 +24,7 @@ import (
|
||||
"github.com/netbirdio/netbird/client/internal/peer"
|
||||
"github.com/netbirdio/netbird/client/internal/profilemanager"
|
||||
daemonProto "github.com/netbirdio/netbird/client/proto"
|
||||
mgmtProto "github.com/netbirdio/netbird/management/proto"
|
||||
mgmtProto "github.com/netbirdio/netbird/shared/management/proto"
|
||||
"github.com/netbirdio/netbird/management/server"
|
||||
"github.com/netbirdio/netbird/management/server/activity"
|
||||
"github.com/netbirdio/netbird/management/server/integrations/port_forwarding"
|
||||
@@ -33,7 +33,7 @@ import (
|
||||
"github.com/netbirdio/netbird/management/server/store"
|
||||
"github.com/netbirdio/netbird/management/server/telemetry"
|
||||
"github.com/netbirdio/netbird/management/server/types"
|
||||
"github.com/netbirdio/netbird/signal/proto"
|
||||
"github.com/netbirdio/netbird/shared/signal/proto"
|
||||
signalServer "github.com/netbirdio/netbird/signal/server"
|
||||
)
|
||||
|
||||
@@ -94,7 +94,7 @@ func TestConnectWithRetryRuns(t *testing.T) {
|
||||
t.Fatalf("failed to set active profile state: %v", err)
|
||||
}
|
||||
|
||||
s := New(ctx, "debug", false)
|
||||
s := New(ctx, "debug", "", false)
|
||||
|
||||
s.config = config
|
||||
|
||||
@@ -151,7 +151,7 @@ func TestServer_Up(t *testing.T) {
|
||||
t.Fatalf("failed to set active profile state: %v", err)
|
||||
}
|
||||
|
||||
s := New(ctx, "console", false)
|
||||
s := New(ctx, "console", "", false)
|
||||
|
||||
err = s.Start()
|
||||
require.NoError(t, err)
|
||||
@@ -227,7 +227,7 @@ func TestServer_SubcribeEvents(t *testing.T) {
|
||||
t.Fatalf("failed to set active profile state: %v", err)
|
||||
}
|
||||
|
||||
s := New(ctx, "console", false)
|
||||
s := New(ctx, "console", "", false)
|
||||
|
||||
err = s.Start()
|
||||
require.NoError(t, err)
|
||||
|
||||
@@ -16,7 +16,7 @@ import (
|
||||
"github.com/netbirdio/netbird/client/anonymize"
|
||||
"github.com/netbirdio/netbird/client/internal/peer"
|
||||
"github.com/netbirdio/netbird/client/proto"
|
||||
"github.com/netbirdio/netbird/management/domain"
|
||||
"github.com/netbirdio/netbird/shared/management/domain"
|
||||
"github.com/netbirdio/netbird/version"
|
||||
)
|
||||
|
||||
|
||||
@@ -8,7 +8,7 @@ import (
|
||||
|
||||
"google.golang.org/grpc/metadata"
|
||||
|
||||
"github.com/netbirdio/netbird/management/proto"
|
||||
"github.com/netbirdio/netbird/shared/management/proto"
|
||||
)
|
||||
|
||||
// DeviceNameCtxKey context key for device name
|
||||
|
||||
@@ -831,6 +831,7 @@ func (s *serviceClient) onTrayReady() {
|
||||
s.mLazyConnEnabled = s.mSettings.AddSubMenuItemCheckbox("Enable Lazy Connections", lazyConnMenuDescr, false)
|
||||
s.mBlockInbound = s.mSettings.AddSubMenuItemCheckbox("Block Inbound Connections", blockInboundMenuDescr, false)
|
||||
s.mNotifications = s.mSettings.AddSubMenuItemCheckbox("Notifications", notificationsMenuDescr, false)
|
||||
s.mSettings.AddSeparator()
|
||||
s.mAdvancedSettings = s.mSettings.AddSubMenuItem("Advanced Settings", advancedSettingsMenuDescr)
|
||||
s.mCreateDebugBundle = s.mSettings.AddSubMenuItem("Create Debug Bundle", debugBundleMenuDescr)
|
||||
s.loadSettings()
|
||||
|
||||
+3
-3
@@ -395,12 +395,12 @@ func (s *serviceClient) configureServiceForDebug(
|
||||
time.Sleep(time.Second)
|
||||
|
||||
if enablePersistence {
|
||||
if _, err := conn.SetNetworkMapPersistence(s.ctx, &proto.SetNetworkMapPersistenceRequest{
|
||||
if _, err := conn.SetSyncResponsePersistence(s.ctx, &proto.SetSyncResponsePersistenceRequest{
|
||||
Enabled: true,
|
||||
}); err != nil {
|
||||
return fmt.Errorf("enable network map persistence: %v", err)
|
||||
return fmt.Errorf("enable sync response persistence: %v", err)
|
||||
}
|
||||
log.Info("Network map persistence enabled for debug")
|
||||
log.Info("Sync response persistence enabled for debug")
|
||||
}
|
||||
|
||||
if _, err := conn.Up(s.ctx, &proto.UpRequest{}); err != nil {
|
||||
|
||||
@@ -13,6 +13,7 @@ import (
|
||||
"fyne.io/systray"
|
||||
log "github.com/sirupsen/logrus"
|
||||
|
||||
"github.com/netbirdio/netbird/client/proto"
|
||||
"github.com/netbirdio/netbird/version"
|
||||
)
|
||||
|
||||
@@ -231,3 +232,19 @@ func (h *eventHandler) runSelfCommand(ctx context.Context, command, arg string)
|
||||
|
||||
log.Printf("command '%s %s' completed successfully", command, arg)
|
||||
}
|
||||
|
||||
func (h *eventHandler) logout(ctx context.Context) error {
|
||||
client, err := h.client.getSrvClient(defaultFailTimeout)
|
||||
if err != nil {
|
||||
return fmt.Errorf("failed to get service client: %w", err)
|
||||
}
|
||||
|
||||
_, err = client.Logout(ctx, &proto.LogoutRequest{})
|
||||
if err != nil {
|
||||
return fmt.Errorf("logout failed: %w", err)
|
||||
}
|
||||
|
||||
h.client.getSrvConfig()
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
+95
-13
@@ -40,12 +40,13 @@ func (s *serviceClient) showProfilesUI() {
|
||||
list := widget.NewList(
|
||||
func() int { return len(profiles) },
|
||||
func() fyne.CanvasObject {
|
||||
// Each item: Selected indicator, Name, spacer, Select & Remove buttons
|
||||
// Each item: Selected indicator, Name, spacer, Select, Logout & Remove buttons
|
||||
return container.NewHBox(
|
||||
widget.NewLabel(""), // indicator
|
||||
widget.NewLabel(""), // profile name
|
||||
layout.NewSpacer(),
|
||||
widget.NewButton("Select", nil),
|
||||
widget.NewButton("Logout", nil),
|
||||
widget.NewButton("Remove", nil),
|
||||
)
|
||||
},
|
||||
@@ -55,7 +56,8 @@ func (s *serviceClient) showProfilesUI() {
|
||||
indicator := row.Objects[0].(*widget.Label)
|
||||
nameLabel := row.Objects[1].(*widget.Label)
|
||||
selectBtn := row.Objects[3].(*widget.Button)
|
||||
removeBtn := row.Objects[4].(*widget.Button)
|
||||
logoutBtn := row.Objects[4].(*widget.Button)
|
||||
removeBtn := row.Objects[5].(*widget.Button)
|
||||
|
||||
profile := profiles[i]
|
||||
// Show a checkmark if selected
|
||||
@@ -105,7 +107,7 @@ func (s *serviceClient) showProfilesUI() {
|
||||
return
|
||||
}
|
||||
|
||||
status, err := conn.Status(context.Background(), &proto.StatusRequest{})
|
||||
status, err := conn.Status(s.ctx, &proto.StatusRequest{})
|
||||
if err != nil {
|
||||
log.Errorf("failed to get status after switching profile: %v", err)
|
||||
return
|
||||
@@ -125,6 +127,12 @@ func (s *serviceClient) showProfilesUI() {
|
||||
)
|
||||
}
|
||||
|
||||
logoutBtn.Show()
|
||||
logoutBtn.SetText("Logout")
|
||||
logoutBtn.OnTapped = func() {
|
||||
s.handleProfileLogout(profile.Name, refresh)
|
||||
}
|
||||
|
||||
// Remove profile
|
||||
removeBtn.SetText("Remove")
|
||||
removeBtn.OnTapped = func() {
|
||||
@@ -135,7 +143,7 @@ func (s *serviceClient) showProfilesUI() {
|
||||
if !confirm {
|
||||
return
|
||||
}
|
||||
// remove
|
||||
|
||||
err = s.removeProfile(profile.Name)
|
||||
if err != nil {
|
||||
log.Errorf("failed to remove profile: %v", err)
|
||||
@@ -230,7 +238,7 @@ func (s *serviceClient) addProfile(profileName string) error {
|
||||
return fmt.Errorf("get current user: %w", err)
|
||||
}
|
||||
|
||||
_, err = conn.AddProfile(context.Background(), &proto.AddProfileRequest{
|
||||
_, err = conn.AddProfile(s.ctx, &proto.AddProfileRequest{
|
||||
ProfileName: profileName,
|
||||
Username: currUser.Username,
|
||||
})
|
||||
@@ -253,7 +261,7 @@ func (s *serviceClient) switchProfile(profileName string) error {
|
||||
return fmt.Errorf("get current user: %w", err)
|
||||
}
|
||||
|
||||
if _, err := conn.SwitchProfile(context.Background(), &proto.SwitchProfileRequest{
|
||||
if _, err := conn.SwitchProfile(s.ctx, &proto.SwitchProfileRequest{
|
||||
ProfileName: &profileName,
|
||||
Username: &currUser.Username,
|
||||
}); err != nil {
|
||||
@@ -279,7 +287,7 @@ func (s *serviceClient) removeProfile(profileName string) error {
|
||||
return fmt.Errorf("get current user: %w", err)
|
||||
}
|
||||
|
||||
_, err = conn.RemoveProfile(context.Background(), &proto.RemoveProfileRequest{
|
||||
_, err = conn.RemoveProfile(s.ctx, &proto.RemoveProfileRequest{
|
||||
ProfileName: profileName,
|
||||
Username: currUser.Username,
|
||||
})
|
||||
@@ -305,7 +313,7 @@ func (s *serviceClient) getProfiles() ([]Profile, error) {
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("get current user: %w", err)
|
||||
}
|
||||
profilesResp, err := conn.ListProfiles(context.Background(), &proto.ListProfilesRequest{
|
||||
profilesResp, err := conn.ListProfiles(s.ctx, &proto.ListProfilesRequest{
|
||||
Username: currUser.Username,
|
||||
})
|
||||
if err != nil {
|
||||
@@ -324,6 +332,52 @@ func (s *serviceClient) getProfiles() ([]Profile, error) {
|
||||
return profiles, nil
|
||||
}
|
||||
|
||||
func (s *serviceClient) handleProfileLogout(profileName string, refreshCallback func()) {
|
||||
dialog.ShowConfirm(
|
||||
"Logout",
|
||||
fmt.Sprintf("Are you sure you want to logout from '%s'?", profileName),
|
||||
func(confirm bool) {
|
||||
if !confirm {
|
||||
return
|
||||
}
|
||||
|
||||
conn, err := s.getSrvClient(defaultFailTimeout)
|
||||
if err != nil {
|
||||
log.Errorf("failed to get service client: %v", err)
|
||||
dialog.ShowError(fmt.Errorf("failed to connect to service"), s.wProfiles)
|
||||
return
|
||||
}
|
||||
|
||||
currUser, err := user.Current()
|
||||
if err != nil {
|
||||
log.Errorf("failed to get current user: %v", err)
|
||||
dialog.ShowError(fmt.Errorf("failed to get current user"), s.wProfiles)
|
||||
return
|
||||
}
|
||||
|
||||
username := currUser.Username
|
||||
_, err = conn.Logout(s.ctx, &proto.LogoutRequest{
|
||||
ProfileName: &profileName,
|
||||
Username: &username,
|
||||
})
|
||||
if err != nil {
|
||||
log.Errorf("logout failed: %v", err)
|
||||
dialog.ShowError(fmt.Errorf("logout failed"), s.wProfiles)
|
||||
return
|
||||
}
|
||||
|
||||
dialog.ShowInformation(
|
||||
"Logged Out",
|
||||
fmt.Sprintf("Successfully logged out from '%s'", profileName),
|
||||
s.wProfiles,
|
||||
)
|
||||
|
||||
refreshCallback()
|
||||
},
|
||||
s.wProfiles,
|
||||
)
|
||||
}
|
||||
|
||||
type subItem struct {
|
||||
*systray.MenuItem
|
||||
ctx context.Context
|
||||
@@ -339,6 +393,7 @@ type profileMenu struct {
|
||||
emailMenuItem *systray.MenuItem
|
||||
profileSubItems []*subItem
|
||||
manageProfilesSubItem *subItem
|
||||
logoutSubItem *subItem
|
||||
profilesState []Profile
|
||||
downClickCallback func() error
|
||||
upClickCallback func() error
|
||||
@@ -533,12 +588,11 @@ func (p *profileMenu) refresh() {
|
||||
for {
|
||||
select {
|
||||
case <-ctx.Done():
|
||||
return // context cancelled
|
||||
return
|
||||
case _, ok := <-manageItem.ClickedCh:
|
||||
if !ok {
|
||||
return // channel closed
|
||||
return
|
||||
}
|
||||
// Handle manage profiles click
|
||||
p.eventHandler.runSelfCommand(p.ctx, "profiles", "true")
|
||||
p.refresh()
|
||||
p.loadSettingsCallback()
|
||||
@@ -546,6 +600,30 @@ func (p *profileMenu) refresh() {
|
||||
}
|
||||
}()
|
||||
|
||||
// Add Logout menu item
|
||||
ctx2, cancel2 := context.WithCancel(context.Background())
|
||||
logoutItem := p.profileMenuItem.AddSubMenuItem("Logout", "")
|
||||
p.logoutSubItem = &subItem{logoutItem, ctx2, cancel2}
|
||||
|
||||
go func() {
|
||||
for {
|
||||
select {
|
||||
case <-ctx2.Done():
|
||||
return
|
||||
case _, ok := <-logoutItem.ClickedCh:
|
||||
if !ok {
|
||||
return
|
||||
}
|
||||
if err := p.eventHandler.logout(p.ctx); err != nil {
|
||||
log.Errorf("logout failed: %v", err)
|
||||
p.app.SendNotification(fyne.NewNotification("Error", "Failed to logout"))
|
||||
} else {
|
||||
p.app.SendNotification(fyne.NewNotification("Success", "Logged out successfully"))
|
||||
}
|
||||
}
|
||||
}
|
||||
}()
|
||||
|
||||
if activeProf.ProfileName == "default" || activeProf.Username == currUser.Username {
|
||||
p.profileMenuItem.SetTitle(activeProf.ProfileName)
|
||||
} else {
|
||||
@@ -556,7 +634,6 @@ func (p *profileMenu) refresh() {
|
||||
}
|
||||
|
||||
func (p *profileMenu) clear(profiles []Profile) {
|
||||
// Clear existing profile items
|
||||
for _, item := range p.profileSubItems {
|
||||
item.Remove()
|
||||
item.cancel()
|
||||
@@ -565,11 +642,16 @@ func (p *profileMenu) clear(profiles []Profile) {
|
||||
p.profilesState = profiles
|
||||
|
||||
if p.manageProfilesSubItem != nil {
|
||||
// Remove the manage profiles item if it exists
|
||||
p.manageProfilesSubItem.Remove()
|
||||
p.manageProfilesSubItem.cancel()
|
||||
p.manageProfilesSubItem = nil
|
||||
}
|
||||
|
||||
if p.logoutSubItem != nil {
|
||||
p.logoutSubItem.Remove()
|
||||
p.logoutSubItem.cancel()
|
||||
p.logoutSubItem = nil
|
||||
}
|
||||
}
|
||||
|
||||
func (p *profileMenu) updateMenu() {
|
||||
|
||||
Reference in New Issue
Block a user