mirror of
https://github.com/google-gemini/gemini-cli.git
synced 2026-04-25 20:44:46 -07:00
Disallow unnecessary awaits. (#15172)
This commit is contained in:
committed by
GitHub
parent
3e9a0a7628
commit
7f2d33458a
@@ -165,6 +165,7 @@ export default tseslint.config(
|
|||||||
'prefer-const': ['error', { destructuring: 'all' }],
|
'prefer-const': ['error', { destructuring: 'all' }],
|
||||||
radix: 'error',
|
radix: 'error',
|
||||||
'default-case': 'error',
|
'default-case': 'error',
|
||||||
|
'@typescript-eslint/await-thenable': ['error'],
|
||||||
'@typescript-eslint/no-floating-promises': ['error'],
|
'@typescript-eslint/no-floating-promises': ['error'],
|
||||||
'@typescript-eslint/no-unnecessary-type-assertion': ['error'],
|
'@typescript-eslint/no-unnecessary-type-assertion': ['error'],
|
||||||
},
|
},
|
||||||
|
|||||||
@@ -123,7 +123,7 @@ export class Task {
|
|||||||
// process. This is not scoped to the individual task but reflects the global connection
|
// process. This is not scoped to the individual task but reflects the global connection
|
||||||
// state managed within the @gemini-cli/core module.
|
// state managed within the @gemini-cli/core module.
|
||||||
async getMetadata(): Promise<TaskMetadata> {
|
async getMetadata(): Promise<TaskMetadata> {
|
||||||
const toolRegistry = await this.config.getToolRegistry();
|
const toolRegistry = this.config.getToolRegistry();
|
||||||
const mcpServers = this.config.getMcpClientManager()?.getMcpServers() || {};
|
const mcpServers = this.config.getMcpClientManager()?.getMcpServers() || {};
|
||||||
const serverStatuses = getAllMCPServerStatuses();
|
const serverStatuses = getAllMCPServerStatuses();
|
||||||
const servers = Object.keys(mcpServers).map((serverName) => ({
|
const servers = Object.keys(mcpServers).map((serverName) => ({
|
||||||
|
|||||||
@@ -228,7 +228,9 @@ describe('extensions disable command', () => {
|
|||||||
_: [],
|
_: [],
|
||||||
$0: '',
|
$0: '',
|
||||||
};
|
};
|
||||||
await (command.handler as unknown as (args: TestArgv) => void)(argv);
|
await (command.handler as unknown as (args: TestArgv) => Promise<void>)(
|
||||||
|
argv,
|
||||||
|
);
|
||||||
expect(mockExtensionManager).toHaveBeenCalledWith(
|
expect(mockExtensionManager).toHaveBeenCalledWith(
|
||||||
expect.objectContaining({
|
expect.objectContaining({
|
||||||
workspaceDir: '/test/dir',
|
workspaceDir: '/test/dir',
|
||||||
|
|||||||
@@ -205,7 +205,9 @@ describe('extensions enable command', () => {
|
|||||||
_: [],
|
_: [],
|
||||||
$0: '',
|
$0: '',
|
||||||
};
|
};
|
||||||
await (command.handler as unknown as (args: TestArgv) => void)(argv);
|
await (command.handler as unknown as (args: TestArgv) => Promise<void>)(
|
||||||
|
argv,
|
||||||
|
);
|
||||||
|
|
||||||
expect(
|
expect(
|
||||||
mockExtensionManager.prototype.enableExtension,
|
mockExtensionManager.prototype.enableExtension,
|
||||||
|
|||||||
@@ -180,7 +180,9 @@ describe('extensions link command', () => {
|
|||||||
_: [],
|
_: [],
|
||||||
$0: '',
|
$0: '',
|
||||||
};
|
};
|
||||||
await (command.handler as unknown as (args: TestArgv) => void)(argv);
|
await (command.handler as unknown as (args: TestArgv) => Promise<void>)(
|
||||||
|
argv,
|
||||||
|
);
|
||||||
|
|
||||||
expect(
|
expect(
|
||||||
mockExtensionManager.prototype.installOrUpdateExtension,
|
mockExtensionManager.prototype.installOrUpdateExtension,
|
||||||
|
|||||||
@@ -49,7 +49,7 @@ const setCommand: CommandModule<object, SetArgs> = {
|
|||||||
if (!extension || !extensionManager) {
|
if (!extension || !extensionManager) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const extensionConfig = extensionManager.loadExtensionConfig(
|
const extensionConfig = await extensionManager.loadExtensionConfig(
|
||||||
extension.path,
|
extension.path,
|
||||||
);
|
);
|
||||||
if (!extensionConfig) {
|
if (!extensionConfig) {
|
||||||
@@ -89,7 +89,7 @@ const listCommand: CommandModule<object, ListArgs> = {
|
|||||||
if (!extension || !extensionManager) {
|
if (!extension || !extensionManager) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const extensionConfig = extensionManager.loadExtensionConfig(
|
const extensionConfig = await extensionManager.loadExtensionConfig(
|
||||||
extension.path,
|
extension.path,
|
||||||
);
|
);
|
||||||
if (
|
if (
|
||||||
|
|||||||
@@ -287,7 +287,9 @@ describe('extensions uninstall command', () => {
|
|||||||
[key: string]: unknown;
|
[key: string]: unknown;
|
||||||
}
|
}
|
||||||
const argv: TestArgv = { names: ['my-extension'], _: [], $0: '' };
|
const argv: TestArgv = { names: ['my-extension'], _: [], $0: '' };
|
||||||
await (command.handler as unknown as (args: TestArgv) => void)(argv);
|
await (command.handler as unknown as (args: TestArgv) => Promise<void>)(
|
||||||
|
argv,
|
||||||
|
);
|
||||||
|
|
||||||
expect(mockUninstallExtension).toHaveBeenCalledWith(
|
expect(mockUninstallExtension).toHaveBeenCalledWith(
|
||||||
'my-extension',
|
'my-extension',
|
||||||
|
|||||||
@@ -41,7 +41,7 @@ async function validateExtension(args: ValidateArgs) {
|
|||||||
});
|
});
|
||||||
const absoluteInputPath = path.resolve(args.path);
|
const absoluteInputPath = path.resolve(args.path);
|
||||||
const extensionConfig: ExtensionConfig =
|
const extensionConfig: ExtensionConfig =
|
||||||
extensionManager.loadExtensionConfig(absoluteInputPath);
|
await extensionManager.loadExtensionConfig(absoluteInputPath);
|
||||||
const warnings: string[] = [];
|
const warnings: string[] = [];
|
||||||
const errors: string[] = [];
|
const errors: string[] = [];
|
||||||
|
|
||||||
|
|||||||
@@ -4,7 +4,15 @@
|
|||||||
* SPDX-License-Identifier: Apache-2.0
|
* SPDX-License-Identifier: Apache-2.0
|
||||||
*/
|
*/
|
||||||
|
|
||||||
import { describe, it, expect, vi, type Mock, type MockInstance } from 'vitest';
|
import {
|
||||||
|
describe,
|
||||||
|
it,
|
||||||
|
expect,
|
||||||
|
vi,
|
||||||
|
beforeEach,
|
||||||
|
type Mock,
|
||||||
|
type MockInstance,
|
||||||
|
} from 'vitest';
|
||||||
import yargs, { type Argv } from 'yargs';
|
import yargs, { type Argv } from 'yargs';
|
||||||
import { addCommand } from './add.js';
|
import { addCommand } from './add.js';
|
||||||
import { loadSettings, SettingScope } from '../../config/settings.js';
|
import { loadSettings, SettingScope } from '../../config/settings.js';
|
||||||
|
|||||||
@@ -220,7 +220,7 @@ export class ExtensionManager extends ExtensionLoader {
|
|||||||
}
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
newExtensionConfig = this.loadExtensionConfig(localSourcePath);
|
newExtensionConfig = await this.loadExtensionConfig(localSourcePath);
|
||||||
|
|
||||||
if (isUpdate && installMetadata.autoUpdate) {
|
if (isUpdate && installMetadata.autoUpdate) {
|
||||||
const oldSettings = new Set(
|
const oldSettings = new Set(
|
||||||
@@ -364,7 +364,7 @@ export class ExtensionManager extends ExtensionLoader {
|
|||||||
// to get the name and version for logging.
|
// to get the name and version for logging.
|
||||||
if (!newExtensionConfig && localSourcePath) {
|
if (!newExtensionConfig && localSourcePath) {
|
||||||
try {
|
try {
|
||||||
newExtensionConfig = this.loadExtensionConfig(localSourcePath);
|
newExtensionConfig = await this.loadExtensionConfig(localSourcePath);
|
||||||
} catch {
|
} catch {
|
||||||
// Ignore error, this is just for logging.
|
// Ignore error, this is just for logging.
|
||||||
}
|
}
|
||||||
@@ -491,7 +491,7 @@ export class ExtensionManager extends ExtensionLoader {
|
|||||||
}
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
let config = this.loadExtensionConfig(effectiveExtensionPath);
|
let config = await this.loadExtensionConfig(effectiveExtensionPath);
|
||||||
if (
|
if (
|
||||||
this.getExtensions().find((extension) => extension.name === config.name)
|
this.getExtensions().find((extension) => extension.name === config.name)
|
||||||
) {
|
) {
|
||||||
@@ -571,13 +571,13 @@ export class ExtensionManager extends ExtensionLoader {
|
|||||||
return this.maybeStopExtension(extension);
|
return this.maybeStopExtension(extension);
|
||||||
}
|
}
|
||||||
|
|
||||||
loadExtensionConfig(extensionDir: string): ExtensionConfig {
|
async loadExtensionConfig(extensionDir: string): Promise<ExtensionConfig> {
|
||||||
const configFilePath = path.join(extensionDir, EXTENSIONS_CONFIG_FILENAME);
|
const configFilePath = path.join(extensionDir, EXTENSIONS_CONFIG_FILENAME);
|
||||||
if (!fs.existsSync(configFilePath)) {
|
if (!fs.existsSync(configFilePath)) {
|
||||||
throw new Error(`Configuration file not found at ${configFilePath}`);
|
throw new Error(`Configuration file not found at ${configFilePath}`);
|
||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
const configContent = fs.readFileSync(configFilePath, 'utf-8');
|
const configContent = await fs.promises.readFile(configFilePath, 'utf-8');
|
||||||
const rawConfig = JSON.parse(configContent) as ExtensionConfig;
|
const rawConfig = JSON.parse(configContent) as ExtensionConfig;
|
||||||
if (!rawConfig.name || !rawConfig.version) {
|
if (!rawConfig.name || !rawConfig.version) {
|
||||||
throw new Error(
|
throw new Error(
|
||||||
|
|||||||
@@ -1424,9 +1424,10 @@ This extension will run the following MCP servers:
|
|||||||
],
|
],
|
||||||
});
|
});
|
||||||
|
|
||||||
const previousExtensionConfig = extensionManager.loadExtensionConfig(
|
const previousExtensionConfig =
|
||||||
path.join(userExtensionsDir, 'my-local-extension'),
|
await extensionManager.loadExtensionConfig(
|
||||||
);
|
path.join(userExtensionsDir, 'my-local-extension'),
|
||||||
|
);
|
||||||
mockPromptForSettings.mockResolvedValueOnce('new-setting-value');
|
mockPromptForSettings.mockResolvedValueOnce('new-setting-value');
|
||||||
|
|
||||||
// 3. Call installOrUpdateExtension to perform the update.
|
// 3. Call installOrUpdateExtension to perform the update.
|
||||||
@@ -1481,9 +1482,10 @@ This extension will run the following MCP servers:
|
|||||||
],
|
],
|
||||||
});
|
});
|
||||||
|
|
||||||
const previousExtensionConfig = extensionManager.loadExtensionConfig(
|
const previousExtensionConfig =
|
||||||
path.join(userExtensionsDir, 'my-auto-update-ext'),
|
await extensionManager.loadExtensionConfig(
|
||||||
);
|
path.join(userExtensionsDir, 'my-auto-update-ext'),
|
||||||
|
);
|
||||||
|
|
||||||
// 3. Attempt to update and assert it fails
|
// 3. Attempt to update and assert it fails
|
||||||
await expect(
|
await expect(
|
||||||
@@ -1967,7 +1969,7 @@ This extension will run the following MCP servers:
|
|||||||
expect(activeExtensions).toHaveLength(0);
|
expect(activeExtensions).toHaveLength(0);
|
||||||
|
|
||||||
await extensionManager.enableExtension('ext1', SettingScope.User);
|
await extensionManager.enableExtension('ext1', SettingScope.User);
|
||||||
activeExtensions = await getActiveExtensions();
|
activeExtensions = getActiveExtensions();
|
||||||
expect(activeExtensions).toHaveLength(1);
|
expect(activeExtensions).toHaveLength(1);
|
||||||
expect(activeExtensions[0].name).toBe('ext1');
|
expect(activeExtensions[0].name).toBe('ext1');
|
||||||
});
|
});
|
||||||
@@ -1984,7 +1986,7 @@ This extension will run the following MCP servers:
|
|||||||
expect(activeExtensions).toHaveLength(0);
|
expect(activeExtensions).toHaveLength(0);
|
||||||
|
|
||||||
await extensionManager.enableExtension('ext1', SettingScope.Workspace);
|
await extensionManager.enableExtension('ext1', SettingScope.Workspace);
|
||||||
activeExtensions = await getActiveExtensions();
|
activeExtensions = getActiveExtensions();
|
||||||
expect(activeExtensions).toHaveLength(1);
|
expect(activeExtensions).toHaveLength(1);
|
||||||
expect(activeExtensions[0].name).toBe('ext1');
|
expect(activeExtensions[0].name).toBe('ext1');
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -221,9 +221,11 @@ describe('github.ts', () => {
|
|||||||
});
|
});
|
||||||
|
|
||||||
it('should return NOT_UPDATABLE for non-git/non-release extensions', async () => {
|
it('should return NOT_UPDATABLE for non-git/non-release extensions', async () => {
|
||||||
vi.mocked(mockExtensionManager.loadExtensionConfig).mockReturnValue({
|
vi.mocked(mockExtensionManager.loadExtensionConfig).mockReturnValue(
|
||||||
version: '1.0.0',
|
Promise.resolve({
|
||||||
} as unknown as ExtensionConfig);
|
version: '1.0.0',
|
||||||
|
} as unknown as ExtensionConfig),
|
||||||
|
);
|
||||||
|
|
||||||
const linkExt = {
|
const linkExt = {
|
||||||
installMetadata: { type: 'link' },
|
installMetadata: { type: 'link' },
|
||||||
|
|||||||
@@ -175,7 +175,7 @@ export async function checkForExtensionUpdate(
|
|||||||
if (installMetadata?.type === 'local') {
|
if (installMetadata?.type === 'local') {
|
||||||
let latestConfig: ExtensionConfig | undefined;
|
let latestConfig: ExtensionConfig | undefined;
|
||||||
try {
|
try {
|
||||||
latestConfig = extensionManager.loadExtensionConfig(
|
latestConfig = await extensionManager.loadExtensionConfig(
|
||||||
installMetadata.source,
|
installMetadata.source,
|
||||||
);
|
);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
|
|||||||
@@ -145,10 +145,12 @@ describe('Extension Update Logic', () => {
|
|||||||
});
|
});
|
||||||
|
|
||||||
it('should successfully update extension and set state to UPDATED_NEEDS_RESTART by default', async () => {
|
it('should successfully update extension and set state to UPDATED_NEEDS_RESTART by default', async () => {
|
||||||
vi.mocked(mockExtensionManager.loadExtensionConfig).mockReturnValue({
|
vi.mocked(mockExtensionManager.loadExtensionConfig).mockReturnValue(
|
||||||
name: 'test-extension',
|
Promise.resolve({
|
||||||
version: '1.0.0',
|
name: 'test-extension',
|
||||||
});
|
version: '1.0.0',
|
||||||
|
}),
|
||||||
|
);
|
||||||
vi.mocked(
|
vi.mocked(
|
||||||
mockExtensionManager.installOrUpdateExtension,
|
mockExtensionManager.installOrUpdateExtension,
|
||||||
).mockResolvedValue({
|
).mockResolvedValue({
|
||||||
@@ -183,10 +185,12 @@ describe('Extension Update Logic', () => {
|
|||||||
});
|
});
|
||||||
|
|
||||||
it('should set state to UPDATED if enableExtensionReloading is true', async () => {
|
it('should set state to UPDATED if enableExtensionReloading is true', async () => {
|
||||||
vi.mocked(mockExtensionManager.loadExtensionConfig).mockReturnValue({
|
vi.mocked(mockExtensionManager.loadExtensionConfig).mockReturnValue(
|
||||||
name: 'test-extension',
|
Promise.resolve({
|
||||||
version: '1.0.0',
|
name: 'test-extension',
|
||||||
});
|
version: '1.0.0',
|
||||||
|
}),
|
||||||
|
);
|
||||||
vi.mocked(
|
vi.mocked(
|
||||||
mockExtensionManager.installOrUpdateExtension,
|
mockExtensionManager.installOrUpdateExtension,
|
||||||
).mockResolvedValue({
|
).mockResolvedValue({
|
||||||
@@ -212,10 +216,12 @@ describe('Extension Update Logic', () => {
|
|||||||
});
|
});
|
||||||
|
|
||||||
it('should rollback and set state to ERROR if installation fails', async () => {
|
it('should rollback and set state to ERROR if installation fails', async () => {
|
||||||
vi.mocked(mockExtensionManager.loadExtensionConfig).mockReturnValue({
|
vi.mocked(mockExtensionManager.loadExtensionConfig).mockReturnValue(
|
||||||
name: 'test-extension',
|
Promise.resolve({
|
||||||
version: '1.0.0',
|
name: 'test-extension',
|
||||||
});
|
version: '1.0.0',
|
||||||
|
}),
|
||||||
|
);
|
||||||
vi.mocked(
|
vi.mocked(
|
||||||
mockExtensionManager.installOrUpdateExtension,
|
mockExtensionManager.installOrUpdateExtension,
|
||||||
).mockRejectedValue(new Error('Install failed'));
|
).mockRejectedValue(new Error('Install failed'));
|
||||||
@@ -257,10 +263,12 @@ describe('Extension Update Logic', () => {
|
|||||||
['ext3', { status: ExtensionUpdateState.UPDATE_AVAILABLE }],
|
['ext3', { status: ExtensionUpdateState.UPDATE_AVAILABLE }],
|
||||||
]);
|
]);
|
||||||
|
|
||||||
vi.mocked(mockExtensionManager.loadExtensionConfig).mockReturnValue({
|
vi.mocked(mockExtensionManager.loadExtensionConfig).mockReturnValue(
|
||||||
name: 'ext',
|
Promise.resolve({
|
||||||
version: '1.0.0',
|
name: 'ext',
|
||||||
});
|
version: '1.0.0',
|
||||||
|
}),
|
||||||
|
);
|
||||||
vi.mocked(
|
vi.mocked(
|
||||||
mockExtensionManager.installOrUpdateExtension,
|
mockExtensionManager.installOrUpdateExtension,
|
||||||
).mockResolvedValue({ ...mockExtension, version: '1.1.0' });
|
).mockResolvedValue({ ...mockExtension, version: '1.1.0' });
|
||||||
|
|||||||
@@ -59,7 +59,7 @@ export async function updateExtension(
|
|||||||
|
|
||||||
const tempDir = await ExtensionStorage.createTmpDir();
|
const tempDir = await ExtensionStorage.createTmpDir();
|
||||||
try {
|
try {
|
||||||
const previousExtensionConfig = extensionManager.loadExtensionConfig(
|
const previousExtensionConfig = await extensionManager.loadExtensionConfig(
|
||||||
extension.path,
|
extension.path,
|
||||||
);
|
);
|
||||||
let updatedExtension: GeminiCLIExtension;
|
let updatedExtension: GeminiCLIExtension;
|
||||||
|
|||||||
@@ -48,7 +48,7 @@ describe('chatCommand', () => {
|
|||||||
|
|
||||||
beforeEach(() => {
|
beforeEach(() => {
|
||||||
mockGetHistory = vi.fn().mockReturnValue([]);
|
mockGetHistory = vi.fn().mockReturnValue([]);
|
||||||
mockGetChat = vi.fn().mockResolvedValue({
|
mockGetChat = vi.fn().mockReturnValue({
|
||||||
getHistory: mockGetHistory,
|
getHistory: mockGetHistory,
|
||||||
});
|
});
|
||||||
mockSaveCheckpoint = vi.fn().mockResolvedValue(undefined);
|
mockSaveCheckpoint = vi.fn().mockResolvedValue(undefined);
|
||||||
|
|||||||
@@ -121,7 +121,7 @@ const saveCommand: SlashCommand = {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const chat = await config?.getGeminiClient()?.getChat();
|
const chat = config?.getGeminiClient()?.getChat();
|
||||||
if (!chat) {
|
if (!chat) {
|
||||||
return {
|
return {
|
||||||
type: 'message',
|
type: 'message',
|
||||||
@@ -332,7 +332,7 @@ const shareCommand: SlashCommand = {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
const chat = await context.services.config?.getGeminiClient()?.getChat();
|
const chat = context.services.config?.getGeminiClient()?.getChat();
|
||||||
if (!chat) {
|
if (!chat) {
|
||||||
return {
|
return {
|
||||||
type: 'message',
|
type: 'message',
|
||||||
|
|||||||
@@ -15,7 +15,7 @@ export const copyCommand: SlashCommand = {
|
|||||||
kind: CommandKind.BUILT_IN,
|
kind: CommandKind.BUILT_IN,
|
||||||
autoExecute: true,
|
autoExecute: true,
|
||||||
action: async (context, _args): Promise<SlashCommandActionReturn | void> => {
|
action: async (context, _args): Promise<SlashCommandActionReturn | void> => {
|
||||||
const chat = await context.services.config?.getGeminiClient()?.getChat();
|
const chat = context.services.config?.getGeminiClient()?.getChat();
|
||||||
const history = chat?.getHistory();
|
const history = chat?.getHistory();
|
||||||
|
|
||||||
// Get the last message from the AI (model role)
|
// Get the last message from the AI (model role)
|
||||||
|
|||||||
@@ -85,7 +85,7 @@ describe('mcpCommand', () => {
|
|||||||
}),
|
}),
|
||||||
getMcpServers: vi.fn().mockReturnValue({}),
|
getMcpServers: vi.fn().mockReturnValue({}),
|
||||||
getBlockedMcpServers: vi.fn().mockReturnValue([]),
|
getBlockedMcpServers: vi.fn().mockReturnValue([]),
|
||||||
getPromptRegistry: vi.fn().mockResolvedValue({
|
getPromptRegistry: vi.fn().mockReturnValue({
|
||||||
getAllPrompts: vi.fn().mockReturnValue([]),
|
getAllPrompts: vi.fn().mockReturnValue([]),
|
||||||
getPromptsByServer: vi.fn().mockReturnValue([]),
|
getPromptsByServer: vi.fn().mockReturnValue([]),
|
||||||
}),
|
}),
|
||||||
|
|||||||
@@ -216,7 +216,7 @@ const listAction = async (
|
|||||||
const allTools = toolRegistry.getAllTools();
|
const allTools = toolRegistry.getAllTools();
|
||||||
const mcpTools = allTools.filter((tool) => tool instanceof DiscoveredMCPTool);
|
const mcpTools = allTools.filter((tool) => tool instanceof DiscoveredMCPTool);
|
||||||
|
|
||||||
const promptRegistry = await config.getPromptRegistry();
|
const promptRegistry = config.getPromptRegistry();
|
||||||
const mcpPrompts = promptRegistry
|
const mcpPrompts = promptRegistry
|
||||||
.getAllPrompts()
|
.getAllPrompts()
|
||||||
.filter(
|
.filter(
|
||||||
|
|||||||
@@ -85,7 +85,7 @@ export const memoryCommand: SlashCommand = {
|
|||||||
);
|
);
|
||||||
|
|
||||||
try {
|
try {
|
||||||
const config = await context.services.config;
|
const config = context.services.config;
|
||||||
if (config) {
|
if (config) {
|
||||||
const { memoryContent, fileCount } =
|
const { memoryContent, fileCount } =
|
||||||
await refreshServerHierarchicalMemory(config);
|
await refreshServerHierarchicalMemory(config);
|
||||||
|
|||||||
@@ -116,7 +116,7 @@ async function restoreAction(
|
|||||||
} else if (action.type === 'load_history' && loadHistory) {
|
} else if (action.type === 'load_history' && loadHistory) {
|
||||||
loadHistory(action.history);
|
loadHistory(action.history);
|
||||||
if (action.clientHistory) {
|
if (action.clientHistory) {
|
||||||
await config?.getGeminiClient()?.setHistory(action.clientHistory);
|
config?.getGeminiClient()?.setHistory(action.clientHistory);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -89,7 +89,7 @@ describe('MultiFolderTrustDialog', () => {
|
|||||||
|
|
||||||
const keypressCallback = mockedUseKeypress.mock.calls[0][0];
|
const keypressCallback = mockedUseKeypress.mock.calls[0][0];
|
||||||
await act(async () => {
|
await act(async () => {
|
||||||
await keypressCallback({
|
keypressCallback({
|
||||||
name: 'escape',
|
name: 'escape',
|
||||||
ctrl: false,
|
ctrl: false,
|
||||||
meta: false,
|
meta: false,
|
||||||
@@ -117,7 +117,7 @@ describe('MultiFolderTrustDialog', () => {
|
|||||||
|
|
||||||
const { onSelect } = mockedRadioButtonSelect.mock.calls[0][0];
|
const { onSelect } = mockedRadioButtonSelect.mock.calls[0][0];
|
||||||
await act(async () => {
|
await act(async () => {
|
||||||
await onSelect(MultiFolderTrustChoice.NO);
|
onSelect(MultiFolderTrustChoice.NO);
|
||||||
});
|
});
|
||||||
|
|
||||||
expect(mockFinishAddingDirectories).toHaveBeenCalledWith(
|
expect(mockFinishAddingDirectories).toHaveBeenCalledWith(
|
||||||
@@ -145,7 +145,7 @@ describe('MultiFolderTrustDialog', () => {
|
|||||||
|
|
||||||
const { onSelect } = mockedRadioButtonSelect.mock.calls[0][0];
|
const { onSelect } = mockedRadioButtonSelect.mock.calls[0][0];
|
||||||
await act(async () => {
|
await act(async () => {
|
||||||
await onSelect(MultiFolderTrustChoice.YES);
|
onSelect(MultiFolderTrustChoice.YES);
|
||||||
});
|
});
|
||||||
|
|
||||||
expect(mockAddDirectory).toHaveBeenCalledWith('/path/to/folder1');
|
expect(mockAddDirectory).toHaveBeenCalledWith('/path/to/folder1');
|
||||||
@@ -166,7 +166,7 @@ describe('MultiFolderTrustDialog', () => {
|
|||||||
|
|
||||||
const { onSelect } = mockedRadioButtonSelect.mock.calls[0][0];
|
const { onSelect } = mockedRadioButtonSelect.mock.calls[0][0];
|
||||||
await act(async () => {
|
await act(async () => {
|
||||||
await onSelect(MultiFolderTrustChoice.YES_AND_REMEMBER);
|
onSelect(MultiFolderTrustChoice.YES_AND_REMEMBER);
|
||||||
});
|
});
|
||||||
|
|
||||||
expect(mockAddDirectory).toHaveBeenCalledWith('/path/to/folder1');
|
expect(mockAddDirectory).toHaveBeenCalledWith('/path/to/folder1');
|
||||||
@@ -192,7 +192,7 @@ describe('MultiFolderTrustDialog', () => {
|
|||||||
const { onSelect } = mockedRadioButtonSelect.mock.calls[0][0];
|
const { onSelect } = mockedRadioButtonSelect.mock.calls[0][0];
|
||||||
|
|
||||||
await act(async () => {
|
await act(async () => {
|
||||||
await onSelect(MultiFolderTrustChoice.NO);
|
onSelect(MultiFolderTrustChoice.NO);
|
||||||
});
|
});
|
||||||
|
|
||||||
expect(lastFrame()).toContain('Applying trust settings...');
|
expect(lastFrame()).toContain('Applying trust settings...');
|
||||||
@@ -210,7 +210,7 @@ describe('MultiFolderTrustDialog', () => {
|
|||||||
|
|
||||||
const { onSelect } = mockedRadioButtonSelect.mock.calls[0][0];
|
const { onSelect } = mockedRadioButtonSelect.mock.calls[0][0];
|
||||||
await act(async () => {
|
await act(async () => {
|
||||||
await onSelect(MultiFolderTrustChoice.YES);
|
onSelect(MultiFolderTrustChoice.YES);
|
||||||
});
|
});
|
||||||
|
|
||||||
expect(mockAddItem).toHaveBeenCalledWith(
|
expect(mockAddItem).toHaveBeenCalledWith(
|
||||||
@@ -243,7 +243,7 @@ describe('MultiFolderTrustDialog', () => {
|
|||||||
|
|
||||||
const { onSelect } = mockedRadioButtonSelect.mock.calls[0][0];
|
const { onSelect } = mockedRadioButtonSelect.mock.calls[0][0];
|
||||||
await act(async () => {
|
await act(async () => {
|
||||||
await onSelect(MultiFolderTrustChoice.YES);
|
onSelect(MultiFolderTrustChoice.YES);
|
||||||
});
|
});
|
||||||
|
|
||||||
expect(mockAddDirectory).toHaveBeenCalledWith('/path/to/good');
|
expect(mockAddDirectory).toHaveBeenCalledWith('/path/to/good');
|
||||||
|
|||||||
@@ -55,7 +55,7 @@ export const VimModeProvider = ({
|
|||||||
if (newValue) {
|
if (newValue) {
|
||||||
setVimMode('NORMAL');
|
setVimMode('NORMAL');
|
||||||
}
|
}
|
||||||
await settings.setValue(SettingScope.User, 'general.vimMode', newValue);
|
settings.setValue(SettingScope.User, 'general.vimMode', newValue);
|
||||||
return newValue;
|
return newValue;
|
||||||
}, [vimEnabled, settings]);
|
}, [vimEnabled, settings]);
|
||||||
|
|
||||||
|
|||||||
@@ -1120,7 +1120,7 @@ describe('useSlashCommandProcessor', () => {
|
|||||||
|
|
||||||
// We should not see a change until we fire an event.
|
// We should not see a change until we fire an event.
|
||||||
await waitFor(() => expect(result.current.slashCommands).toEqual([]));
|
await waitFor(() => expect(result.current.slashCommands).toEqual([]));
|
||||||
await act(() => {
|
act(() => {
|
||||||
appEvents.emit('extensionsStarting');
|
appEvents.emit('extensionsStarting');
|
||||||
});
|
});
|
||||||
await waitFor(() =>
|
await waitFor(() =>
|
||||||
|
|||||||
@@ -140,9 +140,7 @@ describe('useFolderTrust', () => {
|
|||||||
});
|
});
|
||||||
|
|
||||||
await act(async () => {
|
await act(async () => {
|
||||||
await result.current.handleFolderTrustSelect(
|
result.current.handleFolderTrustSelect(FolderTrustChoice.TRUST_FOLDER);
|
||||||
FolderTrustChoice.TRUST_FOLDER,
|
|
||||||
);
|
|
||||||
});
|
});
|
||||||
|
|
||||||
await waitFor(() => {
|
await waitFor(() => {
|
||||||
|
|||||||
@@ -136,7 +136,7 @@ describe('useQuotaAndFallback', () => {
|
|||||||
mockGoogleApiError,
|
mockGoogleApiError,
|
||||||
1000 * 60 * 5,
|
1000 * 60 * 5,
|
||||||
); // 5 minutes
|
); // 5 minutes
|
||||||
await act(() => {
|
act(() => {
|
||||||
promise = handler('gemini-pro', 'gemini-flash', error);
|
promise = handler('gemini-pro', 'gemini-flash', error);
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -155,7 +155,7 @@ describe('useQuotaAndFallback', () => {
|
|||||||
expect(mockHistoryManager.addItem).not.toHaveBeenCalled();
|
expect(mockHistoryManager.addItem).not.toHaveBeenCalled();
|
||||||
|
|
||||||
// Simulate the user choosing to continue with the fallback model
|
// Simulate the user choosing to continue with the fallback model
|
||||||
await act(() => {
|
act(() => {
|
||||||
result.current.handleProQuotaChoice('retry_always');
|
result.current.handleProQuotaChoice('retry_always');
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -182,7 +182,7 @@ describe('useQuotaAndFallback', () => {
|
|||||||
.calls[0][0] as FallbackModelHandler;
|
.calls[0][0] as FallbackModelHandler;
|
||||||
|
|
||||||
let promise1: Promise<FallbackIntent | null>;
|
let promise1: Promise<FallbackIntent | null>;
|
||||||
await act(() => {
|
act(() => {
|
||||||
promise1 = handler(
|
promise1 = handler(
|
||||||
'gemini-pro',
|
'gemini-pro',
|
||||||
'gemini-flash',
|
'gemini-flash',
|
||||||
@@ -206,7 +206,7 @@ describe('useQuotaAndFallback', () => {
|
|||||||
expect(result2!).toBe('stop');
|
expect(result2!).toBe('stop');
|
||||||
expect(result.current.proQuotaRequest).toBe(firstRequest);
|
expect(result.current.proQuotaRequest).toBe(firstRequest);
|
||||||
|
|
||||||
await act(() => {
|
act(() => {
|
||||||
result.current.handleProQuotaChoice('retry_always');
|
result.current.handleProQuotaChoice('retry_always');
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -247,7 +247,7 @@ describe('useQuotaAndFallback', () => {
|
|||||||
.calls[0][0] as FallbackModelHandler;
|
.calls[0][0] as FallbackModelHandler;
|
||||||
|
|
||||||
let promise: Promise<FallbackIntent | null>;
|
let promise: Promise<FallbackIntent | null>;
|
||||||
await act(() => {
|
act(() => {
|
||||||
promise = handler('model-A', 'model-B', error);
|
promise = handler('model-A', 'model-B', error);
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -265,7 +265,7 @@ describe('useQuotaAndFallback', () => {
|
|||||||
);
|
);
|
||||||
|
|
||||||
// Simulate the user choosing to continue with the fallback model
|
// Simulate the user choosing to continue with the fallback model
|
||||||
await act(() => {
|
act(() => {
|
||||||
result.current.handleProQuotaChoice('retry_always');
|
result.current.handleProQuotaChoice('retry_always');
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -303,7 +303,7 @@ describe('useQuotaAndFallback', () => {
|
|||||||
let promise: Promise<FallbackIntent | null>;
|
let promise: Promise<FallbackIntent | null>;
|
||||||
const error = new ModelNotFoundError('model not found', 404);
|
const error = new ModelNotFoundError('model not found', 404);
|
||||||
|
|
||||||
await act(() => {
|
act(() => {
|
||||||
promise = handler('gemini-3-pro-preview', 'gemini-2.5-pro', error);
|
promise = handler('gemini-3-pro-preview', 'gemini-2.5-pro', error);
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -322,7 +322,7 @@ To disable Gemini 3, disable "Preview features" in /settings.`,
|
|||||||
);
|
);
|
||||||
|
|
||||||
// Simulate the user choosing to switch
|
// Simulate the user choosing to switch
|
||||||
await act(() => {
|
act(() => {
|
||||||
result.current.handleProQuotaChoice('retry_always');
|
result.current.handleProQuotaChoice('retry_always');
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -364,7 +364,7 @@ To disable Gemini 3, disable "Preview features" in /settings.`,
|
|||||||
const handler = setFallbackHandlerSpy.mock
|
const handler = setFallbackHandlerSpy.mock
|
||||||
.calls[0][0] as FallbackModelHandler;
|
.calls[0][0] as FallbackModelHandler;
|
||||||
let promise: Promise<FallbackIntent | null>;
|
let promise: Promise<FallbackIntent | null>;
|
||||||
await act(() => {
|
act(() => {
|
||||||
promise = handler(
|
promise = handler(
|
||||||
'gemini-pro',
|
'gemini-pro',
|
||||||
'gemini-flash',
|
'gemini-flash',
|
||||||
@@ -372,7 +372,7 @@ To disable Gemini 3, disable "Preview features" in /settings.`,
|
|||||||
);
|
);
|
||||||
});
|
});
|
||||||
|
|
||||||
await act(() => {
|
act(() => {
|
||||||
result.current.handleProQuotaChoice('retry_later');
|
result.current.handleProQuotaChoice('retry_later');
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -395,7 +395,7 @@ To disable Gemini 3, disable "Preview features" in /settings.`,
|
|||||||
.calls[0][0] as FallbackModelHandler;
|
.calls[0][0] as FallbackModelHandler;
|
||||||
|
|
||||||
let promise: Promise<FallbackIntent | null>;
|
let promise: Promise<FallbackIntent | null>;
|
||||||
await act(() => {
|
act(() => {
|
||||||
promise = handler(
|
promise = handler(
|
||||||
'gemini-pro',
|
'gemini-pro',
|
||||||
'gemini-flash',
|
'gemini-flash',
|
||||||
@@ -403,7 +403,7 @@ To disable Gemini 3, disable "Preview features" in /settings.`,
|
|||||||
);
|
);
|
||||||
});
|
});
|
||||||
|
|
||||||
await act(() => {
|
act(() => {
|
||||||
result.current.handleProQuotaChoice('retry_always');
|
result.current.handleProQuotaChoice('retry_always');
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -431,7 +431,7 @@ To disable Gemini 3, disable "Preview features" in /settings.`,
|
|||||||
const handler = setFallbackHandlerSpy.mock
|
const handler = setFallbackHandlerSpy.mock
|
||||||
.calls[0][0] as FallbackModelHandler;
|
.calls[0][0] as FallbackModelHandler;
|
||||||
let promise: Promise<FallbackIntent | null>;
|
let promise: Promise<FallbackIntent | null>;
|
||||||
await act(() => {
|
act(() => {
|
||||||
promise = handler(
|
promise = handler(
|
||||||
PREVIEW_GEMINI_MODEL,
|
PREVIEW_GEMINI_MODEL,
|
||||||
DEFAULT_GEMINI_MODEL,
|
DEFAULT_GEMINI_MODEL,
|
||||||
@@ -439,7 +439,7 @@ To disable Gemini 3, disable "Preview features" in /settings.`,
|
|||||||
);
|
);
|
||||||
});
|
});
|
||||||
|
|
||||||
await act(() => {
|
act(() => {
|
||||||
result.current.handleProQuotaChoice('retry_always');
|
result.current.handleProQuotaChoice('retry_always');
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -466,7 +466,7 @@ To disable Gemini 3, disable "Preview features" in /settings.`,
|
|||||||
const handler = setFallbackHandlerSpy.mock
|
const handler = setFallbackHandlerSpy.mock
|
||||||
.calls[0][0] as FallbackModelHandler;
|
.calls[0][0] as FallbackModelHandler;
|
||||||
let promise: Promise<FallbackIntent | null>;
|
let promise: Promise<FallbackIntent | null>;
|
||||||
await act(() => {
|
act(() => {
|
||||||
promise = handler(
|
promise = handler(
|
||||||
PREVIEW_GEMINI_MODEL,
|
PREVIEW_GEMINI_MODEL,
|
||||||
DEFAULT_GEMINI_FLASH_MODEL,
|
DEFAULT_GEMINI_FLASH_MODEL,
|
||||||
@@ -474,7 +474,7 @@ To disable Gemini 3, disable "Preview features" in /settings.`,
|
|||||||
);
|
);
|
||||||
});
|
});
|
||||||
|
|
||||||
await act(() => {
|
act(() => {
|
||||||
result.current.handleProQuotaChoice('retry_always');
|
result.current.handleProQuotaChoice('retry_always');
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|||||||
@@ -270,9 +270,7 @@ describe('AgentExecutor', () => {
|
|||||||
);
|
);
|
||||||
parentToolRegistry.registerTool(MOCK_TOOL_NOT_ALLOWED);
|
parentToolRegistry.registerTool(MOCK_TOOL_NOT_ALLOWED);
|
||||||
|
|
||||||
vi.spyOn(mockConfig, 'getToolRegistry').mockResolvedValue(
|
vi.spyOn(mockConfig, 'getToolRegistry').mockReturnValue(parentToolRegistry);
|
||||||
parentToolRegistry,
|
|
||||||
);
|
|
||||||
|
|
||||||
mockedGetDirectoryContextString.mockResolvedValue(
|
mockedGetDirectoryContextString.mockResolvedValue(
|
||||||
'Mocked Environment Context',
|
'Mocked Environment Context',
|
||||||
|
|||||||
@@ -106,7 +106,7 @@ export class AgentExecutor<TOutput extends z.ZodTypeAny> {
|
|||||||
): Promise<AgentExecutor<TOutput>> {
|
): Promise<AgentExecutor<TOutput>> {
|
||||||
// Create an isolated tool registry for this agent instance.
|
// Create an isolated tool registry for this agent instance.
|
||||||
const agentToolRegistry = new ToolRegistry(runtimeContext);
|
const agentToolRegistry = new ToolRegistry(runtimeContext);
|
||||||
const parentToolRegistry = await runtimeContext.getToolRegistry();
|
const parentToolRegistry = runtimeContext.getToolRegistry();
|
||||||
|
|
||||||
if (definition.toolConfig) {
|
if (definition.toolConfig) {
|
||||||
for (const toolRef of definition.toolConfig.tools) {
|
for (const toolRef of definition.toolConfig.tools) {
|
||||||
|
|||||||
@@ -189,7 +189,7 @@ describe('oauth2', () => {
|
|||||||
end: vi.fn(),
|
end: vi.fn(),
|
||||||
} as unknown as http.ServerResponse;
|
} as unknown as http.ServerResponse;
|
||||||
|
|
||||||
await requestCallback(mockReq, mockRes);
|
requestCallback(mockReq, mockRes);
|
||||||
|
|
||||||
const client = await clientPromise;
|
const client = await clientPromise;
|
||||||
expect(client).toBe(mockOAuth2Client);
|
expect(client).toBe(mockOAuth2Client);
|
||||||
@@ -203,7 +203,9 @@ describe('oauth2', () => {
|
|||||||
|
|
||||||
// Manually trigger the 'tokens' event listener
|
// Manually trigger the 'tokens' event listener
|
||||||
if (tokensListener) {
|
if (tokensListener) {
|
||||||
await tokensListener(mockTokens);
|
await (
|
||||||
|
tokensListener as unknown as (tokens: Credentials) => Promise<void>
|
||||||
|
)(mockTokens);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Verify Google Account was cached
|
// Verify Google Account was cached
|
||||||
@@ -575,9 +577,7 @@ describe('oauth2', () => {
|
|||||||
const mockExternalAccountClient = {
|
const mockExternalAccountClient = {
|
||||||
getAccessToken: vi.fn().mockResolvedValue({ token: 'byoid-token' }),
|
getAccessToken: vi.fn().mockResolvedValue({ token: 'byoid-token' }),
|
||||||
};
|
};
|
||||||
const mockFromJSON = vi
|
const mockFromJSON = vi.fn().mockReturnValue(mockExternalAccountClient);
|
||||||
.fn()
|
|
||||||
.mockResolvedValue(mockExternalAccountClient);
|
|
||||||
const mockGoogleAuthInstance = {
|
const mockGoogleAuthInstance = {
|
||||||
fromJSON: mockFromJSON,
|
fromJSON: mockFromJSON,
|
||||||
};
|
};
|
||||||
@@ -834,7 +834,7 @@ describe('oauth2', () => {
|
|||||||
} as unknown as http.ServerResponse;
|
} as unknown as http.ServerResponse;
|
||||||
|
|
||||||
await expect(async () => {
|
await expect(async () => {
|
||||||
await requestCallback(mockReq, mockRes);
|
requestCallback(mockReq, mockRes);
|
||||||
await clientPromise;
|
await clientPromise;
|
||||||
}).rejects.toThrow(
|
}).rejects.toThrow(
|
||||||
'Google OAuth error: access_denied. User denied access',
|
'Google OAuth error: access_denied. User denied access',
|
||||||
@@ -891,7 +891,7 @@ describe('oauth2', () => {
|
|||||||
} as unknown as http.ServerResponse;
|
} as unknown as http.ServerResponse;
|
||||||
|
|
||||||
await expect(async () => {
|
await expect(async () => {
|
||||||
await requestCallback(mockReq, mockRes);
|
requestCallback(mockReq, mockRes);
|
||||||
await clientPromise;
|
await clientPromise;
|
||||||
}).rejects.toThrow(
|
}).rejects.toThrow(
|
||||||
'Google OAuth error: server_error. No additional details provided',
|
'Google OAuth error: server_error. No additional details provided',
|
||||||
@@ -954,7 +954,7 @@ describe('oauth2', () => {
|
|||||||
} as unknown as http.ServerResponse;
|
} as unknown as http.ServerResponse;
|
||||||
|
|
||||||
await expect(async () => {
|
await expect(async () => {
|
||||||
await requestCallback(mockReq, mockRes);
|
requestCallback(mockReq, mockRes);
|
||||||
await clientPromise;
|
await clientPromise;
|
||||||
}).rejects.toThrow(
|
}).rejects.toThrow(
|
||||||
'Failed to exchange authorization code for tokens: Token exchange failed',
|
'Failed to exchange authorization code for tokens: Token exchange failed',
|
||||||
@@ -1038,7 +1038,7 @@ describe('oauth2', () => {
|
|||||||
end: vi.fn(),
|
end: vi.fn(),
|
||||||
} as unknown as http.ServerResponse;
|
} as unknown as http.ServerResponse;
|
||||||
|
|
||||||
await requestCallback(mockReq, mockRes);
|
requestCallback(mockReq, mockRes);
|
||||||
const client = await clientPromise;
|
const client = await clientPromise;
|
||||||
|
|
||||||
// Authentication should succeed even if fetchAndCacheUserInfo fails
|
// Authentication should succeed even if fetchAndCacheUserInfo fails
|
||||||
|
|||||||
@@ -120,7 +120,7 @@ async function initOauthClient(
|
|||||||
const auth = new GoogleAuth({
|
const auth = new GoogleAuth({
|
||||||
scopes: OAUTH_SCOPE,
|
scopes: OAUTH_SCOPE,
|
||||||
});
|
});
|
||||||
const byoidClient = await auth.fromJSON({
|
const byoidClient = auth.fromJSON({
|
||||||
...credentials,
|
...credentials,
|
||||||
refresh_token: credentials.refresh_token ?? undefined,
|
refresh_token: credentials.refresh_token ?? undefined,
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -304,12 +304,12 @@ describe('Gemini Client (client.ts)', () => {
|
|||||||
it('should create a new chat session, clearing the old history', async () => {
|
it('should create a new chat session, clearing the old history', async () => {
|
||||||
// 1. Get the initial chat instance and add some history.
|
// 1. Get the initial chat instance and add some history.
|
||||||
const initialChat = client.getChat();
|
const initialChat = client.getChat();
|
||||||
const initialHistory = await client.getHistory();
|
const initialHistory = client.getHistory();
|
||||||
await client.addHistory({
|
await client.addHistory({
|
||||||
role: 'user',
|
role: 'user',
|
||||||
parts: [{ text: 'some old message' }],
|
parts: [{ text: 'some old message' }],
|
||||||
});
|
});
|
||||||
const historyWithOldMessage = await client.getHistory();
|
const historyWithOldMessage = client.getHistory();
|
||||||
expect(historyWithOldMessage.length).toBeGreaterThan(
|
expect(historyWithOldMessage.length).toBeGreaterThan(
|
||||||
initialHistory.length,
|
initialHistory.length,
|
||||||
);
|
);
|
||||||
@@ -319,7 +319,7 @@ describe('Gemini Client (client.ts)', () => {
|
|||||||
|
|
||||||
// 3. Get the new chat instance and its history.
|
// 3. Get the new chat instance and its history.
|
||||||
const newChat = client.getChat();
|
const newChat = client.getChat();
|
||||||
const newHistory = await client.getHistory();
|
const newHistory = client.getHistory();
|
||||||
|
|
||||||
// 4. Assert that the chat instance is new and the history is reset.
|
// 4. Assert that the chat instance is new and the history is reset.
|
||||||
expect(newChat).not.toBe(initialChat);
|
expect(newChat).not.toBe(initialChat);
|
||||||
|
|||||||
@@ -540,7 +540,7 @@ export class GeminiClient {
|
|||||||
if (this.currentSequenceModel) {
|
if (this.currentSequenceModel) {
|
||||||
modelToUse = this.currentSequenceModel;
|
modelToUse = this.currentSequenceModel;
|
||||||
} else {
|
} else {
|
||||||
const router = await this.config.getModelRouterService();
|
const router = this.config.getModelRouterService();
|
||||||
const decision = await router.route(routingContext);
|
const decision = await router.route(routingContext);
|
||||||
modelToUse = decision.model;
|
modelToUse = decision.model;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -300,7 +300,7 @@ export async function initializeTelemetry(
|
|||||||
});
|
});
|
||||||
|
|
||||||
try {
|
try {
|
||||||
await sdk.start();
|
sdk.start();
|
||||||
if (config.getDebugMode()) {
|
if (config.getDebugMode()) {
|
||||||
debugLogger.log('OpenTelemetry SDK started successfully.');
|
debugLogger.log('OpenTelemetry SDK started successfully.');
|
||||||
}
|
}
|
||||||
@@ -355,7 +355,7 @@ export async function shutdownTelemetry(
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
await ClearcutLogger.getInstance()?.shutdown();
|
ClearcutLogger.getInstance()?.shutdown();
|
||||||
await sdk.shutdown();
|
await sdk.shutdown();
|
||||||
if (config.getDebugMode() && fromProcessExit) {
|
if (config.getDebugMode() && fromProcessExit) {
|
||||||
debugLogger.log('OpenTelemetry SDK shut down successfully.');
|
debugLogger.log('OpenTelemetry SDK shut down successfully.');
|
||||||
|
|||||||
@@ -149,7 +149,7 @@ describe('checkpoint utils', () => {
|
|||||||
] as ToolCallRequestInfo[];
|
] as ToolCallRequestInfo[];
|
||||||
|
|
||||||
(mockGitService.createFileSnapshot as Mock).mockResolvedValue('hash123');
|
(mockGitService.createFileSnapshot as Mock).mockResolvedValue('hash123');
|
||||||
(mockGeminiClient.getHistory as Mock).mockResolvedValue([
|
(mockGeminiClient.getHistory as Mock).mockReturnValue([
|
||||||
{ role: 'user', parts: [] },
|
{ role: 'user', parts: [] },
|
||||||
]);
|
]);
|
||||||
|
|
||||||
|
|||||||
@@ -125,7 +125,7 @@ export async function processRestorableToolCalls<HistoryType>(
|
|||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
const clientHistory = await geminiClient.getHistory();
|
const clientHistory = geminiClient.getHistory();
|
||||||
const checkpointData: ToolCallData<HistoryType> = {
|
const checkpointData: ToolCallData<HistoryType> = {
|
||||||
history,
|
history,
|
||||||
clientHistory,
|
clientHistory,
|
||||||
|
|||||||
@@ -237,7 +237,7 @@ describe('editCorrector', () => {
|
|||||||
mockGeminiClientInstance = new GeminiClient(
|
mockGeminiClientInstance = new GeminiClient(
|
||||||
mockConfigInstance,
|
mockConfigInstance,
|
||||||
) as Mocked<GeminiClient>;
|
) as Mocked<GeminiClient>;
|
||||||
mockGeminiClientInstance.getHistory = vi.fn().mockResolvedValue([]);
|
mockGeminiClientInstance.getHistory = vi.fn().mockReturnValue([]);
|
||||||
mockBaseLlmClientInstance = {
|
mockBaseLlmClientInstance = {
|
||||||
generateJson: mockGenerateJson,
|
generateJson: mockGenerateJson,
|
||||||
config: {
|
config: {
|
||||||
@@ -606,9 +606,7 @@ describe('editCorrector', () => {
|
|||||||
],
|
],
|
||||||
},
|
},
|
||||||
];
|
];
|
||||||
(mockGeminiClientInstance.getHistory as Mock).mockResolvedValue(
|
(mockGeminiClientInstance.getHistory as Mock).mockReturnValue(history);
|
||||||
history,
|
|
||||||
);
|
|
||||||
|
|
||||||
const result = await ensureCorrectEdit(
|
const result = await ensureCorrectEdit(
|
||||||
filePath,
|
filePath,
|
||||||
|
|||||||
@@ -90,7 +90,7 @@ async function findLastEditTimestamp(
|
|||||||
filePath: string,
|
filePath: string,
|
||||||
client: GeminiClient,
|
client: GeminiClient,
|
||||||
): Promise<number> {
|
): Promise<number> {
|
||||||
const history = (await client.getHistory()) ?? [];
|
const history = client.getHistory() ?? [];
|
||||||
|
|
||||||
// Tools that may reference the file path in their FunctionResponse `output`.
|
// Tools that may reference the file path in their FunctionResponse `output`.
|
||||||
const toolsInResp = new Set([
|
const toolsInResp = new Set([
|
||||||
|
|||||||
Reference in New Issue
Block a user