diff options
Diffstat (limited to 'packages/cli/src')
| -rw-r--r-- | packages/cli/src/config/settings.test.ts | 56 | ||||
| -rw-r--r-- | packages/cli/src/config/settings.ts | 17 |
2 files changed, 59 insertions, 14 deletions
diff --git a/packages/cli/src/config/settings.test.ts b/packages/cli/src/config/settings.test.ts index b99e8b79..ae655fe1 100644 --- a/packages/cli/src/config/settings.test.ts +++ b/packages/cli/src/config/settings.test.ts @@ -46,7 +46,7 @@ import stripJsonComments from 'strip-json-comments'; // Will be mocked separatel import { loadSettings, USER_SETTINGS_PATH, // This IS the mocked path. - SYSTEM_SETTINGS_PATH, + getSystemSettingsPath, SETTINGS_DIRECTORY_NAME, // This is from the original module, but used by the mock. SettingScope, } from './settings.js'; @@ -104,7 +104,7 @@ describe('Settings Loading and Merging', () => { it('should load system settings if only system file exists', () => { (mockFsExistsSync as Mock).mockImplementation( - (p: fs.PathLike) => p === SYSTEM_SETTINGS_PATH, + (p: fs.PathLike) => p === getSystemSettingsPath(), ); const systemSettingsContent = { theme: 'system-default', @@ -112,7 +112,7 @@ describe('Settings Loading and Merging', () => { }; (fs.readFileSync as Mock).mockImplementation( (p: fs.PathOrFileDescriptor) => { - if (p === SYSTEM_SETTINGS_PATH) + if (p === getSystemSettingsPath()) return JSON.stringify(systemSettingsContent); return '{}'; }, @@ -121,7 +121,7 @@ describe('Settings Loading and Merging', () => { const settings = loadSettings(MOCK_WORKSPACE_DIR); expect(fs.readFileSync).toHaveBeenCalledWith( - SYSTEM_SETTINGS_PATH, + getSystemSettingsPath(), 'utf-8', ); expect(settings.system.settings).toEqual(systemSettingsContent); @@ -257,7 +257,7 @@ describe('Settings Loading and Merging', () => { (fs.readFileSync as Mock).mockImplementation( (p: fs.PathOrFileDescriptor) => { - if (p === SYSTEM_SETTINGS_PATH) + if (p === getSystemSettingsPath()) return JSON.stringify(systemSettingsContent); if (p === USER_SETTINGS_PATH) return JSON.stringify(userSettingsContent); @@ -743,7 +743,7 @@ describe('Settings Loading and Merging', () => { (fs.readFileSync as Mock).mockImplementation( (p: fs.PathOrFileDescriptor) => { - if (p === SYSTEM_SETTINGS_PATH) { + if (p === getSystemSettingsPath()) { process.env.SHARED_VAR = 'system_value_for_system_read'; // Set for system settings read return JSON.stringify(systemSettingsContent); } @@ -913,6 +913,50 @@ describe('Settings Loading and Merging', () => { delete process.env.TEST_HOST; delete process.env.TEST_PORT; }); + + describe('when GEMINI_CLI_SYSTEM_SETTINGS_PATH is set', () => { + const MOCK_ENV_SYSTEM_SETTINGS_PATH = '/mock/env/system/settings.json'; + + beforeEach(() => { + process.env.GEMINI_CLI_SYSTEM_SETTINGS_PATH = + MOCK_ENV_SYSTEM_SETTINGS_PATH; + }); + + afterEach(() => { + delete process.env.GEMINI_CLI_SYSTEM_SETTINGS_PATH; + }); + + it('should load system settings from the path specified in the environment variable', () => { + (mockFsExistsSync as Mock).mockImplementation( + (p: fs.PathLike) => p === MOCK_ENV_SYSTEM_SETTINGS_PATH, + ); + const systemSettingsContent = { + theme: 'env-var-theme', + sandbox: true, + }; + (fs.readFileSync as Mock).mockImplementation( + (p: fs.PathOrFileDescriptor) => { + if (p === MOCK_ENV_SYSTEM_SETTINGS_PATH) + return JSON.stringify(systemSettingsContent); + return '{}'; + }, + ); + + const settings = loadSettings(MOCK_WORKSPACE_DIR); + + expect(fs.readFileSync).toHaveBeenCalledWith( + MOCK_ENV_SYSTEM_SETTINGS_PATH, + 'utf-8', + ); + expect(settings.system.path).toBe(MOCK_ENV_SYSTEM_SETTINGS_PATH); + expect(settings.system.settings).toEqual(systemSettingsContent); + expect(settings.merged).toEqual({ + ...systemSettingsContent, + customThemes: {}, + mcpServers: {}, + }); + }); + }); }); describe('LoadedSettings class', () => { diff --git a/packages/cli/src/config/settings.ts b/packages/cli/src/config/settings.ts index 3cbfe22d..bc2206a7 100644 --- a/packages/cli/src/config/settings.ts +++ b/packages/cli/src/config/settings.ts @@ -25,7 +25,10 @@ export const SETTINGS_DIRECTORY_NAME = '.gemini'; export const USER_SETTINGS_DIR = path.join(homedir(), SETTINGS_DIRECTORY_NAME); export const USER_SETTINGS_PATH = path.join(USER_SETTINGS_DIR, 'settings.json'); -function getSystemSettingsPath(): string { +export function getSystemSettingsPath(): string { + if (process.env.GEMINI_CLI_SYSTEM_SETTINGS_PATH) { + return process.env.GEMINI_CLI_SYSTEM_SETTINGS_PATH; + } if (platform() === 'darwin') { return '/Library/Application Support/GeminiCli/settings.json'; } else if (platform() === 'win32') { @@ -35,8 +38,6 @@ function getSystemSettingsPath(): string { } } -export const SYSTEM_SETTINGS_PATH = getSystemSettingsPath(); - export enum SettingScope { User = 'User', Workspace = 'Workspace', @@ -297,11 +298,11 @@ export function loadSettings(workspaceDir: string): LoadedSettings { let userSettings: Settings = {}; let workspaceSettings: Settings = {}; const settingsErrors: SettingsError[] = []; - + const systemSettingsPath = getSystemSettingsPath(); // Load system settings try { - if (fs.existsSync(SYSTEM_SETTINGS_PATH)) { - const systemContent = fs.readFileSync(SYSTEM_SETTINGS_PATH, 'utf-8'); + if (fs.existsSync(systemSettingsPath)) { + const systemContent = fs.readFileSync(systemSettingsPath, 'utf-8'); const parsedSystemSettings = JSON.parse( stripJsonComments(systemContent), ) as Settings; @@ -310,7 +311,7 @@ export function loadSettings(workspaceDir: string): LoadedSettings { } catch (error: unknown) { settingsErrors.push({ message: getErrorMessage(error), - path: SYSTEM_SETTINGS_PATH, + path: systemSettingsPath, }); } @@ -368,7 +369,7 @@ export function loadSettings(workspaceDir: string): LoadedSettings { return new LoadedSettings( { - path: SYSTEM_SETTINGS_PATH, + path: systemSettingsPath, settings: systemSettings, }, { |
