@aws/lsp-codewhisperer 0.0.62 → 0.0.63
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +32 -0
- package/out/language-server/agenticChat/agenticChatController.d.ts +3 -2
- package/out/language-server/agenticChat/agenticChatController.js +96 -26
- package/out/language-server/agenticChat/agenticChatController.js.map +1 -1
- package/out/language-server/agenticChat/constants/constants.d.ts +9 -0
- package/out/language-server/agenticChat/constants/constants.js +16 -0
- package/out/language-server/agenticChat/constants/constants.js.map +1 -0
- package/out/language-server/agenticChat/constants/modelSelection.d.ts +7 -0
- package/out/language-server/agenticChat/constants/modelSelection.js +21 -0
- package/out/language-server/agenticChat/constants/modelSelection.js.map +1 -0
- package/out/language-server/agenticChat/context/additionalContextProvider.d.ts +5 -0
- package/out/language-server/agenticChat/context/additionalContextProvider.js +52 -13
- package/out/language-server/agenticChat/context/additionalContextProvider.js.map +1 -1
- package/out/language-server/agenticChat/context/contextCommandsProvider.js +1 -1
- package/out/language-server/agenticChat/context/contextCommandsProvider.js.map +1 -1
- package/out/language-server/agenticChat/qAgenticChatServer.js +3 -0
- package/out/language-server/agenticChat/qAgenticChatServer.js.map +1 -1
- package/out/language-server/agenticChat/tools/mcp/chokidarFileWatcher.d.ts +8 -0
- package/out/language-server/agenticChat/tools/mcp/chokidarFileWatcher.js +47 -0
- package/out/language-server/agenticChat/tools/mcp/chokidarFileWatcher.js.map +1 -0
- package/out/language-server/agenticChat/tools/mcp/mcpEventHandler.d.ts +4 -0
- package/out/language-server/agenticChat/tools/mcp/mcpEventHandler.js +87 -8
- package/out/language-server/agenticChat/tools/mcp/mcpEventHandler.js.map +1 -1
- package/out/language-server/agenticChat/tools/toolServer.js +1 -1
- package/out/language-server/agenticChat/tools/toolServer.js.map +1 -1
- package/out/language-server/agenticChat/utils/agenticChatControllerHelper.d.ts +8 -0
- package/out/language-server/agenticChat/utils/agenticChatControllerHelper.js +15 -0
- package/out/language-server/agenticChat/utils/agenticChatControllerHelper.js.map +1 -0
- package/out/language-server/agenticChat/utils/pathValidation.d.ts +21 -0
- package/out/language-server/agenticChat/utils/pathValidation.js +44 -0
- package/out/language-server/agenticChat/utils/pathValidation.js.map +1 -0
- package/out/language-server/chat/chatController.d.ts +1 -1
- package/out/language-server/chat/chatController.js.map +1 -1
- package/out/language-server/chat/telemetry/chatTelemetryController.d.ts +1 -1
- package/out/language-server/chat/telemetry/chatTelemetryController.js +2 -1
- package/out/language-server/chat/telemetry/chatTelemetryController.js.map +1 -1
- package/out/language-server/inline-completion/codeWhispererServer.js +53 -29
- package/out/language-server/inline-completion/codeWhispererServer.js.map +1 -1
- package/out/language-server/localProjectContext/localProjectContextServer.js +21 -5
- package/out/language-server/localProjectContext/localProjectContextServer.js.map +1 -1
- package/out/language-server/netTransform/artifactManager.d.ts +4 -1
- package/out/language-server/netTransform/artifactManager.js +53 -2
- package/out/language-server/netTransform/artifactManager.js.map +1 -1
- package/out/language-server/netTransform/models.d.ts +32 -2
- package/out/language-server/netTransform/models.js.map +1 -1
- package/out/language-server/netTransform/tests/mockData.js +1 -1
- package/out/language-server/netTransform/tests/mockData.js.map +1 -1
- package/out/language-server/workspaceContext/dependency/dependencyEventBundler.d.ts +3 -3
- package/out/language-server/workspaceContext/dependency/dependencyEventBundler.js +3 -3
- package/out/language-server/workspaceContext/dependency/dependencyHandler/JSTSDependencyHandler.js +1 -2
- package/out/language-server/workspaceContext/dependency/dependencyHandler/JSTSDependencyHandler.js.map +1 -1
- package/out/language-server/workspaceContext/dependency/dependencyHandler/JavaDependencyHandler.js +1 -2
- package/out/language-server/workspaceContext/dependency/dependencyHandler/JavaDependencyHandler.js.map +1 -1
- package/out/language-server/workspaceContext/dependency/dependencyHandler/LanguageDependencyHandler.d.ts +5 -6
- package/out/language-server/workspaceContext/dependency/dependencyHandler/LanguageDependencyHandler.js +17 -27
- package/out/language-server/workspaceContext/dependency/dependencyHandler/LanguageDependencyHandler.js.map +1 -1
- package/out/language-server/workspaceContext/dependency/dependencyHandler/PythonDependencyHandler.js +1 -2
- package/out/language-server/workspaceContext/dependency/dependencyHandler/PythonDependencyHandler.js.map +1 -1
- package/out/language-server/workspaceContext/util.js +3 -1
- package/out/language-server/workspaceContext/util.js.map +1 -1
- package/out/language-server/workspaceContext/workspaceContextServer.js +21 -10
- package/out/language-server/workspaceContext/workspaceContextServer.js.map +1 -1
- package/out/language-server/workspaceContext/workspaceFolderManager.d.ts +1 -2
- package/out/language-server/workspaceContext/workspaceFolderManager.js +24 -30
- package/out/language-server/workspaceContext/workspaceFolderManager.js.map +1 -1
- package/out/shared/constants.d.ts +1 -0
- package/out/shared/constants.js +2 -1
- package/out/shared/constants.js.map +1 -1
- package/out/shared/imageVerification.d.ts +1 -0
- package/out/shared/imageVerification.js +3 -2
- package/out/shared/imageVerification.js.map +1 -1
- package/out/shared/languageDetection.js +1 -1
- package/out/shared/languageDetection.js.map +1 -1
- package/out/shared/streamingClientService.js +2 -2
- package/out/shared/streamingClientService.js.map +1 -1
- package/out/shared/telemetry/telemetryService.js +1 -2
- package/out/shared/telemetry/telemetryService.js.map +1 -1
- package/package.json +1 -1
- package/out/language-server/agenticChat/constants.d.ts +0 -8
- package/out/language-server/agenticChat/constants.js +0 -12
- package/out/language-server/agenticChat/constants.js.map +0 -1
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,37 @@
|
|
|
1
1
|
# Changelog
|
|
2
2
|
|
|
3
|
+
## [0.0.63](https://github.com/aws/language-servers/compare/lsp-codewhisperer/v0.0.62...lsp-codewhisperer/v0.0.63) (2025-07-08)
|
|
4
|
+
|
|
5
|
+
|
|
6
|
+
### Features
|
|
7
|
+
|
|
8
|
+
* added file watchers to listen to mcp and persona config ([#1714](https://github.com/aws/language-servers/issues/1714)) ([4c5a7f8](https://github.com/aws/language-servers/commit/4c5a7f893bad37bea1946d37d06f57197c3ef04b))
|
|
9
|
+
* adding streakLength back for UserTriggerDecisionEvent ([#1841](https://github.com/aws/language-servers/issues/1841)) ([7052132](https://github.com/aws/language-servers/commit/7052132a5198944ef05ddbf857d622ba518e71da))
|
|
10
|
+
* **amazonq:** add transformation preferences functionality to input gen ([#1792](https://github.com/aws/language-servers/issues/1792)) ([095f737](https://github.com/aws/language-servers/commit/095f737b86e6234b2568c6d4deafbbb90967bdbc))
|
|
11
|
+
* **amazonq:** update workspace context server A/B testing filter ([#1830](https://github.com/aws/language-servers/issues/1830)) ([faeeee3](https://github.com/aws/language-servers/commit/faeeee3da7a8712f3501055ba8d485528185cdb6))
|
|
12
|
+
* **flags:** change flag name to enablewebformtransform([#1804](https://github.com/aws/language-servers/issues/1804)) ([3b6c3be](https://github.com/aws/language-servers/commit/3b6c3be7630248cd00c19c16637f016d799ef8d1))
|
|
13
|
+
* passing partialResultToken to onInlineCompletionHandler result for EDITS ([#1840](https://github.com/aws/language-servers/issues/1840)) ([270d5a3](https://github.com/aws/language-servers/commit/270d5a3c5adba6b49d938f310ac89ae9b7fbc401))
|
|
14
|
+
* support listAvailableModels server request ([#1808](https://github.com/aws/language-servers/issues/1808)) ([9f1ddb3](https://github.com/aws/language-servers/commit/9f1ddb327778dba6da49337b79c5fef19023b52d))
|
|
15
|
+
|
|
16
|
+
|
|
17
|
+
### Bug Fixes
|
|
18
|
+
|
|
19
|
+
* adding agenticcoding field to amazonqaddMessage metric([#1849](https://github.com/aws/language-servers/issues/1849)) ([d677c52](https://github.com/aws/language-servers/commit/d677c52c6139859bc0f2dd8e7ffe6a85b87db3f6))
|
|
20
|
+
* adding files on VSC windows properly triggers reindexing ([#1820](https://github.com/aws/language-servers/issues/1820)) ([0c2d8eb](https://github.com/aws/language-servers/commit/0c2d8eb7dd875dfe86d1b2d094ec53a2a1221b97))
|
|
21
|
+
* **amazonq:** allow taking .jpg file as image context, add image cont… ([#1814](https://github.com/aws/language-servers/issues/1814)) ([4d36fa4](https://github.com/aws/language-servers/commit/4d36fa4a0a04692dba720bc0288c6cee7f45a1fc))
|
|
22
|
+
* **amazonq:** change the customer UI message to out of the workspace ([#1822](https://github.com/aws/language-servers/issues/1822)) ([624def5](https://github.com/aws/language-servers/commit/624def51e4d9e21ee8d045ffe528455b69cdfecb))
|
|
23
|
+
* **amazonq:** change the image filter used in open file dialog ([#1838](https://github.com/aws/language-servers/issues/1838)) ([d9da4cb](https://github.com/aws/language-servers/commit/d9da4cbb7b1995ef43aaba1b7e67d26fd61a3c57))
|
|
24
|
+
* **amazonq:** fix to add upper limit validation for tool description ([#1760](https://github.com/aws/language-servers/issues/1760)) ([2d18a3b](https://github.com/aws/language-servers/commit/2d18a3ba69d22b26dea5170656d79b9eacc202b1))
|
|
25
|
+
* **amazonq:** fix typo in image context list ([#1836](https://github.com/aws/language-servers/issues/1836)) ([179b553](https://github.com/aws/language-servers/commit/179b553a1444201e696fd52e7705dc0c05154eab))
|
|
26
|
+
* **amazonq:** handle undefined paths gracefully and retry ([#1825](https://github.com/aws/language-servers/issues/1825)) ([c52b017](https://github.com/aws/language-servers/commit/c52b017eef0666433cbb0b6d8086254dc1af5fee))
|
|
27
|
+
* **amazonq:** include tsx and jsx files in workspace context server ([#1790](https://github.com/aws/language-servers/issues/1790)) ([79691ef](https://github.com/aws/language-servers/commit/79691ef607d9bc98032fe2e59a5031601a4dba9a))
|
|
28
|
+
* **amazonq:** make workspace context server upload dependency chunks sequentially ([#1769](https://github.com/aws/language-servers/issues/1769)) ([c8329e6](https://github.com/aws/language-servers/commit/c8329e6b90be2c24d72a4525b8903384746de2ab))
|
|
29
|
+
* **amazonq:** prevent WCS matching workspaceFolder with only prefix ([#1782](https://github.com/aws/language-servers/issues/1782)) ([988d952](https://github.com/aws/language-servers/commit/988d952485b0f026200a19d17cacd323cd9e359e))
|
|
30
|
+
* **amazonq:** shouldn't exit inline flow before we're sure there is no Edit/Completion trigger ([#1819](https://github.com/aws/language-servers/issues/1819)) ([dc8d89b](https://github.com/aws/language-servers/commit/dc8d89b39ee230aba6cfb032f81bda3476a5cc84))
|
|
31
|
+
* imagecontext image name bug, mutliple images in pinned context ([#1834](https://github.com/aws/language-servers/issues/1834)) ([27d60ab](https://github.com/aws/language-servers/commit/27d60ab5f5249635a9e73be1ee96ecb820133f9a))
|
|
32
|
+
* remove redundent thinking... for file operations ([#1839](https://github.com/aws/language-servers/issues/1839)) ([0078602](https://github.com/aws/language-servers/commit/00786023c9c257c9bb8066c36715864b32b4e069))
|
|
33
|
+
* should always trigger EDIT suggestion if triggering via acceptance ([#1826](https://github.com/aws/language-servers/issues/1826)) ([6c9e522](https://github.com/aws/language-servers/commit/6c9e5225a58d7cf43931d84e7ae63275d6f9c066))
|
|
34
|
+
|
|
3
35
|
## [0.0.62](https://github.com/aws/language-servers/compare/lsp-codewhisperer/v0.0.61...lsp-codewhisperer/v0.0.62) (2025-07-02)
|
|
4
36
|
|
|
5
37
|
|
|
@@ -4,7 +4,7 @@
|
|
|
4
4
|
*/
|
|
5
5
|
import { ToolUse } from '@amzn/codewhisperer-streaming';
|
|
6
6
|
import { ChatCommandInput } from '../../shared/streamingClientService';
|
|
7
|
-
import { Status, ButtonClickParams, ButtonClickResult, InlineChatResultParams, PromptInputOptionChangeParams, RuleClickParams, ListRulesParams, ActiveEditorChangedParams, PinnedContextParams, ExecuteCommandParams, FollowUpClickParams, OpenFileDialogParams, OpenFileDialogResult } from '@aws/language-server-runtimes/protocol';
|
|
7
|
+
import { Status, ButtonClickParams, ButtonClickResult, InlineChatResultParams, PromptInputOptionChangeParams, RuleClickParams, ListRulesParams, ActiveEditorChangedParams, PinnedContextParams, ExecuteCommandParams, FollowUpClickParams, ListAvailableModelsParams, ListAvailableModelsResult, OpenFileDialogParams, OpenFileDialogResult } from '@aws/language-server-runtimes/protocol';
|
|
8
8
|
import { FeedbackParams, InsertToCursorPositionParams, InlineChatParams, ConversationClickParams, ListConversationsParams, ListMcpServersParams, McpServerClickParams, TabBarActionParams, CreatePromptParams, FileClickParams } from '@aws/language-server-runtimes/protocol';
|
|
9
9
|
import { CancellationToken, Chat, ChatParams, ChatResult, EndChatParams, QuickActionParams, ResponseError, TabAddParams, TabRemoveParams, TabChangeParams, InlineChatResult } from '@aws/language-server-runtimes/server-interface';
|
|
10
10
|
import { Features, LspHandlers } from '../types';
|
|
@@ -16,7 +16,7 @@ import { ChatSessionService } from '../chat/chatSessionService';
|
|
|
16
16
|
import { AgenticChatResultStream } from './agenticChatResultStream';
|
|
17
17
|
import { AdditionalContentEntryAddition } from './context/agenticChatTriggerContext';
|
|
18
18
|
import { PaidTierMode } from '../paidTier/paidTier';
|
|
19
|
-
type ChatHandlers = Omit<LspHandlers<Chat>, 'openTab' | 'sendChatUpdate' | 'sendContextCommands' | 'onListConversations' | 'onConversationClick' | 'onListMcpServers' | 'onMcpServerClick' | 'onTabBarAction' | 'getSerializedChat' | 'chatOptionsUpdate' | '
|
|
19
|
+
type ChatHandlers = Omit<LspHandlers<Chat>, 'openTab' | 'sendChatUpdate' | 'sendContextCommands' | 'onListConversations' | 'onConversationClick' | 'onListMcpServers' | 'onMcpServerClick' | 'onTabBarAction' | 'getSerializedChat' | 'chatOptionsUpdate' | 'onListRules' | 'sendPinnedContext' | 'onActiveEditorChanged' | 'onPinnedContextAdd' | 'onPinnedContextRemove' | 'onOpenFileDialog' | 'onListAvailableModels'>;
|
|
20
20
|
export declare class AgenticChatController implements ChatHandlers {
|
|
21
21
|
#private;
|
|
22
22
|
constructor(chatSessionManagementService: ChatSessionManagementService, features: Features, telemetryService: TelemetryService, serviceManager?: AmazonQBaseServiceManager);
|
|
@@ -42,6 +42,7 @@ export declare class AgenticChatController implements ChatHandlers {
|
|
|
42
42
|
list: import("@aws/language-server-runtimes/protocol").DetailedListGroup[];
|
|
43
43
|
}>;
|
|
44
44
|
onMcpServerClick(params: McpServerClickParams): Promise<any>;
|
|
45
|
+
onListAvailableModels(params: ListAvailableModelsParams): Promise<ListAvailableModelsResult>;
|
|
45
46
|
onChatPrompt(params: ChatParams, token: CancellationToken): Promise<ChatResult | ResponseError<ChatResult>>;
|
|
46
47
|
truncatePinnedContext(remainingCharacterBudget: number, pinnedContext?: AdditionalContentEntryAddition[]): number;
|
|
47
48
|
/**
|
|
@@ -38,12 +38,13 @@ const listDirectory_1 = require("./tools/listDirectory");
|
|
|
38
38
|
const fsWrite_1 = require("./tools/fsWrite");
|
|
39
39
|
const executeBash_1 = require("./tools/executeBash");
|
|
40
40
|
const toolShared_1 = require("./tools/toolShared");
|
|
41
|
+
const pathValidation_1 = require("./utils/pathValidation");
|
|
41
42
|
const grepSearch_1 = require("./tools/grepSearch");
|
|
42
43
|
const fileSearch_1 = require("./tools/fileSearch");
|
|
43
44
|
const fsReplace_1 = require("./tools/fsReplace");
|
|
44
45
|
const lsp_core_2 = require("@aws/lsp-core");
|
|
45
46
|
const diff_1 = require("diff");
|
|
46
|
-
const constants_2 = require("./constants");
|
|
47
|
+
const constants_2 = require("./constants/constants");
|
|
47
48
|
const errors_2 = require("./errors");
|
|
48
49
|
const vscode_uri_1 = require("vscode-uri");
|
|
49
50
|
const executeBash_2 = require("./tools/executeBash");
|
|
@@ -54,8 +55,10 @@ const mcpManager_1 = require("./tools/mcp/mcpManager");
|
|
|
54
55
|
const mcpTool_1 = require("./tools/mcp/mcpTool");
|
|
55
56
|
const paidTier_1 = require("../paidTier/paidTier");
|
|
56
57
|
const util_1 = require("./tools/chatDb/util");
|
|
58
|
+
const modelSelection_1 = require("./constants/modelSelection");
|
|
57
59
|
const imageVerification_1 = require("../../shared/imageVerification");
|
|
58
60
|
const path_1 = require("@aws/lsp-core/out/util/path");
|
|
61
|
+
const agenticChatControllerHelper_1 = require("./utils/agenticChatControllerHelper");
|
|
59
62
|
class AgenticChatController {
|
|
60
63
|
#features;
|
|
61
64
|
#chatSessionManagementService;
|
|
@@ -267,7 +270,7 @@ class AgenticChatController {
|
|
|
267
270
|
if (params.fileType === 'image') {
|
|
268
271
|
// 1. Prompt user for file selection
|
|
269
272
|
const supportedExtensions = imageVerification_1.DEFAULT_IMAGE_VERIFICATION_OPTIONS.supportedExtensions;
|
|
270
|
-
const filters = { 'Image Files': supportedExtensions
|
|
273
|
+
const filters = { 'Image Files': supportedExtensions };
|
|
271
274
|
const result = await this.#features.lsp.window.showOpenDialog({
|
|
272
275
|
canSelectFiles: true,
|
|
273
276
|
canSelectFolders: false,
|
|
@@ -287,7 +290,7 @@ class AgenticChatController {
|
|
|
287
290
|
let errorMessage;
|
|
288
291
|
for (const filePath of result.uris) {
|
|
289
292
|
// Extract filename from the URI for error messages
|
|
290
|
-
const fileName =
|
|
293
|
+
const fileName = path.basename(filePath) || '';
|
|
291
294
|
const sanitizedPath = (0, path_1.sanitize)(filePath);
|
|
292
295
|
// Get file size and content for verification
|
|
293
296
|
const size = await this.#features.workspace.fs.getFileSize(sanitizedPath);
|
|
@@ -363,6 +366,7 @@ class AgenticChatController {
|
|
|
363
366
|
this.#chatHistoryDb.close();
|
|
364
367
|
this.#contextCommandsProvider?.dispose();
|
|
365
368
|
this.#userWrittenCodeTracker?.dispose();
|
|
369
|
+
this.#mcpEventHandler.dispose();
|
|
366
370
|
}
|
|
367
371
|
async onListConversations(params) {
|
|
368
372
|
return this.#tabBarController.onListConversations(params);
|
|
@@ -382,6 +386,28 @@ class AgenticChatController {
|
|
|
382
386
|
async onMcpServerClick(params) {
|
|
383
387
|
return this.#mcpEventHandler.onMcpServerClick(params);
|
|
384
388
|
}
|
|
389
|
+
async onListAvailableModels(params) {
|
|
390
|
+
const region = AmazonQTokenServiceManager_1.AmazonQTokenServiceManager.getInstance().getRegion();
|
|
391
|
+
const models = region && modelSelection_1.MODEL_OPTIONS_FOR_REGION[region] ? modelSelection_1.MODEL_OPTIONS_FOR_REGION[region] : modelSelection_1.MODEL_OPTIONS;
|
|
392
|
+
const sessionResult = this.#chatSessionManagementService.getSession(params.tabId);
|
|
393
|
+
const { data: session, success } = sessionResult;
|
|
394
|
+
if (!success) {
|
|
395
|
+
return {
|
|
396
|
+
tabId: params.tabId,
|
|
397
|
+
models: models,
|
|
398
|
+
};
|
|
399
|
+
}
|
|
400
|
+
const savedModelId = this.#chatHistoryDb.getModelId();
|
|
401
|
+
const selectedModelId = savedModelId && models.some(model => model.id === savedModelId)
|
|
402
|
+
? savedModelId
|
|
403
|
+
: (0, agenticChatControllerHelper_1.getLatestAvailableModel)(region).id;
|
|
404
|
+
session.modelId = selectedModelId;
|
|
405
|
+
return {
|
|
406
|
+
tabId: params.tabId,
|
|
407
|
+
models: models,
|
|
408
|
+
selectedModelId: selectedModelId,
|
|
409
|
+
};
|
|
410
|
+
}
|
|
385
411
|
async #sendProgressToClient(chunk, partialResultToken) {
|
|
386
412
|
if (!(0, utils_2.isNullish)(partialResultToken)) {
|
|
387
413
|
await this.#features.lsp.sendProgress(protocol_1.chatRequestType, partialResultToken, chunk);
|
|
@@ -433,6 +459,9 @@ class AgenticChatController {
|
|
|
433
459
|
await chatResultStream.updateOngoingProgressResult('Canceled');
|
|
434
460
|
// Finally, send telemetry/metrics
|
|
435
461
|
this.#telemetryController.emitInteractWithAgenticChat('StopChat', params.tabId, session.pairProgrammingMode, session.getConversationType());
|
|
462
|
+
metric.setDimension('languageServerVersion', this.#features.runtime.serverInfo.version);
|
|
463
|
+
metric.setDimension('codewhispererCustomizationArn', this.#customizationArn);
|
|
464
|
+
metric.setDimension('enabled', session.pairProgrammingMode);
|
|
436
465
|
await this.#telemetryController.emitAddMessageMetric(params.tabId, metric.metric, 'Cancelled');
|
|
437
466
|
});
|
|
438
467
|
session.setConversationType('AgenticChat');
|
|
@@ -455,6 +484,8 @@ class AgenticChatController {
|
|
|
455
484
|
const contextItems = [...additionalContext, ...activeFile];
|
|
456
485
|
triggerContext.documentReference = this.#additionalContextProvider.getFileListFromContext(contextItems);
|
|
457
486
|
const customContext = await this.#additionalContextProvider.getImageBlocksFromContext(params.context, params.tabId);
|
|
487
|
+
// Add image context to triggerContext.documentReference for transparency
|
|
488
|
+
await this.#additionalContextProvider.appendCustomContextToTriggerContext(triggerContext, params.context, params.tabId);
|
|
458
489
|
// Get the initial request input
|
|
459
490
|
const initialRequestInput = await this.#prepareRequestInput(params, session, triggerContext, additionalContext, chatResultStream, customContext);
|
|
460
491
|
// Generate a unique ID for this prompt
|
|
@@ -593,7 +624,7 @@ class AgenticChatController {
|
|
|
593
624
|
this.#debug(`LLM Response Latency: ${llmLatency}`);
|
|
594
625
|
// This is needed to handle the case where the response stream times out
|
|
595
626
|
// and we want to auto-retry
|
|
596
|
-
if (!result.success && result.error.startsWith(constants_2.
|
|
627
|
+
if (!result.success && result.error.startsWith(constants_2.RESPONSE_TIMEOUT_PARTIAL_MSG)) {
|
|
597
628
|
const content = 'You took too long to respond - try to split up the work into smaller steps. Do not apologize.';
|
|
598
629
|
if (this.#isPromptCanceled(token, session, promptId)) {
|
|
599
630
|
// Only skip adding message to the history DB, continue executing to avoid unexpected stop for the conversation
|
|
@@ -648,7 +679,7 @@ class AgenticChatController {
|
|
|
648
679
|
if (pendingToolUses.length === 0) {
|
|
649
680
|
this.recordChunk('agent_loop_done');
|
|
650
681
|
// No more tool uses, we're done
|
|
651
|
-
this.#telemetryController.emitAgencticLoop_InvokeLLM(response.$metadata.requestId, conversationId, 'AgenticChat', undefined, undefined, 'Succeeded', this.#features.runtime.serverInfo.version ?? '', llmLatency, this.#toolCallLatencies, this.#timeToFirstChunk, this.#timeBetweenChunks, session.pairProgrammingMode);
|
|
682
|
+
this.#telemetryController.emitAgencticLoop_InvokeLLM(response.$metadata.requestId, conversationId, 'AgenticChat', undefined, undefined, 'Succeeded', this.#features.runtime.serverInfo.version ?? '', session.modelId, llmLatency, this.#toolCallLatencies, this.#timeToFirstChunk, this.#timeBetweenChunks, session.pairProgrammingMode);
|
|
652
683
|
finalResult = result;
|
|
653
684
|
break;
|
|
654
685
|
}
|
|
@@ -669,7 +700,7 @@ class AgenticChatController {
|
|
|
669
700
|
metric.setDimension('requestIds', metric.metric.requestIds);
|
|
670
701
|
const toolNames = this.#toolUseLatencies.map(item => item.toolName);
|
|
671
702
|
const toolUseIds = this.#toolUseLatencies.map(item => item.toolUseId);
|
|
672
|
-
this.#telemetryController.emitAgencticLoop_InvokeLLM(response.$metadata.requestId, conversationId, 'AgenticChatWithToolUse', toolNames ?? undefined, toolUseIds ?? undefined, 'Succeeded', this.#features.runtime.serverInfo.version ?? '', llmLatency, this.#toolCallLatencies, this.#timeToFirstChunk, this.#timeBetweenChunks, session.pairProgrammingMode);
|
|
703
|
+
this.#telemetryController.emitAgencticLoop_InvokeLLM(response.$metadata.requestId, conversationId, 'AgenticChatWithToolUse', toolNames ?? undefined, toolUseIds ?? undefined, 'Succeeded', this.#features.runtime.serverInfo.version ?? '', session.modelId, llmLatency, this.#toolCallLatencies, this.#timeToFirstChunk, this.#timeBetweenChunks, session.pairProgrammingMode);
|
|
673
704
|
}
|
|
674
705
|
else {
|
|
675
706
|
// Send an error card to UI?
|
|
@@ -678,7 +709,7 @@ class AgenticChatController {
|
|
|
678
709
|
status: codewhisperer_streaming_1.ToolResultStatus.ERROR,
|
|
679
710
|
content: [{ text: result.error }],
|
|
680
711
|
}));
|
|
681
|
-
this.#telemetryController.emitAgencticLoop_InvokeLLM(response.$metadata.requestId, conversationId, 'AgenticChatWithToolUse', undefined, undefined, 'Failed', this.#features.runtime.serverInfo.version ?? '', llmLatency, this.#toolCallLatencies, this.#timeToFirstChunk, this.#timeBetweenChunks, session.pairProgrammingMode);
|
|
712
|
+
this.#telemetryController.emitAgencticLoop_InvokeLLM(response.$metadata.requestId, conversationId, 'AgenticChatWithToolUse', undefined, undefined, 'Failed', this.#features.runtime.serverInfo.version ?? '', session.modelId, llmLatency, this.#toolCallLatencies, this.#timeToFirstChunk, this.#timeBetweenChunks, session.pairProgrammingMode);
|
|
682
713
|
if (result.error.startsWith('ToolUse input is invalid JSON:')) {
|
|
683
714
|
content =
|
|
684
715
|
'Your toolUse input is incomplete, try again. If the error happens consistently, break this task down into multiple tool uses with smaller input. Do not apologize.';
|
|
@@ -724,7 +755,7 @@ class AgenticChatController {
|
|
|
724
755
|
*/
|
|
725
756
|
truncateRequest(request, pinnedContext) {
|
|
726
757
|
// TODO: Confirm if this limit applies to SendMessage and rename this constant
|
|
727
|
-
let remainingCharacterBudget = constants_2.
|
|
758
|
+
let remainingCharacterBudget = constants_2.GENERATE_ASSISTANT_RESPONSE_INPUT_LIMIT;
|
|
728
759
|
if (!request?.conversationState?.currentMessage?.userInputMessage) {
|
|
729
760
|
return remainingCharacterBudget;
|
|
730
761
|
}
|
|
@@ -732,9 +763,9 @@ class AgenticChatController {
|
|
|
732
763
|
// 1. prioritize user input message
|
|
733
764
|
let truncatedUserInputMessage = '';
|
|
734
765
|
if (message) {
|
|
735
|
-
if (message.length > constants_2.
|
|
736
|
-
this.#debug(`Truncating userInputMessage to ${constants_2.
|
|
737
|
-
truncatedUserInputMessage = message.substring(0, constants_2.
|
|
766
|
+
if (message.length > constants_2.GENERATE_ASSISTANT_RESPONSE_INPUT_LIMIT) {
|
|
767
|
+
this.#debug(`Truncating userInputMessage to ${constants_2.GENERATE_ASSISTANT_RESPONSE_INPUT_LIMIT} characters}`);
|
|
768
|
+
truncatedUserInputMessage = message.substring(0, constants_2.GENERATE_ASSISTANT_RESPONSE_INPUT_LIMIT);
|
|
738
769
|
remainingCharacterBudget = remainingCharacterBudget - truncatedUserInputMessage.length;
|
|
739
770
|
request.conversationState.currentMessage.userInputMessage.content = truncatedUserInputMessage;
|
|
740
771
|
}
|
|
@@ -1135,7 +1166,7 @@ class AgenticChatController {
|
|
|
1135
1166
|
#shouldSendBackErrorContent(toolResult) {
|
|
1136
1167
|
if (toolResult.status === codewhisperer_streaming_1.ToolResultStatus.ERROR) {
|
|
1137
1168
|
for (const content of toolResult.content ?? []) {
|
|
1138
|
-
if (content.json && JSON.stringify(content.json).includes(constants_2.
|
|
1169
|
+
if (content.json && JSON.stringify(content.json).includes(constants_2.OUTPUT_LIMIT_EXCEEDS_PARTIAL_MSG)) {
|
|
1139
1170
|
// do not send the content response back for this case to avoid unnecessary messages
|
|
1140
1171
|
return false;
|
|
1141
1172
|
}
|
|
@@ -1230,7 +1261,7 @@ class AgenticChatController {
|
|
|
1230
1261
|
}
|
|
1231
1262
|
if ((result.text && result.text.length > maxToolResponseSize) ||
|
|
1232
1263
|
(result.json && JSON.stringify(result.json).length > maxToolResponseSize)) {
|
|
1233
|
-
throw Error(`${toolUse.name} ${constants_2.
|
|
1264
|
+
throw Error(`${toolUse.name} ${constants_2.OUTPUT_LIMIT_EXCEEDS_PARTIAL_MSG} ${maxToolResponseSize}`);
|
|
1234
1265
|
}
|
|
1235
1266
|
}
|
|
1236
1267
|
/**
|
|
@@ -1463,9 +1494,11 @@ class AgenticChatController {
|
|
|
1463
1494
|
body = '```shell\n' + commandString;
|
|
1464
1495
|
break;
|
|
1465
1496
|
}
|
|
1466
|
-
case 'fsReplace':
|
|
1467
1497
|
case 'fsWrite': {
|
|
1468
1498
|
const writeFilePath = toolUse.input.path;
|
|
1499
|
+
// Validate the path using our synchronous utility
|
|
1500
|
+
(0, pathValidation_1.validatePathBasic)(writeFilePath);
|
|
1501
|
+
this.#debug(`Processing ${toolUse.name} for path: ${writeFilePath}`);
|
|
1469
1502
|
buttons = [{ id: 'allow-tools', text: 'Allow', icon: 'ok', status: 'clear' }];
|
|
1470
1503
|
header = {
|
|
1471
1504
|
icon: 'warning',
|
|
@@ -1477,7 +1510,26 @@ class AgenticChatController {
|
|
|
1477
1510
|
};
|
|
1478
1511
|
body = builtInPermission
|
|
1479
1512
|
? `I need permission to modify files.\n\`${writeFilePath}\``
|
|
1480
|
-
: `I need permission to modify files
|
|
1513
|
+
: `I need permission to modify files outside of your workspace.\n\`${writeFilePath}\``;
|
|
1514
|
+
break;
|
|
1515
|
+
}
|
|
1516
|
+
case 'fsReplace': {
|
|
1517
|
+
const writeFilePath = toolUse.input.path;
|
|
1518
|
+
// For replace, we need to verify the file exists
|
|
1519
|
+
(0, pathValidation_1.validatePathExists)(writeFilePath);
|
|
1520
|
+
this.#debug(`Processing ${toolUse.name} for path: ${writeFilePath}`);
|
|
1521
|
+
buttons = [{ id: 'allow-tools', text: 'Allow', icon: 'ok', status: 'clear' }];
|
|
1522
|
+
header = {
|
|
1523
|
+
icon: 'warning',
|
|
1524
|
+
iconForegroundStatus: 'warning',
|
|
1525
|
+
body: builtInPermission
|
|
1526
|
+
? '#### Allow file modification'
|
|
1527
|
+
: '#### Allow file modification outside of your workspace',
|
|
1528
|
+
buttons,
|
|
1529
|
+
};
|
|
1530
|
+
body = builtInPermission
|
|
1531
|
+
? `I need permission to modify files.\n\`${writeFilePath}\``
|
|
1532
|
+
: `I need permission to modify files outside of your workspace.\n\`${writeFilePath}\``;
|
|
1481
1533
|
break;
|
|
1482
1534
|
}
|
|
1483
1535
|
case 'fsRead':
|
|
@@ -1493,6 +1545,9 @@ class AgenticChatController {
|
|
|
1493
1545
|
};
|
|
1494
1546
|
if (toolName === 'fsRead') {
|
|
1495
1547
|
const paths = toolUse.input.paths;
|
|
1548
|
+
// Validate paths using our synchronous utility
|
|
1549
|
+
(0, pathValidation_1.validatePaths)(paths);
|
|
1550
|
+
this.#debug(`Processing ${toolUse.name} for paths: ${JSON.stringify(paths)}`);
|
|
1496
1551
|
const formattedPaths = [];
|
|
1497
1552
|
paths.forEach(element => formattedPaths.push(`\`${element}\``));
|
|
1498
1553
|
body = builtInPermission
|
|
@@ -1501,6 +1556,9 @@ class AgenticChatController {
|
|
|
1501
1556
|
}
|
|
1502
1557
|
else {
|
|
1503
1558
|
const readFilePath = toolUse.input.path;
|
|
1559
|
+
// Validate the path using our synchronous utility
|
|
1560
|
+
(0, pathValidation_1.validatePathExists)(readFilePath);
|
|
1561
|
+
this.#debug(`Processing ${toolUse.name} for path: ${readFilePath}`);
|
|
1504
1562
|
body = builtInPermission
|
|
1505
1563
|
? `I need permission to list directories.\n\`${readFilePath}\``
|
|
1506
1564
|
: `I need permission to list directories outside the workspace.\n\`${readFilePath}\``;
|
|
@@ -1811,6 +1869,8 @@ class AgenticChatController {
|
|
|
1811
1869
|
const requestID = (0, utils_2.getRequestID)(err) ?? '';
|
|
1812
1870
|
metric.setDimension('cwsprChatResponseCode', (0, utils_2.getHttpStatusCode)(err) ?? 0);
|
|
1813
1871
|
metric.setDimension('languageServerVersion', this.#features.runtime.serverInfo.version);
|
|
1872
|
+
metric.setDimension('codewhispererCustomizationArn', this.#customizationArn);
|
|
1873
|
+
metric.setDimension('enabled', agenticCodingMode);
|
|
1814
1874
|
metric.metric.requestIds = [requestID];
|
|
1815
1875
|
metric.metric.cwsprChatMessageId = errorMessageId;
|
|
1816
1876
|
metric.metric.cwsprChatConversationId = conversationId;
|
|
@@ -1841,7 +1901,7 @@ class AgenticChatController {
|
|
|
1841
1901
|
this.#telemetryController.emitMessageResponseError(tabId, metric.metric, requestID, customErrMessage, agenticCodingMode);
|
|
1842
1902
|
}
|
|
1843
1903
|
else {
|
|
1844
|
-
this.#telemetryController.emitMessageResponseError(tabId, metric.metric, requestID, errorMessage ?? constants_2.
|
|
1904
|
+
this.#telemetryController.emitMessageResponseError(tabId, metric.metric, requestID, errorMessage ?? constants_2.GENERIC_ERROR_MS, agenticCodingMode);
|
|
1845
1905
|
}
|
|
1846
1906
|
let authFollowType = undefined;
|
|
1847
1907
|
// first check if there is an AmazonQ related auth follow up
|
|
@@ -1907,7 +1967,7 @@ class AgenticChatController {
|
|
|
1907
1967
|
this.#features.logging.error(`Unknown Error: ${lsp_core_2.loggingUtils.formatErr(err)}`);
|
|
1908
1968
|
return new server_interface_1.ResponseError(server_interface_1.LSPErrorCodes.RequestFailed, err.message, {
|
|
1909
1969
|
type: 'answer',
|
|
1910
|
-
body: requestID ? `${constants_2.
|
|
1970
|
+
body: requestID ? `${constants_2.GENERIC_ERROR_MS} \n\nRequest ID: ${requestID}` : constants_2.GENERIC_ERROR_MS,
|
|
1911
1971
|
messageId: errorMessageId,
|
|
1912
1972
|
buttons: [],
|
|
1913
1973
|
});
|
|
@@ -2099,11 +2159,13 @@ class AgenticChatController {
|
|
|
2099
2159
|
});
|
|
2100
2160
|
}
|
|
2101
2161
|
onSourceLinkClick() { }
|
|
2102
|
-
|
|
2103
|
-
|
|
2162
|
+
/**
|
|
2163
|
+
* @deprecated use aws/chat/listAvailableModels server request instead
|
|
2164
|
+
*/
|
|
2165
|
+
#legacySetModelId(tabId, session) {
|
|
2104
2166
|
// Since model selection is mandatory, the only time modelId is not set is when the chat history is empty.
|
|
2105
2167
|
// In that case, we use the default modelId.
|
|
2106
|
-
let modelId = this.#chatHistoryDb.getModelId() ?? constants_2.
|
|
2168
|
+
let modelId = this.#chatHistoryDb.getModelId() ?? constants_2.DEFAULT_MODEL_ID;
|
|
2107
2169
|
const region = AmazonQTokenServiceManager_1.AmazonQTokenServiceManager.getInstance().getRegion();
|
|
2108
2170
|
if (region === 'eu-central-1') {
|
|
2109
2171
|
// Only 3.7 Sonnet is available in eu-central-1 for now
|
|
@@ -2111,7 +2173,11 @@ class AgenticChatController {
|
|
|
2111
2173
|
// @ts-ignore
|
|
2112
2174
|
this.#features.chat.chatOptionsUpdate({ region });
|
|
2113
2175
|
}
|
|
2114
|
-
this.#features.chat.chatOptionsUpdate({ modelId: modelId, tabId:
|
|
2176
|
+
this.#features.chat.chatOptionsUpdate({ modelId: modelId, tabId: tabId });
|
|
2177
|
+
session.modelId = modelId;
|
|
2178
|
+
}
|
|
2179
|
+
onTabAdd(params) {
|
|
2180
|
+
this.#telemetryController.activeTabId = params.tabId;
|
|
2115
2181
|
if (!params.restoredTab) {
|
|
2116
2182
|
this.sendPinnedContext(params.tabId);
|
|
2117
2183
|
}
|
|
@@ -2120,7 +2186,7 @@ class AgenticChatController {
|
|
|
2120
2186
|
if (!success) {
|
|
2121
2187
|
return new server_interface_1.ResponseError(protocol_2.ErrorCodes.InternalError, sessionResult.error);
|
|
2122
2188
|
}
|
|
2123
|
-
|
|
2189
|
+
this.#legacySetModelId(params.tabId, session);
|
|
2124
2190
|
// Get the saved pair programming mode from the database or default to true if not found
|
|
2125
2191
|
const savedPairProgrammingMode = this.#chatHistoryDb.getPairProgrammingMode();
|
|
2126
2192
|
session.pairProgrammingMode = savedPairProgrammingMode !== undefined ? savedPairProgrammingMode : true;
|
|
@@ -2486,8 +2552,8 @@ class AgenticChatController {
|
|
|
2486
2552
|
const timeoutPromise = new Promise((_, reject) => {
|
|
2487
2553
|
timeoutId = setTimeout(() => {
|
|
2488
2554
|
abortController.abort();
|
|
2489
|
-
reject(new errors_2.AgenticChatError(`${constants_2.
|
|
2490
|
-
}, constants_2.
|
|
2555
|
+
reject(new errors_2.AgenticChatError(`${constants_2.RESPONSE_TIMEOUT_PARTIAL_MSG} ${constants_2.RESPONSE_TIMEOUT_MS}ms`, 'ResponseProcessingTimeout'));
|
|
2556
|
+
}, constants_2.RESPONSE_TIMEOUT_MS);
|
|
2491
2557
|
});
|
|
2492
2558
|
const streamWriter = chatResultStream.getResultStreamWriter();
|
|
2493
2559
|
const processResponsePromise = this.#processAgenticChatResponse(response, metric, chatResultStream, streamWriter, session, contextList, abortController.signal);
|
|
@@ -2622,6 +2688,10 @@ class AgenticChatController {
|
|
|
2622
2688
|
* nothing is happening.
|
|
2623
2689
|
*/
|
|
2624
2690
|
async #showLoadingIfRequired(toolUseEvent, streamWriter, toolUseStartTimes, toolUseLoadingTimeouts) {
|
|
2691
|
+
const canWrite = new Set(this.#features.agent.getBuiltInWriteToolNames());
|
|
2692
|
+
if (toolUseEvent.name && canWrite.has(toolUseEvent.name)) {
|
|
2693
|
+
return;
|
|
2694
|
+
}
|
|
2625
2695
|
const toolUseId = toolUseEvent.toolUseId;
|
|
2626
2696
|
if (!toolUseEvent.stop && toolUseId) {
|
|
2627
2697
|
if (!toolUseStartTimes[toolUseId]) {
|
|
@@ -2632,9 +2702,9 @@ class AgenticChatController {
|
|
|
2632
2702
|
}
|
|
2633
2703
|
this.#debug(`ToolUseEvent ${toolUseId} started`);
|
|
2634
2704
|
toolUseLoadingTimeouts[toolUseId] = setTimeout(async () => {
|
|
2635
|
-
this.#debug(`ToolUseEvent ${toolUseId} is taking longer than ${constants_2.
|
|
2705
|
+
this.#debug(`ToolUseEvent ${toolUseId} is taking longer than ${constants_2.LOADING_THRESHOLD_MS}ms, showing loading indicator`);
|
|
2636
2706
|
await streamWriter.write({ ...constants_1.loadingMessage, messageId: `loading-${toolUseId}` });
|
|
2637
|
-
}, constants_2.
|
|
2707
|
+
}, constants_2.LOADING_THRESHOLD_MS);
|
|
2638
2708
|
}
|
|
2639
2709
|
}
|
|
2640
2710
|
else if (toolUseEvent.stop && toolUseId) {
|