From 790484bda2fd1c559b7fdc2bea619c0bc1180336 Mon Sep 17 00:00:00 2001 From: Hakan Sariman Date: Sun, 22 Jun 2025 11:17:20 +0300 Subject: [PATCH] feat: integrate profile manager with event handling for improved profile selection --- client/ui/client_ui.go | 4 +- client/ui/profile.go | 92 ++++++++++++++++++++++++++++++++++++------ 2 files changed, 82 insertions(+), 14 deletions(-) diff --git a/client/ui/client_ui.go b/client/ui/client_ui.go index 055a38995..0e5baddb2 100644 --- a/client/ui/client_ui.go +++ b/client/ui/client_ui.go @@ -332,6 +332,7 @@ func newServiceClient(args *newServiceClientArgs) *serviceClient { } s.eventHandler = newEventHandler(s) + s.profileManager = profilemanager.NewProfileManager() s.setNewIcons() switch { @@ -722,10 +723,9 @@ func (s *serviceClient) onTrayReady() { s.mStatus.SetIcon(s.icDisconnectedDot) s.mStatus.Disable() - s.profileManager = profilemanager.NewProfileManager() profileMenuItem := systray.AddMenuItem("", "") emailMenuItem := systray.AddMenuItem("", "") - s.mProfile = newProfileMenu(s.profileManager, profileMenuItem, emailMenuItem) + s.mProfile = newProfileMenu(s.profileManager, *s.eventHandler, profileMenuItem, emailMenuItem) systray.AddSeparator() s.mUp = systray.AddMenuItem("Connect", "Connect") diff --git a/client/ui/profile.go b/client/ui/profile.go index 179cc8f77..98e454a65 100644 --- a/client/ui/profile.go +++ b/client/ui/profile.go @@ -1,6 +1,7 @@ package main import ( + "context" "errors" "fmt" @@ -245,21 +246,30 @@ func (s *serviceClient) getProfiles() ([]profilemanager.Profile, error) { return prof, nil } -type profileMenu struct { - profileManager *profilemanager.ProfileManager - profileMenuItem *systray.MenuItem - emailMenuItem *systray.MenuItem - profileItems []*systray.MenuItem - manageProfilesItem *systray.MenuItem +type subItem struct { + *systray.MenuItem + ctx context.Context + cancel context.CancelFunc } -func newProfileMenu(profileManager *profilemanager.ProfileManager, profileMenuItem, emailMenuItem *systray.MenuItem) *profileMenu { +type profileMenu struct { + profileManager *profilemanager.ProfileManager + eventHandler eventHandler + profileMenuItem *systray.MenuItem + emailMenuItem *systray.MenuItem + profileSubItems []*subItem + manageProfilesSubItem *subItem +} + +func newProfileMenu(profileManager *profilemanager.ProfileManager, eventHandler eventHandler, profileMenuItem, emailMenuItem *systray.MenuItem) *profileMenu { p := profileMenu{ profileManager: profileManager, + eventHandler: eventHandler, profileMenuItem: profileMenuItem, emailMenuItem: emailMenuItem, } + p.emailMenuItem.Disable() p.refresh() return &p @@ -273,25 +283,83 @@ func (p *profileMenu) refresh() { } // Clear existing profile items - for _, item := range p.profileItems { + for _, item := range p.profileSubItems { item.Remove() + item.cancel() } - if p.manageProfilesItem != nil { + if p.manageProfilesSubItem != nil { // Remove the manage profiles item if it exists - p.manageProfilesItem.Remove() + p.manageProfilesSubItem.Remove() + p.manageProfilesSubItem.cancel() + p.manageProfilesSubItem = nil } + var activeProfile *profilemanager.Profile for _, profile := range profiles { item := p.profileMenuItem.AddSubMenuItem(profile.Name, "") if profile.IsActive { item.Check() + activeProfile = &profile } - p.profileItems = append(p.profileItems, item) + ctx, cancel := context.WithCancel(context.Background()) + p.profileSubItems = append(p.profileSubItems, &subItem{item, ctx, cancel}) + + go func() { + for { + select { + case <-ctx.Done(): + return // context cancelled + case _, ok := <-item.ClickedCh: + if !ok { + return // channel closed + } + + // Handle profile selection + if profile.IsActive { + log.Infof("Profile '%s' is already active", profile.Name) + return + } + err := p.profileManager.SwitchProfile(profile.Name) + if err != nil { + log.Errorf("failed to switch profile '%s': %v", profile.Name, err) + return + } + log.Infof("Switched to profile '%s'", profile.Name) + p.profileMenuItem.SetTitle(profile.Name) + // TODO(hakan): update email menu item if needed + } + } + }() + // TODO(hakan): handle switch profile } p.profileMenuItem.AddSeparator() - p.manageProfilesItem = p.profileMenuItem.AddSubMenuItem("Manage Profiles", "") + ctx, cancel := context.WithCancel(context.Background()) + manageItem := p.profileMenuItem.AddSubMenuItem("Manage Profiles", "") + p.manageProfilesSubItem = &subItem{manageItem, ctx, cancel} + + go func() { + for { + select { + case <-ctx.Done(): + return // context cancelled + case _, ok := <-manageItem.ClickedCh: + if !ok { + return // channel closed + } + // Handle manage profiles click + p.eventHandler.runSelfCommand("profiles", "true") + } + } + }() + + if activeProfile != nil { + p.profileMenuItem.SetTitle(activeProfile.Name) + } else { + p.profileMenuItem.SetTitle("Profile: None") + p.emailMenuItem.Hide() + } }