From beee8414a3a2628ecf7fc715897751c4a39b1cb1 Mon Sep 17 00:00:00 2001 From: trevor-signal <131492920+trevor-signal@users.noreply.github.com> Date: Thu, 14 Mar 2024 13:01:40 -0400 Subject: [PATCH] Enable minimize to tray on linux in production --- app/SystemTraySettingCache.ts | 5 +- app/main.ts | 12 +++-- .../app/SystemTraySettingCache_test.ts | 29 ++++-------- ts/test-node/types/Settings_test.ts | 46 ++++++++++++++++--- ts/types/Settings.ts | 27 ++++++++--- ts/windows/settings/preload.ts | 10 +--- 6 files changed, 81 insertions(+), 48 deletions(-) diff --git a/app/SystemTraySettingCache.ts b/app/SystemTraySettingCache.ts index 4bd60a79b3..e320c1ec50 100644 --- a/app/SystemTraySettingCache.ts +++ b/app/SystemTraySettingCache.ts @@ -21,8 +21,7 @@ export class SystemTraySettingCache { constructor( private readonly ephemeralConfig: Pick, - private readonly argv: Array, - private readonly appVersion: string + private readonly argv: Array ) {} async get(): Promise { @@ -53,7 +52,7 @@ export class SystemTraySettingCache { log.info( `getSystemTraySetting saw --use-tray-icon flag. Returning ${result}` ); - } else if (isSystemTraySupported(OS, this.appVersion)) { + } else if (isSystemTraySupported(OS)) { const value = this.ephemeralConfig.get('system-tray-setting'); if (value !== undefined) { log.info('getSystemTraySetting got value', value); diff --git a/app/main.ts b/app/main.ts index d904493e11..c772ec3867 100644 --- a/app/main.ts +++ b/app/main.ts @@ -84,7 +84,10 @@ import { shouldMinimizeToSystemTray, parseSystemTraySetting, } from '../ts/types/SystemTraySetting'; -import { isSystemTraySupported } from '../ts/types/Settings'; +import { + getDefaultSystemTraySetting, + isSystemTraySupported, +} from '../ts/types/Settings'; import * as ephemeralConfig from './ephemeral_config'; import * as logging from '../ts/logging/main_process_logging'; import { MainSQL } from '../ts/sql/main'; @@ -396,8 +399,7 @@ const zoomFactorService = new ZoomFactorService({ let systemTrayService: SystemTrayService | undefined; const systemTraySettingCache = new SystemTraySettingCache( ephemeralConfig, - process.argv, - app.getVersion() + process.argv ); const windowFromUserConfig = userConfig.get('window'); @@ -1789,10 +1791,10 @@ app.on('ready', async () => { // would still show the window. // (User can change these settings later) if ( - isSystemTraySupported(OS, app.getVersion()) && + isSystemTraySupported(OS) && (await systemTraySettingCache.get()) === SystemTraySetting.Uninitialized ) { - const newValue = SystemTraySetting.MinimizeToSystemTray; + const newValue = getDefaultSystemTraySetting(OS, app.getVersion()); getLogger().info(`app.ready: setting system-tray-setting to ${newValue}`); systemTraySettingCache.set(newValue); diff --git a/ts/test-node/app/SystemTraySettingCache_test.ts b/ts/test-node/app/SystemTraySettingCache_test.ts index 09f719bed0..dda1906dd7 100644 --- a/ts/test-node/app/SystemTraySettingCache_test.ts +++ b/ts/test-node/app/SystemTraySettingCache_test.ts @@ -28,21 +28,16 @@ describe('SystemTraySettingCache', () => { }); it('returns MinimizeToAndStartInSystemTray if passed the --start-in-tray argument', async () => { - const justOneArg = new SystemTraySettingCache( - config, - ['--start-in-tray'], - '1.2.3' - ); + const justOneArg = new SystemTraySettingCache(config, ['--start-in-tray']); assert.strictEqual( await justOneArg.get(), SystemTraySetting.MinimizeToAndStartInSystemTray ); - const bothArgs = new SystemTraySettingCache( - config, - ['--start-in-tray', '--use-tray-icon'], - '1.2.3' - ); + const bothArgs = new SystemTraySettingCache(config, [ + '--start-in-tray', + '--use-tray-icon', + ]); assert.strictEqual( await bothArgs.get(), SystemTraySetting.MinimizeToAndStartInSystemTray @@ -53,11 +48,7 @@ describe('SystemTraySettingCache', () => { }); it('returns MinimizeToSystemTray if passed the --use-tray-icon argument', async () => { - const cache = new SystemTraySettingCache( - config, - ['--use-tray-icon'], - '1.2.3' - ); + const cache = new SystemTraySettingCache(config, ['--use-tray-icon']); assert.strictEqual( await cache.get(), SystemTraySetting.MinimizeToSystemTray @@ -70,7 +61,7 @@ describe('SystemTraySettingCache', () => { it('returns Uninitialized if system tray is supported but no preference is stored', async () => { sandbox.stub(process, 'platform').value('win32'); - const cache = new SystemTraySettingCache(config, [], '1.2.3'); + const cache = new SystemTraySettingCache(config, []); assert.strictEqual(await cache.get(), SystemTraySetting.Uninitialized); assert(configGetStub.calledOnceWith('system-tray-setting')); assert( @@ -86,7 +77,7 @@ describe('SystemTraySettingCache', () => { configGetStub.returns('garbage'); - const cache = new SystemTraySettingCache(config, [], '1.2.3'); + const cache = new SystemTraySettingCache(config, []); assert.strictEqual(await cache.get(), SystemTraySetting.Uninitialized); assert(configGetStub.calledOnceWith('system-tray-setting')); assert( @@ -102,7 +93,7 @@ describe('SystemTraySettingCache', () => { configGetStub.returns('MinimizeToSystemTray'); - const cache = new SystemTraySettingCache(config, [], '1.2.3'); + const cache = new SystemTraySettingCache(config, []); assert.strictEqual( await cache.get(), SystemTraySetting.MinimizeToSystemTray @@ -113,7 +104,7 @@ describe('SystemTraySettingCache', () => { it('returns DoNotUseSystemTray if system tray is unsupported and there are no CLI flags', async () => { sandbox.stub(process, 'platform').value('darwin'); - const cache = new SystemTraySettingCache(config, [], '1.2.3'); + const cache = new SystemTraySettingCache(config, []); assert.strictEqual(await cache.get(), SystemTraySetting.DoNotUseSystemTray); sinon.assert.notCalled(configGetStub); diff --git a/ts/test-node/types/Settings_test.ts b/ts/test-node/types/Settings_test.ts index d288d5084d..e875d83b21 100644 --- a/ts/test-node/types/Settings_test.ts +++ b/ts/test-node/types/Settings_test.ts @@ -7,6 +7,7 @@ import { assert } from 'chai'; import { getOSFunctions } from '../../util/os/shared'; import * as Settings from '../../types/Settings'; +import { SystemTraySetting } from '../../types/SystemTraySetting'; describe('Settings', () => { let sandbox: Sinon.SinonSandbox; @@ -128,26 +129,59 @@ describe('Settings', () => { it('returns false on macOS', () => { sandbox.stub(process, 'platform').value('darwin'); const OS = getOSFunctions(os.release()); - assert.isFalse(Settings.isSystemTraySupported(OS, '1.2.3')); + assert.isFalse(Settings.isSystemTraySupported(OS)); }); it('returns true on Windows 8', () => { sandbox.stub(process, 'platform').value('win32'); sandbox.stub(os, 'release').returns('8.0.0'); const OS = getOSFunctions(os.release()); - assert.isTrue(Settings.isSystemTraySupported(OS, '1.2.3')); + assert.isTrue(Settings.isSystemTraySupported(OS)); }); - it('returns false on Linux production', () => { + it('returns true on Linux', () => { sandbox.stub(process, 'platform').value('linux'); const OS = getOSFunctions(os.release()); - assert.isFalse(Settings.isSystemTraySupported(OS, '1.2.3')); + assert.isTrue(Settings.isSystemTraySupported(OS)); + }); + }); + + describe('getDefaultSystemTraySetting', () => { + it('returns DoNotUseSystemTray is unsupported OS', () => { + sandbox.stub(process, 'platform').value('darwin'); + const OS = getOSFunctions(os.release()); + assert.strictEqual( + Settings.getDefaultSystemTraySetting(OS, '1.2.3'), + SystemTraySetting.DoNotUseSystemTray + ); }); - it('returns true on Linux beta', () => { + it('returns MinimizeToSystemTray on Windows 8', () => { + sandbox.stub(process, 'platform').value('win32'); + sandbox.stub(os, 'release').returns('8.0.0'); + const OS = getOSFunctions(os.release()); + assert.strictEqual( + Settings.getDefaultSystemTraySetting(OS, '1.2.3'), + SystemTraySetting.MinimizeToSystemTray + ); + }); + + it('returns MinimizeToSystemTray on Linux Beta', () => { sandbox.stub(process, 'platform').value('linux'); const OS = getOSFunctions(os.release()); - assert.isTrue(Settings.isSystemTraySupported(OS, '1.2.3-beta.4')); + assert.strictEqual( + Settings.getDefaultSystemTraySetting(OS, '1.2.3-beta.1'), + SystemTraySetting.MinimizeToSystemTray + ); + }); + + it('returns DoNotUseSystemTray on Linux Prod', () => { + sandbox.stub(process, 'platform').value('linux'); + const OS = getOSFunctions(os.release()); + assert.strictEqual( + Settings.getDefaultSystemTraySetting(OS, '1.2.3'), + SystemTraySetting.DoNotUseSystemTray + ); }); }); }); diff --git a/ts/types/Settings.ts b/ts/types/Settings.ts index 31100d9d66..7a045ee254 100644 --- a/ts/types/Settings.ts +++ b/ts/types/Settings.ts @@ -4,6 +4,7 @@ import semver from 'semver'; import type { OSType } from '../util/os/shared'; +import { SystemTraySetting } from './SystemTraySetting'; import { isProduction } from '../util/version'; const MIN_WINDOWS_VERSION = '8.0.0'; @@ -29,19 +30,31 @@ export const isDrawAttentionSupported = (OS: OSType): boolean => !OS.isMacOS(); * Returns `true` if you can minimize the app to the system tray. Users can override this * option with a command line flag, but that is not officially supported. */ -export const isSystemTraySupported = ( +export const isSystemTraySupported = (OS: OSType): boolean => + OS.isWindows() || OS.isLinux(); + +export const getDefaultSystemTraySetting = ( OS: OSType, appVersion: string -): boolean => - // We eventually want to support Linux in production. - OS.isWindows() || (OS.isLinux() && !isProduction(appVersion)); +): SystemTraySetting => { + if (!isSystemTraySupported(OS)) { + return SystemTraySetting.DoNotUseSystemTray; + } + + // System tray on linux may not be well supported, so we default to it being off in + // production + if (OS.isLinux() && isProduction(appVersion)) { + return SystemTraySetting.DoNotUseSystemTray; + } + + return SystemTraySetting.MinimizeToSystemTray; +}; // On Windows minimize and start in system tray is default when app is selected // to launch at login, because we can provide `['--start-in-tray']` args. export const isMinimizeToAndStartInSystemTraySupported = ( - OS: OSType, - appVersion: string -): boolean => !OS.isWindows() && isSystemTraySupported(OS, appVersion); + OS: OSType +): boolean => !OS.isWindows() && isSystemTraySupported(OS); export const isAutoDownloadUpdatesSupported = (OS: OSType): boolean => OS.isWindows() || OS.isMacOS(); diff --git a/ts/windows/settings/preload.ts b/ts/windows/settings/preload.ts index c390a2edf2..35d9a678f6 100644 --- a/ts/windows/settings/preload.ts +++ b/ts/windows/settings/preload.ts @@ -310,15 +310,9 @@ async function renderPreferences() { isHideMenuBarSupported: Settings.isHideMenuBarSupported(OS), isNotificationAttentionSupported: Settings.isDrawAttentionSupported(OS), isSyncSupported: !isSyncNotSupported, - isSystemTraySupported: Settings.isSystemTraySupported( - OS, - MinimalSignalContext.getVersion() - ), + isSystemTraySupported: Settings.isSystemTraySupported(OS), isMinimizeToAndStartInSystemTraySupported: - Settings.isMinimizeToAndStartInSystemTraySupported( - OS, - MinimalSignalContext.getVersion() - ), + Settings.isMinimizeToAndStartInSystemTraySupported(OS), // Change handlers onAudioNotificationsChange: attachRenderCallback(