Skip to content

Commit 3492013

Browse files
committed
Resolve comments
1 parent 8954644 commit 3492013

File tree

4 files changed

+78
-40
lines changed

4 files changed

+78
-40
lines changed

client/internal/engine.go

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -306,6 +306,10 @@ func (e *Engine) Stop() error {
306306
e.srWatcher.Close()
307307
}
308308

309+
if e.updateManager != nil {
310+
e.updateManager.Stop()
311+
}
312+
309313
e.statusRecorder.ReplaceOfflinePeers([]peer.State{})
310314
e.statusRecorder.UpdateDNSStates([]peer.NSGroupState{})
311315
e.statusRecorder.UpdateRelayStates([]relay.ProbeResult{})

client/internal/updatemanager/manager.go

Lines changed: 41 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,8 @@
11
package updatemanager
22

33
import (
4+
"context"
5+
"fmt"
46
"github.com/netbirdio/netbird/client/internal/peer"
57
cProto "github.com/netbirdio/netbird/client/proto"
68
"io"
@@ -16,7 +18,14 @@ import (
1618
"github.com/netbirdio/netbird/version"
1719
)
1820

21+
const (
22+
latestVersion = "latest"
23+
disableAutoUpdate = "disabled"
24+
)
25+
1926
type UpdateManager struct {
27+
ctx context.Context
28+
cancel context.CancelFunc
2029
version string
2130
update *version.Update
2231
lastTrigger time.Time
@@ -25,33 +34,41 @@ type UpdateManager struct {
2534

2635
func NewUpdateManager(statusRecorder *peer.Status) *UpdateManager {
2736
update := version.NewUpdate("nb/client")
37+
ctx, cancel := context.WithCancel(context.Background())
2838
manager := &UpdateManager{
2939
update: update,
3040
lastTrigger: time.Now().Add(-10 * time.Minute),
3141
statusRecorder: statusRecorder,
42+
ctx: ctx,
43+
cancel: cancel,
44+
version: disableAutoUpdate,
3245
}
33-
manager.version = "disabled"
3446
update.SetDaemonVersion(version.NetbirdVersion())
3547
update.SetOnUpdateListener(manager.CheckForUpdates)
3648
return manager
3749
}
3850

3951
func (u *UpdateManager) SetVersion(v string) {
4052
if u.version != v {
41-
log.Errorf("############## Version set to %s", v)
53+
log.Tracef("Auto-update verstion set to %s", v)
4254
u.version = v
4355
go u.CheckForUpdates()
4456
}
4557
}
4658

59+
func (u *UpdateManager) Stop() {
60+
u.update.StopWatch()
61+
u.cancel()
62+
}
63+
4764
func (u *UpdateManager) CheckForUpdates() {
48-
if u.version == "disabled" {
65+
if u.version == disableAutoUpdate {
4966
log.Trace("Skipped checking for updates, auto-update is disabled")
5067
return
5168
}
5269
currentVersionString := version.NetbirdVersion()
5370
updateVersionString := u.version
54-
if updateVersionString == "latest" || updateVersionString == "" {
71+
if updateVersionString == latestVersion || updateVersionString == "" {
5572
if u.update.LatestAvailable == nil {
5673
log.Tracef("Latest version not fetched yet")
5774
return
@@ -89,27 +106,39 @@ func (u *UpdateManager) CheckForUpdates() {
89106
}
90107
}
91108

92-
func downloadFileToTemporaryDir(fileURL string) (string, error) { //nolint:unused
109+
func downloadFileToTemporaryDir(ctx context.Context, fileURL string) (string, error) { //nolint:unused
93110
tempDir, err := os.MkdirTemp("", "netbird-installer-*")
94111
if err != nil {
95-
return "", err
112+
return "", fmt.Errorf("error creating temporary directory: %w", err)
96113
}
97114
fileNameParts := strings.Split(fileURL, "/")
98115
out, err := os.Create(filepath.Join(tempDir, fileNameParts[len(fileNameParts)-1]))
99116
if err != nil {
100-
return "", err
117+
return "", fmt.Errorf("error creating temporary file: %w", err)
101118
}
102-
defer out.Close()
119+
defer func() {
120+
if err := out.Close(); err != nil {
121+
log.Errorf("Error closing temporary file: %v", err)
122+
}
123+
}()
103124

104-
resp, err := http.Get(fileURL)
125+
req, err := http.NewRequestWithContext(ctx, "GET", fileURL, nil)
126+
if err != nil {
127+
return "", fmt.Errorf("error creating file download request: %w", err)
128+
}
129+
resp, err := http.DefaultClient.Do(req)
105130
if err != nil {
106-
return "", err
131+
return "", fmt.Errorf("error downloading file: %w", err)
107132
}
108-
defer resp.Body.Close()
133+
defer func() {
134+
if err := resp.Body.Close(); err != nil {
135+
log.Errorf("Error closing response body: %v", err)
136+
}
137+
}()
109138

110139
_, err = io.Copy(out, resp.Body)
111140
if err != nil {
112-
return "", err
141+
return "", fmt.Errorf("error downloading file: %w", err)
113142
}
114143

115144
log.Tracef("Downloaded update file to %s", out.Name())

client/internal/updatemanager/update_darwin.go

Lines changed: 31 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -4,9 +4,9 @@ package updatemanager
44

55
import (
66
"fmt"
7-
log "github.com/sirupsen/logrus"
87
"os"
98
"os/exec"
9+
"os/user"
1010
"runtime"
1111
"strings"
1212
"syscall"
@@ -27,9 +27,9 @@ func (u *UpdateManager) triggerUpdate(targetVersion string) error {
2727
// Installed using pkg file
2828
url := strings.ReplaceAll(pkgDownloadURL, "%version", targetVersion)
2929
url = strings.ReplaceAll(url, "%arch", runtime.GOARCH)
30-
path, err := downloadFileToTemporaryDir(url)
30+
path, err := downloadFileToTemporaryDir(u.ctx, url)
3131
if err != nil {
32-
return err
32+
return fmt.Errorf("error downloading update file: %w", err)
3333
}
3434

3535
volume := "/"
@@ -44,7 +44,7 @@ func (u *UpdateManager) triggerUpdate(targetVersion string) error {
4444

4545
err = cmd.Start()
4646
if err != nil {
47-
return err
47+
return fmt.Errorf("error running pkg file: %w", err)
4848
}
4949
err = cmd.Process.Release()
5050

@@ -56,43 +56,42 @@ func (u *UpdateManager) updateHomeBrew() error {
5656
// To find out which user installed NetBird using HomeBrew we can check the owner of our brew tap directory
5757
fileInfo, err := os.Stat("/opt/homebrew/Library/Taps/netbirdio/homebrew-tap/")
5858
if err != nil {
59-
return err
59+
return fmt.Errorf("error getting homebrew installation path info: %w", err)
6060
}
6161

6262
fileSysInfo, ok := fileInfo.Sys().(*syscall.Stat_t)
6363
if !ok {
64-
return fmt.Errorf("Error checking file owner, sysInfo type is %T not *syscall.Stat_t", fileInfo.Sys())
64+
return fmt.Errorf("error checking file owner, sysInfo type is %T not *syscall.Stat_t", fileInfo.Sys())
6565
}
6666

67-
// Get user name from UID
68-
cmd := exec.Command("id", "-nu", fmt.Sprintf("%d", fileSysInfo.Uid))
69-
out, err := cmd.CombinedOutput()
67+
// Get username from UID
68+
installer, err := user.LookupId(fmt.Sprintf("%d", fileSysInfo.Uid))
7069
if err != nil {
71-
return err
70+
return fmt.Errorf("error looking up brew installer user: %w", err)
7271
}
73-
userName := strings.TrimSpace(string(out))
74-
72+
userName := installer.Name
7573
// Get user HOME, required for brew to run correctly
7674
// https://github.com/Homebrew/brew/issues/15833
77-
cmd = exec.Command("sudo", "-u", userName, "sh", "-c", "echo $HOME")
78-
out, err = cmd.CombinedOutput()
79-
if err != nil {
80-
return err
81-
}
82-
83-
homeDir := strings.TrimSpace(string(out))
75+
homeDir := installer.HomeDir
8476
// Homebrew does not support installing specific versions
8577
// Thus it will always update to latest and ignore targetVersion
86-
cmd = exec.Command("sudo", "-u", userName, "/opt/homebrew/bin/brew", "upgrade", "netbirdio/tap/netbird")
78+
upgradeArgs := []string{"-u", userName, "/opt/homebrew/bin/brew", "upgrade", "netbirdio/tap/netbird"}
79+
// Check if netbird-ui is installed
80+
cmd := exec.Command("brew", "info", "--json", "netbirdio/tap/netbird-ui")
81+
err = cmd.Run()
82+
if err == nil {
83+
// netbird-ui is installed
84+
upgradeArgs = append(upgradeArgs, "netbirdio/tap/netbird-ui")
85+
}
86+
cmd = exec.Command("sudo", upgradeArgs...)
8787
cmd.Env = append(cmd.Env, "HOME="+homeDir)
8888

8989
// Homebrew upgrade doesn't restart the client on its own
9090
// So we have to wait for it to finish running and ensure it's done
9191
// And then basically restart the netbird service
92-
out, err = cmd.CombinedOutput()
92+
err = cmd.Run()
9393
if err != nil {
94-
log.Errorf("Error running brew upgrade, output: %v", string(out))
95-
return err
94+
return fmt.Errorf("error running brew upgrade: %w", err)
9695
}
9796

9897
currentPID := os.Getpid()
@@ -101,9 +100,15 @@ func (u *UpdateManager) updateHomeBrew() error {
101100
// This is a workaround since attempting to restart using launchctl will kill the service and die before starting
102101
// the service again as it's a child process
103102
// using SigTerm should ensure a clean shutdown
104-
cmd = exec.Command("kill", "-15", fmt.Sprintf("%d", currentPID))
105-
err = cmd.Run()
103+
process, err := os.FindProcess(currentPID)
104+
if err != nil {
105+
return fmt.Errorf("error finding current process: %w", err)
106+
}
107+
err = process.Signal(syscall.SIGTERM)
108+
if err != nil {
109+
return fmt.Errorf("error sending SIGTERM to current process: %w", err)
110+
}
106111
// We're dying now, which should restart us
107112

108-
return err
113+
return nil
109114
}

client/internal/updatemanager/update_windows.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,7 @@ func (u *UpdateManager) triggerUpdate(targetVersion string) error {
2020
k, err := registry.OpenKey(registry.LOCAL_MACHINE, `SOFTWARE\Microsoft\Windows\CurrentVersion\App Paths\Netbird`, registry.QUERY_VALUE)
2121
if err != nil && strings.Contains(err.Error(), "system cannot find the file specified") {
2222
// Installed using MSI installer
23-
path, err := downloadFileToTemporaryDir(strings.ReplaceAll(msiDownloadURL, "%s", targetVersion))
23+
path, err := downloadFileToTemporaryDir(u.ctx, strings.ReplaceAll(msiDownloadURL, "%s", targetVersion))
2424
if err != nil {
2525
return err
2626
}
@@ -36,7 +36,7 @@ func (u *UpdateManager) triggerUpdate(targetVersion string) error {
3636
}
3737

3838
// Installed using EXE installer
39-
path, err := downloadFileToTemporaryDir(strings.ReplaceAll(exeDownloadURL, "%s", targetVersion))
39+
path, err := downloadFileToTemporaryDir(u.ctx, strings.ReplaceAll(exeDownloadURL, "%s", targetVersion))
4040
if err != nil {
4141
return err
4242
}

0 commit comments

Comments
 (0)