From d90e230942835b8867425642b9d6d417c89a67ac Mon Sep 17 00:00:00 2001 From: Manodnya Bhoite Date: Tue, 29 Apr 2025 14:34:19 -0700 Subject: [PATCH 1/8] initial --- .../amazonq/webview/BrowserConnector.kt | 31 ++++++++++++++ .../amazonq/lsp/AmazonQLanguageServer.kt | 14 +++++++ .../amazonq/lsp/artifacts/ManifestFetcher.kt | 2 +- .../AwsServerCapabilitiesProvider.kt | 8 +++- .../lsp/model/aws/chat/FlareChatCommands.kt | 2 + .../model/aws/chat/GetSerializedChatParams.kt | 34 ++++++++++++++++ .../lsp/model/aws/chat/TabBarActionParams.kt | 40 +++++++++++++++++++ 7 files changed, 128 insertions(+), 3 deletions(-) create mode 100644 plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/GetSerializedChatParams.kt create mode 100644 plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/TabBarActionParams.kt diff --git a/plugins/amazonq/chat/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/webview/BrowserConnector.kt b/plugins/amazonq/chat/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/webview/BrowserConnector.kt index aa2dbed4239..2e40b6af5bb 100644 --- a/plugins/amazonq/chat/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/webview/BrowserConnector.kt +++ b/plugins/amazonq/chat/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/webview/BrowserConnector.kt @@ -4,6 +4,7 @@ package software.aws.toolkits.jetbrains.services.amazonq.webview import com.fasterxml.jackson.databind.JsonNode +import com.google.gson.Gson import com.intellij.ide.BrowserUtil import com.intellij.ide.util.RunOnceUtil import com.intellij.openapi.project.Project @@ -28,6 +29,7 @@ import software.aws.toolkits.jetbrains.services.amazonq.commands.MessageSerializ import software.aws.toolkits.jetbrains.services.amazonq.lsp.AmazonQLanguageServer import software.aws.toolkits.jetbrains.services.amazonq.lsp.AmazonQLspService import software.aws.toolkits.jetbrains.services.amazonq.lsp.encryption.JwtEncryptionManager +import software.aws.toolkits.jetbrains.services.amazonq.lsp.flareChat.AwsServerCapabilitiesProvider import software.aws.toolkits.jetbrains.services.amazonq.lsp.flareChat.ChatCommunicationManager import software.aws.toolkits.jetbrains.services.amazonq.lsp.flareChat.getTextDocumentIdentifier import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.ButtonClickNotification @@ -37,6 +39,7 @@ import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_ import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_COPY_CODE_TO_CLIPBOARD import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_FEEDBACK import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_FOLLOW_UP_CLICK +import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_GET_SERIALIZED_CHAT import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_INFO_LINK_CLICK import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_INSERT_TO_CURSOR import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_LINK_CLICK @@ -45,6 +48,7 @@ import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_ import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_READY import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_SOURCE_LINK_CLICK import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_TAB_ADD +import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_TAB_BAR_ACTIONS import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_TAB_CHANGE import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_TAB_REMOVE import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.ChatNotification @@ -60,6 +64,8 @@ import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.Feedb import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.FeedbackParams import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.FollowUpClickNotification import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.FollowUpClickParams +import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.GetSerializedChatParams +import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.GetSerializedChatRequest import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.InfoLinkClickNotification import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.InfoLinkClickParams import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.InsertToCursorPositionNotification @@ -74,6 +80,8 @@ import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.SEND_ import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.SendChatPromptRequest import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.SourceLinkClickNotification import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.SourceLinkClickParams +import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.TabBarActionParams +import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.TabBarActionRequest import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.TabEventParams import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.TabEventRequest import software.aws.toolkits.jetbrains.services.amazonq.util.command @@ -146,6 +154,14 @@ class BrowserConnector( // Wait for UI ready before starting to send messages to the UI. uiReady.await() + // Chat options including history and quick actions need to be sent in once UI is ready + val showChatOptions = """{ + "command": "chatOptions", + "params": ${Gson().toJson(AwsServerCapabilitiesProvider.getInstance(project).getChatOptions())} + } + """.trimIndent() + browser.postChat(showChatOptions) + // Send inbound messages to the browser val inboundMessages = connections.map { it.messagesFromAppToUi.flow }.merge() inboundMessages @@ -323,6 +339,21 @@ class BrowserConnector( server.copyCodeToClipboard(params) } } + + CHAT_GET_SERIALIZED_CHAT -> { + handleChatNotification(node) + { + server, params -> server.getSerializedActions(params) + } + } + + CHAT_TAB_BAR_ACTIONS -> { + handleChatNotification(node) + { + server, params -> server.tabBarActions(params) + } + + } } } diff --git a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageServer.kt b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageServer.kt index 6c715f96d0f..c554c083c8d 100644 --- a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageServer.kt +++ b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageServer.kt @@ -16,6 +16,7 @@ import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_ import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_COPY_CODE_TO_CLIPBOARD_NOTIFICATION import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_FEEDBACK import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_FOLLOW_UP_CLICK +import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_GET_SERIALIZED_CHAT import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_INFO_LINK_CLICK import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_INSERT_TO_CURSOR_NOTIFICATION import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_LINK_CLICK @@ -23,6 +24,7 @@ import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_ import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_READY import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_SOURCE_LINK_CLICK import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_TAB_ADD +import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_TAB_BAR_ACTIONS import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_TAB_CHANGE import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_TAB_REMOVE import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CopyCodeToClipboardParams @@ -30,6 +32,9 @@ import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.Encry import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.EncryptedQuickActionChatParams import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.FeedbackParams import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.FollowUpClickParams +import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.GetSerializedChatParams +import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.GetSerializedChatRequest +import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.GetSerializedChatResult import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.InfoLinkClickParams import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.InsertToCursorPositionParams import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.LinkClickParams @@ -37,6 +42,8 @@ import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.PROMP import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.PromptInputOptionChangeParams import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.SEND_CHAT_COMMAND_PROMPT import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.SourceLinkClickParams +import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.TabBarActionParams +import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.TabBarActionResult import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.TabEventParams import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.credentials.UpdateCredentialsPayload import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.dependencies.DidChangeDependencyPathsParams @@ -106,4 +113,11 @@ interface AmazonQLanguageServer : LanguageServer { @JsonRequest(CHAT_BUTTON_CLICK) fun buttonClick(params: ButtonClickParams): CompletableFuture + + @JsonRequest(CHAT_TAB_BAR_ACTIONS) + fun tabBarActions(params: TabBarActionParams): CompletableFuture + + @JsonRequest(CHAT_GET_SERIALIZED_CHAT) + fun getSerializedActions(params: GetSerializedChatParams): CompletableFuture + } diff --git a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/artifacts/ManifestFetcher.kt b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/artifacts/ManifestFetcher.kt index 74656d5665b..882bef614cc 100644 --- a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/artifacts/ManifestFetcher.kt +++ b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/artifacts/ManifestFetcher.kt @@ -25,7 +25,7 @@ class ManifestFetcher( private val logger = getLogger() private const val DEFAULT_MANIFEST_URL = - "https://aws-toolkit-language-servers.amazonaws.com/remoteWorkspaceContext/0/manifest.json" + "https://d3akiidp1wvqyg.cloudfront.net/qAgenticChatServer/0/manifest.json" private val DEFAULT_MANIFEST_PATH: Path = getToolkitsCommonCacheRoot() .resolve("aws") diff --git a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/flareChat/AwsServerCapabilitiesProvider.kt b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/flareChat/AwsServerCapabilitiesProvider.kt index 5c4eec4491a..882ee407de6 100644 --- a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/flareChat/AwsServerCapabilitiesProvider.kt +++ b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/flareChat/AwsServerCapabilitiesProvider.kt @@ -15,7 +15,7 @@ class AwsServerCapabilitiesProvider { this.serverCapabilities = serverCapabilities } - fun getChatOptions() = serverCapabilities?.chatOptions ?: DEFAULT_CHAT_OPTIONS + fun getChatOptions() = DEFAULT_CHAT_OPTIONS companion object { fun getInstance(project: Project) = project.service() @@ -30,7 +30,9 @@ class AwsServerCapabilitiesProvider { ) ) ) - ) + ), + history = true, + export = true ) } } @@ -41,6 +43,8 @@ data class AwsServerCapabilities( data class ChatOptions( val quickActions: QuickActions, + val history: Boolean, + val export: Boolean ) data class QuickActions( diff --git a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/FlareChatCommands.kt b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/FlareChatCommands.kt index 3ea5bbccacd..3712cc22a36 100644 --- a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/FlareChatCommands.kt +++ b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/FlareChatCommands.kt @@ -22,3 +22,5 @@ const val CHAT_COPY_CODE_TO_CLIPBOARD = "copyToClipboard" const val CHAT_COPY_CODE_TO_CLIPBOARD_NOTIFICATION = "aws/chat/copyCodeToClipboard" const val CHAT_INSERT_TO_CURSOR = "insertToCursorPosition" const val CHAT_INSERT_TO_CURSOR_NOTIFICATION = "aws/chat/insertToCursorPosition" +const val CHAT_GET_SERIALIZED_CHAT="aws/chat/getSerializedChat" +const val CHAT_TAB_BAR_ACTIONS="aws/chat/tabBarAction" diff --git a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/GetSerializedChatParams.kt b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/GetSerializedChatParams.kt new file mode 100644 index 00000000000..dc614b6fcab --- /dev/null +++ b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/GetSerializedChatParams.kt @@ -0,0 +1,34 @@ +// Copyright 2025 Amazon.com, Inc. or its affiliates. All Rights Reserved. +// SPDX-License-Identifier: Apache-2.0 + +package software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat + +data class GetSerializedChatParams( + val tabId: String, + val format : String +) { + companion object { + fun create(tabId: String, format: SerializedChatFormat): GetSerializedChatParams { + return GetSerializedChatParams(tabId, format.value) + } + } +} + +enum class SerializedChatFormat(val value: String) { + HTML("html"), + MARKDOWN("markdown"); + + override fun toString(): String { + return name.lowercase() + } +} + +data class GetSerializedChatResult( + val content: String +) + +data class GetSerializedChatRequest( + val requestId: String, + override val command: String, + override val params: GetSerializedChatParams, +) : ChatNotification diff --git a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/TabBarActionParams.kt b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/TabBarActionParams.kt new file mode 100644 index 00000000000..f2884cd463d --- /dev/null +++ b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/TabBarActionParams.kt @@ -0,0 +1,40 @@ +// Copyright 2025 Amazon.com, Inc. or its affiliates. All Rights Reserved. +// SPDX-License-Identifier: Apache-2.0 + +package software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat + +//data class TabBarActionParams( +// val tabId: String?, +// val action: TabBarAction +//) +data class TabBarActionParams( + val tabId: String?, + val action: String +) { + companion object { + fun create(tabId: String?, action: TabBarAction): TabBarActionParams { + return TabBarActionParams(tabId, action.value) + } + } +} + + +enum class TabBarAction(val value: String) { + EXPORT("export"), + HISTORY("history"); + + override fun toString(): String { + return name.lowercase() + } + +} + +data class TabBarActionResult( + val success: Boolean +) + +data class TabBarActionRequest( + override val command: String, + override val params: TabBarActionParams, +) : ChatNotification + From f5c8d3891a0c81819562471cccc3e5ef590d6a3e Mon Sep 17 00:00:00 2001 From: Manodnya Bhoite Date: Wed, 30 Apr 2025 14:26:11 -0700 Subject: [PATCH 2/8] Merge conflicts resolved --- .../services/amazonq/webview/Browser.kt | 1 + .../amazonq/webview/BrowserConnector.kt | 25 ++-- .../amazonq/lsp/AmazonQLanguageClient.kt | 12 ++ .../amazonq/lsp/AmazonQLanguageClientImpl.kt | 119 ++++++++++++++++++ .../amazonq/lsp/AmazonQLanguageServer.kt | 4 +- .../lsp/flareChat/ChatCommunicationManager.kt | 9 ++ .../lsp/model/ExtendedClientMetadata.kt | 8 ++ .../amazonq/lsp/model/aws/chat/ChatPrompt.kt | 2 +- .../lsp/model/aws/chat/FlareChatCommands.kt | 3 +- .../model/aws/chat/GetSerializedChatParams.kt | 11 ++ .../aws/chat/ShowSaveFileDialogParams.kt | 15 +++ .../lsp/model/aws/chat/TabBarActionParams.kt | 7 +- 12 files changed, 199 insertions(+), 17 deletions(-) create mode 100644 plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/ShowSaveFileDialogParams.kt diff --git a/plugins/amazonq/chat/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/webview/Browser.kt b/plugins/amazonq/chat/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/webview/Browser.kt index 8177af3f194..dba47f08e6c 100644 --- a/plugins/amazonq/chat/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/webview/Browser.kt +++ b/plugins/amazonq/chat/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/webview/Browser.kt @@ -127,6 +127,7 @@ class Browser(parent: Disposable, private val webUri: URI, val project: Project) } }, { + agenticMode: true, quickActionCommands: $quickActionConfig, disclaimerAcknowledged: ${MeetQSettings.getInstance().disclaimerAcknowledged}, pairProgrammingAcknowledged: ${!MeetQSettings.getInstance().amazonQChatPairProgramming} diff --git a/plugins/amazonq/chat/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/webview/BrowserConnector.kt b/plugins/amazonq/chat/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/webview/BrowserConnector.kt index a2eb3710071..008633b6a79 100644 --- a/plugins/amazonq/chat/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/webview/BrowserConnector.kt +++ b/plugins/amazonq/chat/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/webview/BrowserConnector.kt @@ -18,6 +18,7 @@ import kotlinx.coroutines.flow.distinctUntilChanged import kotlinx.coroutines.flow.launchIn import kotlinx.coroutines.flow.merge import kotlinx.coroutines.flow.onEach +import kotlinx.coroutines.future.await import kotlinx.coroutines.launch import org.cef.browser.CefBrowser import org.eclipse.lsp4j.Position @@ -26,6 +27,7 @@ import software.aws.toolkits.core.utils.getLogger import software.aws.toolkits.core.utils.warn import software.aws.toolkits.jetbrains.services.amazonq.apps.AppConnection import software.aws.toolkits.jetbrains.services.amazonq.commands.MessageSerializer +import software.aws.toolkits.jetbrains.services.amazonq.lsp.AmazonQLanguageClientImpl import software.aws.toolkits.jetbrains.services.amazonq.lsp.AmazonQLanguageServer import software.aws.toolkits.jetbrains.services.amazonq.lsp.AmazonQLspService import software.aws.toolkits.jetbrains.services.amazonq.lsp.encryption.JwtEncryptionManager @@ -42,7 +44,6 @@ import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_ import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_FEEDBACK import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_FILE_CLICK import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_FOLLOW_UP_CLICK -import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_GET_SERIALIZED_CHAT import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_INFO_LINK_CLICK import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_INSERT_TO_CURSOR import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_LINK_CLICK @@ -71,8 +72,10 @@ import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.FileC import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.FileClickParams import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.FollowUpClickNotification import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.FollowUpClickParams +import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.GET_SERIALIZED_CHAT_REQUEST_METHOD import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.GetSerializedChatParams import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.GetSerializedChatRequest +import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.GetSerializedChatResponse import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.InfoLinkClickNotification import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.InfoLinkClickParams import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.InsertToCursorPositionNotification @@ -347,17 +350,25 @@ class BrowserConnector( } } - CHAT_GET_SERIALIZED_CHAT -> { - handleChatNotification(node) - { - server, params -> server.getSerializedActions(params) - } + GET_SERIALIZED_CHAT_REQUEST_METHOD -> { + val response = serializer.deserializeChatMessages(node) + AmazonQLanguageClientImpl.completeSerializedChatResponse( + response.requestId, + response.params.result.content + ) } CHAT_TAB_BAR_ACTIONS -> { handleChatNotification(node) { - server, params -> server.tabBarActions(params) + server, params -> + val result = server.tabBarActions(params) + result.whenComplete { params1, error -> + val res = ChatCommunicationManager.convertNotificationToJsonForChat(CHAT_TAB_BAR_ACTIONS, params1) + browser.postChat(res) + } + + } } diff --git a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageClient.kt b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageClient.kt index 74e007f2a76..dac03072cdc 100644 --- a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageClient.kt +++ b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageClient.kt @@ -5,8 +5,14 @@ package software.aws.toolkits.jetbrains.services.amazonq.lsp import org.eclipse.lsp4j.jsonrpc.services.JsonRequest import org.eclipse.lsp4j.services.LanguageClient +import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.GET_SERIALIZED_CHAT_REQUEST_METHOD +import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.GetSerializedChatParams +import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.GetSerializedChatResult import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.OpenTabParams import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.OpenTabResult +import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.SHOW_SAVE_FILE_DIALOG_REQUEST_METHOD +import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.ShowSaveFileDialogParams +import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.ShowSaveFileDialogResult import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.credentials.ConnectionMetadata import java.util.concurrent.CompletableFuture @@ -20,4 +26,10 @@ interface AmazonQLanguageClient : LanguageClient { @JsonRequest("aws/chat/openTab") fun openTab(params: OpenTabParams): CompletableFuture + + @JsonRequest(SHOW_SAVE_FILE_DIALOG_REQUEST_METHOD) + fun showSaveFileDialog(params: ShowSaveFileDialogParams): CompletableFuture + + @JsonRequest(GET_SERIALIZED_CHAT_REQUEST_METHOD) + fun getSerializedChat(params: GetSerializedChatParams): CompletableFuture } diff --git a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageClientImpl.kt b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageClientImpl.kt index e74c17cd245..135df3bcfec 100644 --- a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageClientImpl.kt +++ b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageClientImpl.kt @@ -3,11 +3,22 @@ package software.aws.toolkits.jetbrains.services.amazonq.lsp +import com.google.gson.Gson import com.intellij.notification.NotificationType import com.intellij.openapi.application.ApplicationManager +import com.intellij.openapi.application.invokeAndWaitIfNeeded +import com.intellij.openapi.fileChooser.FileChooser +import com.intellij.openapi.fileChooser.FileChooserDescriptor +import com.intellij.openapi.fileChooser.FileChooserDescriptorFactory +import com.intellij.openapi.fileChooser.FileChooserFactory +import com.intellij.openapi.fileChooser.FileSaverDescriptor import com.intellij.openapi.fileEditor.FileEditorManager import com.intellij.openapi.project.Project +import com.intellij.openapi.ui.DialogWrapper +import com.intellij.openapi.vfs.LocalFileSystem import com.intellij.openapi.vfs.VirtualFileManager +import com.intellij.ui.components.textFieldWithBrowseButton +import com.intellij.ui.dsl.builder.panel import migration.software.aws.toolkits.jetbrains.settings.AwsSettings import org.eclipse.lsp4j.ConfigurationParams import org.eclipse.lsp4j.MessageActionItem @@ -23,14 +34,30 @@ import software.aws.toolkits.core.utils.warn import software.aws.toolkits.jetbrains.core.credentials.AwsBearerTokenConnection import software.aws.toolkits.jetbrains.core.credentials.ToolkitConnectionManager import software.aws.toolkits.jetbrains.core.credentials.pinning.QConnection +import software.aws.toolkits.jetbrains.services.amazonq.lsp.flareChat.AsyncChatUiListener import software.aws.toolkits.jetbrains.services.amazonq.lsp.flareChat.ChatCommunicationManager +import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.GET_SERIALIZED_CHAT_REQUEST_METHOD +import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.GetSerializedChatParams +import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.GetSerializedChatResult import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.OpenTabParams import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.OpenTabResult +import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.ShowSaveFileDialogParams +import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.ShowSaveFileDialogResult import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.credentials.ConnectionMetadata import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.credentials.SsoProfileData import software.aws.toolkits.jetbrains.services.codewhisperer.customization.CodeWhispererModelConfigurator import software.aws.toolkits.jetbrains.settings.CodeWhispererSettings +import software.aws.toolkits.jetbrains.utils.computeOnEdt +import java.io.File +import java.io.FileFilter +import java.net.URI +import java.util.UUID import java.util.concurrent.CompletableFuture +import java.util.concurrent.ConcurrentHashMap +import java.util.concurrent.TimeUnit +import javax.swing.JComponent +import javax.swing.JFileChooser +import javax.swing.filechooser.FileNameExtensionFilter /** * Concrete implementation of [AmazonQLanguageClient] to handle messages sent from server @@ -87,6 +114,7 @@ class AmazonQLanguageClientImpl(private val project: Project) : AmazonQLanguageC } } + override fun getConnectionMetadata(): CompletableFuture = CompletableFuture.supplyAsync { val connection = ToolkitConnectionManager.getInstance(project) @@ -111,6 +139,71 @@ class AmazonQLanguageClientImpl(private val project: Project) : AmazonQLanguageC // TODO implement chat history, this is here to unblock chat functionality CompletableFuture.completedFuture(OpenTabResult("")) + override fun showSaveFileDialog(params: ShowSaveFileDialogParams): CompletableFuture { + val filters = mutableMapOf() + val formatMappings = listOf( + FormatMapping("markdown", "Markdown", "md"), + FormatMapping("html", "HTML", "html") + ) + + params.supportedFormats.forEach { format -> + formatMappings.find { it.format == format }?.let { mapping -> + filters[mapping.key] = mapping.extensions + } + } + + val saveAtUri = params.defaultURI ?:"export-chat.html" + + return CompletableFuture.supplyAsync{ + + return@supplyAsync invokeAndWaitIfNeeded { + val descriptor = FileSaverDescriptor("Export", "Choose a location to export").apply { + withFileFilter { file -> + filters.values.any { ext -> + file.name.endsWith(".$ext") + } + } + } + + val chosenFile = FileChooserFactory.getInstance().createSaveFileDialog(descriptor, project).save(saveAtUri) + + chosenFile?.let { + return@invokeAndWaitIfNeeded ShowSaveFileDialogResult(chosenFile.file.toURI()) + // TODO: Add error state shown in chat ui instead of throwing + } ?: throw Error( "Export failed") + } + + + } + + + } + + override fun getSerializedChat(params: GetSerializedChatParams): CompletableFuture { + val requestId = UUID.randomUUID().toString() + val result = CompletableFuture() + + pendingSerializedChatRequests[requestId] = result + + val uiMessage = """ + { + "command": "$GET_SERIALIZED_CHAT_REQUEST_METHOD", + "params": ${Gson().toJson(params)}, + "requestId": "$requestId" + } + """.trimIndent() + AsyncChatUiListener.notifyPartialMessageUpdate(uiMessage) + + result.orTimeout(30000, TimeUnit.MILLISECONDS) + .whenComplete { _, error -> + if (error != null) { + pendingSerializedChatRequests.remove(requestId) + } + } + + return result + } + override fun configuration(params: ConfigurationParams): CompletableFuture> { if (params.items.isEmpty()) { return CompletableFuture.completedFuture(null) @@ -166,5 +259,31 @@ class AmazonQLanguageClientImpl(private val project: Project) : AmazonQLanguageC companion object { private val LOG = getLogger() + private val pendingSerializedChatRequests = ConcurrentHashMap>() + fun completeSerializedChatResponse(requestId: String, content: String) { + pendingSerializedChatRequests.remove(requestId)?.complete(GetSerializedChatResult((content))) + } + } +} + +data class FormatMapping( + val format: String, + val key: String, + val extensions: String +) + +class aaaaa(val project: Project, val descriptor: FileChooserDescriptor): DialogWrapper(project) { + + + init { + super.init() + title = "Export" + } + + override fun createCenterPanel(): JComponent? = panel { + row { + textFieldWithBrowseButton(project, descriptor) + } + } } diff --git a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageServer.kt b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageServer.kt index e3e8662f21a..941d31b9a56 100644 --- a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageServer.kt +++ b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageServer.kt @@ -18,7 +18,6 @@ import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_ import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_FEEDBACK import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_FILE_CLICK import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_FOLLOW_UP_CLICK -import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_GET_SERIALIZED_CHAT import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_INFO_LINK_CLICK import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_INSERT_TO_CURSOR_NOTIFICATION import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.CHAT_LINK_CLICK @@ -36,6 +35,7 @@ import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.Encry import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.FeedbackParams import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.FileClickParams import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.FollowUpClickParams +import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.GET_SERIALIZED_CHAT_REQUEST_METHOD import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.GetSerializedChatParams import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.GetSerializedChatRequest import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.GetSerializedChatResult @@ -124,7 +124,7 @@ interface AmazonQLanguageServer : LanguageServer { @JsonRequest(CHAT_TAB_BAR_ACTIONS) fun tabBarActions(params: TabBarActionParams): CompletableFuture - @JsonRequest(CHAT_GET_SERIALIZED_CHAT) + @JsonRequest(GET_SERIALIZED_CHAT_REQUEST_METHOD) fun getSerializedActions(params: GetSerializedChatParams): CompletableFuture @JsonNotification(CHAT_CREATE_PROMPT) diff --git a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/flareChat/ChatCommunicationManager.kt b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/flareChat/ChatCommunicationManager.kt index 1ee2c52fc92..7662436c928 100644 --- a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/flareChat/ChatCommunicationManager.kt +++ b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/flareChat/ChatCommunicationManager.kt @@ -3,6 +3,7 @@ package software.aws.toolkits.jetbrains.services.amazonq.lsp.flareChat +import com.google.gson.Gson import com.intellij.openapi.components.Service import com.intellij.openapi.components.service import com.intellij.openapi.project.Project @@ -65,5 +66,13 @@ class ChatCommunicationManager { "isPartialResult": $isPartialResult } """.trimIndent() + + inline fun convertNotificationToJsonForChat(command: String, params: T? = null) = + """ + { + "command":"$command", + "params": ${if (params != null) Gson().toJson(params) else "{}"} + } + """.trimIndent() } } diff --git a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/ExtendedClientMetadata.kt b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/ExtendedClientMetadata.kt index b25150c36bb..b88bb7c51f7 100644 --- a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/ExtendedClientMetadata.kt +++ b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/ExtendedClientMetadata.kt @@ -16,12 +16,17 @@ data class AwsMetadata( data class AwsClientCapabilities( val q: DeveloperProfiles, + val window: WindowSettings ) data class DeveloperProfiles( val developerProfiles: Boolean, ) +data class WindowSettings( + val showSaveFileDialog: Boolean +) + data class ClientInfoMetadata( val extension: ExtensionMetadata, val clientId: String, @@ -50,6 +55,9 @@ fun createExtendedClientMetadata(): ExtendedClientMetadata { awsClientCapabilities = AwsClientCapabilities( q = DeveloperProfiles( developerProfiles = true + ), + window = WindowSettings( + showSaveFileDialog = true ) ) ) diff --git a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/ChatPrompt.kt b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/ChatPrompt.kt index 79704888817..3e5f430c17a 100644 --- a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/ChatPrompt.kt +++ b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/ChatPrompt.kt @@ -32,5 +32,5 @@ data class InnerChatPrompt( data class InnerChatOptions( @JsonProperty("pair-programmer-mode") - val pairProgrammingMode: String, + val pairProgrammingMode: String?, ) diff --git a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/FlareChatCommands.kt b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/FlareChatCommands.kt index fbffa630788..b0f2f4113c2 100644 --- a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/FlareChatCommands.kt +++ b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/FlareChatCommands.kt @@ -24,6 +24,7 @@ const val CHAT_COPY_CODE_TO_CLIPBOARD = "copyToClipboard" const val CHAT_COPY_CODE_TO_CLIPBOARD_NOTIFICATION = "aws/chat/copyCodeToClipboard" const val CHAT_INSERT_TO_CURSOR = "insertToCursorPosition" const val CHAT_INSERT_TO_CURSOR_NOTIFICATION = "aws/chat/insertToCursorPosition" -const val CHAT_GET_SERIALIZED_CHAT="aws/chat/getSerializedChat" const val CHAT_TAB_BAR_ACTIONS="aws/chat/tabBarAction" const val CHAT_CREATE_PROMPT = "aws/chat/createPrompt" +const val SHOW_SAVE_FILE_DIALOG_REQUEST_METHOD = "aws/showSaveFileDialog" +const val GET_SERIALIZED_CHAT_REQUEST_METHOD = "aws/chat/getSerializedChat" diff --git a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/GetSerializedChatParams.kt b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/GetSerializedChatParams.kt index dc614b6fcab..f16b450fcdd 100644 --- a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/GetSerializedChatParams.kt +++ b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/GetSerializedChatParams.kt @@ -32,3 +32,14 @@ data class GetSerializedChatRequest( override val command: String, override val params: GetSerializedChatParams, ) : ChatNotification + +data class GetSerializedChatResponseParams( + val success: Boolean, + val result: GetSerializedChatResult +) + +data class GetSerializedChatResponse( + val requestId: String, + val command: String, + val params: GetSerializedChatResponseParams, +) diff --git a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/ShowSaveFileDialogParams.kt b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/ShowSaveFileDialogParams.kt new file mode 100644 index 00000000000..8100ff45601 --- /dev/null +++ b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/ShowSaveFileDialogParams.kt @@ -0,0 +1,15 @@ +// Copyright 2025 Amazon.com, Inc. or its affiliates. All Rights Reserved. +// SPDX-License-Identifier: Apache-2.0 + +package software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat + +import java.net.URI + +data class ShowSaveFileDialogParams( + val supportedFormats: List, + val defaultURI: String? +) + +data class ShowSaveFileDialogResult( + val target: URI +) diff --git a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/TabBarActionParams.kt b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/TabBarActionParams.kt index f2884cd463d..ff928c292d3 100644 --- a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/TabBarActionParams.kt +++ b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/TabBarActionParams.kt @@ -3,10 +3,6 @@ package software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat -//data class TabBarActionParams( -// val tabId: String?, -// val action: TabBarAction -//) data class TabBarActionParams( val tabId: String?, val action: String @@ -20,8 +16,7 @@ data class TabBarActionParams( enum class TabBarAction(val value: String) { - EXPORT("export"), - HISTORY("history"); + EXPORT("export"); override fun toString(): String { return name.lowercase() From aed9e92d3e4a8ea154f95e2ca8d5fcbd8f979afb Mon Sep 17 00:00:00 2001 From: Manodnya Bhoite Date: Wed, 30 Apr 2025 14:27:34 -0700 Subject: [PATCH 3/8] revert --- .../jetbrains/services/amazonq/lsp/artifacts/ManifestFetcher.kt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/artifacts/ManifestFetcher.kt b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/artifacts/ManifestFetcher.kt index 882bef614cc..74656d5665b 100644 --- a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/artifacts/ManifestFetcher.kt +++ b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/artifacts/ManifestFetcher.kt @@ -25,7 +25,7 @@ class ManifestFetcher( private val logger = getLogger() private const val DEFAULT_MANIFEST_URL = - "https://d3akiidp1wvqyg.cloudfront.net/qAgenticChatServer/0/manifest.json" + "https://aws-toolkit-language-servers.amazonaws.com/remoteWorkspaceContext/0/manifest.json" private val DEFAULT_MANIFEST_PATH: Path = getToolkitsCommonCacheRoot() .resolve("aws") From 73983989cbffeda0d71d92eb0561e96dc6097bce Mon Sep 17 00:00:00 2001 From: Manodnya Bhoite Date: Wed, 30 Apr 2025 14:55:12 -0700 Subject: [PATCH 4/8] save --- .../amazonq/lsp/model/aws/chat/ShowSaveFileDialogParams.kt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/ShowSaveFileDialogParams.kt b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/ShowSaveFileDialogParams.kt index 8100ff45601..658e71e7afa 100644 --- a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/ShowSaveFileDialogParams.kt +++ b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/ShowSaveFileDialogParams.kt @@ -11,5 +11,5 @@ data class ShowSaveFileDialogParams( ) data class ShowSaveFileDialogResult( - val target: URI + val target: String ) From 8b14510e529e71d010300a1410a8d46a31309a46 Mon Sep 17 00:00:00 2001 From: Manodnya Bhoite Date: Wed, 30 Apr 2025 14:56:22 -0700 Subject: [PATCH 5/8] save --- .../jetbrains/services/amazonq/lsp/AmazonQLanguageClientImpl.kt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageClientImpl.kt b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageClientImpl.kt index 135df3bcfec..c4e88d328bb 100644 --- a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageClientImpl.kt +++ b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageClientImpl.kt @@ -168,7 +168,7 @@ class AmazonQLanguageClientImpl(private val project: Project) : AmazonQLanguageC val chosenFile = FileChooserFactory.getInstance().createSaveFileDialog(descriptor, project).save(saveAtUri) chosenFile?.let { - return@invokeAndWaitIfNeeded ShowSaveFileDialogResult(chosenFile.file.toURI()) + return@invokeAndWaitIfNeeded ShowSaveFileDialogResult(chosenFile.file.path) // TODO: Add error state shown in chat ui instead of throwing } ?: throw Error( "Export failed") } From 2e2ff62fef0ff1373b3377b7f7e2587515a1d1ae Mon Sep 17 00:00:00 2001 From: Manodnya Bhoite Date: Wed, 30 Apr 2025 17:58:54 -0700 Subject: [PATCH 6/8] export chat: --- .../amazonq/webview/BrowserConnector.kt | 12 +--- .../amazonq/lsp/AmazonQLanguageClientImpl.kt | 55 +++---------------- .../amazonq/lsp/AmazonQLanguageServer.kt | 2 - .../AwsServerCapabilitiesProvider.kt | 2 +- .../lsp/flareChat/ChatCommunicationManager.kt | 11 +++- .../lsp/model/ExtendedClientMetadata.kt | 4 +- .../lsp/model/aws/chat/FlareChatCommands.kt | 2 +- .../model/aws/chat/GetSerializedChatParams.kt | 19 +++---- .../aws/chat/ShowSaveFileDialogParams.kt | 6 +- .../lsp/model/aws/chat/TabBarActionParams.kt | 20 +++---- 10 files changed, 42 insertions(+), 91 deletions(-) diff --git a/plugins/amazonq/chat/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/webview/BrowserConnector.kt b/plugins/amazonq/chat/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/webview/BrowserConnector.kt index 008633b6a79..91f7a4152f7 100644 --- a/plugins/amazonq/chat/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/webview/BrowserConnector.kt +++ b/plugins/amazonq/chat/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/webview/BrowserConnector.kt @@ -73,8 +73,6 @@ import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.FileC import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.FollowUpClickNotification import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.FollowUpClickParams import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.GET_SERIALIZED_CHAT_REQUEST_METHOD -import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.GetSerializedChatParams -import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.GetSerializedChatRequest import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.GetSerializedChatResponse import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.InfoLinkClickNotification import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.InfoLinkClickParams @@ -233,7 +231,7 @@ class BrowserConnector( requestFromUi.params.tabId, chatPrompt, textDocumentIdentifier, - cursorState + cursorState, ) val tabId = requestFromUi.params.tabId @@ -359,18 +357,14 @@ class BrowserConnector( } CHAT_TAB_BAR_ACTIONS -> { - handleChatNotification(node) - { - server, params -> + handleChatNotification(node) { + server, params -> val result = server.tabBarActions(params) result.whenComplete { params1, error -> val res = ChatCommunicationManager.convertNotificationToJsonForChat(CHAT_TAB_BAR_ACTIONS, params1) browser.postChat(res) } - - } - } CHAT_CREATE_PROMPT -> { handleChatNotification(node) { diff --git a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageClientImpl.kt b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageClientImpl.kt index c4e88d328bb..3c32fc01d64 100644 --- a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageClientImpl.kt +++ b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageClientImpl.kt @@ -1,24 +1,17 @@ // Copyright 2025 Amazon.com, Inc. or its affiliates. All Rights Reserved. // SPDX-License-Identifier: Apache-2.0 - +@file:Suppress("BannedImports") package software.aws.toolkits.jetbrains.services.amazonq.lsp import com.google.gson.Gson import com.intellij.notification.NotificationType import com.intellij.openapi.application.ApplicationManager import com.intellij.openapi.application.invokeAndWaitIfNeeded -import com.intellij.openapi.fileChooser.FileChooser -import com.intellij.openapi.fileChooser.FileChooserDescriptor -import com.intellij.openapi.fileChooser.FileChooserDescriptorFactory import com.intellij.openapi.fileChooser.FileChooserFactory import com.intellij.openapi.fileChooser.FileSaverDescriptor import com.intellij.openapi.fileEditor.FileEditorManager import com.intellij.openapi.project.Project -import com.intellij.openapi.ui.DialogWrapper -import com.intellij.openapi.vfs.LocalFileSystem import com.intellij.openapi.vfs.VirtualFileManager -import com.intellij.ui.components.textFieldWithBrowseButton -import com.intellij.ui.dsl.builder.panel import migration.software.aws.toolkits.jetbrains.settings.AwsSettings import org.eclipse.lsp4j.ConfigurationParams import org.eclipse.lsp4j.MessageActionItem @@ -47,17 +40,9 @@ import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.credential import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.credentials.SsoProfileData import software.aws.toolkits.jetbrains.services.codewhisperer.customization.CodeWhispererModelConfigurator import software.aws.toolkits.jetbrains.settings.CodeWhispererSettings -import software.aws.toolkits.jetbrains.utils.computeOnEdt -import java.io.File -import java.io.FileFilter -import java.net.URI import java.util.UUID import java.util.concurrent.CompletableFuture -import java.util.concurrent.ConcurrentHashMap import java.util.concurrent.TimeUnit -import javax.swing.JComponent -import javax.swing.JFileChooser -import javax.swing.filechooser.FileNameExtensionFilter /** * Concrete implementation of [AmazonQLanguageClient] to handle messages sent from server @@ -114,7 +99,6 @@ class AmazonQLanguageClientImpl(private val project: Project) : AmazonQLanguageC } } - override fun getConnectionMetadata(): CompletableFuture = CompletableFuture.supplyAsync { val connection = ToolkitConnectionManager.getInstance(project) @@ -152,10 +136,9 @@ class AmazonQLanguageClientImpl(private val project: Project) : AmazonQLanguageC } } - val saveAtUri = params.defaultURI ?:"export-chat.html" - - return CompletableFuture.supplyAsync{ + val saveAtUri = params.defaultUri ?: "export-chat.html" + return CompletableFuture.supplyAsync { return@supplyAsync invokeAndWaitIfNeeded { val descriptor = FileSaverDescriptor("Export", "Choose a location to export").apply { withFileFilter { file -> @@ -170,20 +153,16 @@ class AmazonQLanguageClientImpl(private val project: Project) : AmazonQLanguageC chosenFile?.let { return@invokeAndWaitIfNeeded ShowSaveFileDialogResult(chosenFile.file.path) // TODO: Add error state shown in chat ui instead of throwing - } ?: throw Error( "Export failed") + } ?: throw Error("Export failed") } - - } - - } override fun getSerializedChat(params: GetSerializedChatParams): CompletableFuture { val requestId = UUID.randomUUID().toString() val result = CompletableFuture() - pendingSerializedChatRequests[requestId] = result + ChatCommunicationManager.pendingSerializedChatRequests[requestId] = result val uiMessage = """ { @@ -197,7 +176,7 @@ class AmazonQLanguageClientImpl(private val project: Project) : AmazonQLanguageC result.orTimeout(30000, TimeUnit.MILLISECONDS) .whenComplete { _, error -> if (error != null) { - pendingSerializedChatRequests.remove(requestId) + ChatCommunicationManager.pendingSerializedChatRequests.remove(requestId) } } @@ -259,31 +238,11 @@ class AmazonQLanguageClientImpl(private val project: Project) : AmazonQLanguageC companion object { private val LOG = getLogger() - private val pendingSerializedChatRequests = ConcurrentHashMap>() - fun completeSerializedChatResponse(requestId: String, content: String) { - pendingSerializedChatRequests.remove(requestId)?.complete(GetSerializedChatResult((content))) - } } } data class FormatMapping( val format: String, val key: String, - val extensions: String + val extensions: String, ) - -class aaaaa(val project: Project, val descriptor: FileChooserDescriptor): DialogWrapper(project) { - - - init { - super.init() - title = "Export" - } - - override fun createCenterPanel(): JComponent? = panel { - row { - textFieldWithBrowseButton(project, descriptor) - } - - } -} diff --git a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageServer.kt b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageServer.kt index 941d31b9a56..7f02ed89abc 100644 --- a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageServer.kt +++ b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageServer.kt @@ -37,7 +37,6 @@ import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.FileC import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.FollowUpClickParams import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.GET_SERIALIZED_CHAT_REQUEST_METHOD import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.GetSerializedChatParams -import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.GetSerializedChatRequest import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.GetSerializedChatResult import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.InfoLinkClickParams import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.InsertToCursorPositionParams @@ -129,5 +128,4 @@ interface AmazonQLanguageServer : LanguageServer { @JsonNotification(CHAT_CREATE_PROMPT) fun createPrompt(params: CreatePromptParams): CompletableFuture - } diff --git a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/flareChat/AwsServerCapabilitiesProvider.kt b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/flareChat/AwsServerCapabilitiesProvider.kt index d884d664318..7b36838a9b0 100644 --- a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/flareChat/AwsServerCapabilitiesProvider.kt +++ b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/flareChat/AwsServerCapabilitiesProvider.kt @@ -15,7 +15,7 @@ class AwsServerCapabilitiesProvider { this.serverCapabilities = serverCapabilities } - fun getChatOptions() = serverCapabilities?.chatOptions ?: DEFAULT_CHAT_OPTIONS + fun getChatOptions() = serverCapabilities?.chatOptions ?: DEFAULT_CHAT_OPTIONS companion object { fun getInstance(project: Project) = project.service() diff --git a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/flareChat/ChatCommunicationManager.kt b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/flareChat/ChatCommunicationManager.kt index 7662436c928..c0fe93ef98f 100644 --- a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/flareChat/ChatCommunicationManager.kt +++ b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/flareChat/ChatCommunicationManager.kt @@ -1,6 +1,6 @@ // Copyright 2025 Amazon.com, Inc. or its affiliates. All Rights Reserved. // SPDX-License-Identifier: Apache-2.0 - +@file:Suppress("BannedImports") package software.aws.toolkits.jetbrains.services.amazonq.lsp.flareChat import com.google.gson.Gson @@ -10,8 +10,10 @@ import com.intellij.openapi.project.Project import org.eclipse.lsp4j.ProgressParams import software.aws.toolkits.jetbrains.services.amazonq.lsp.AmazonQLspService import software.aws.toolkits.jetbrains.services.amazonq.lsp.flareChat.ProgressNotificationUtils.getObject +import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.GetSerializedChatResult import software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat.SEND_CHAT_COMMAND_PROMPT import java.util.UUID +import java.util.concurrent.CompletableFuture import java.util.concurrent.ConcurrentHashMap @Service(Service.Level.PROJECT) @@ -57,6 +59,11 @@ class ChatCommunicationManager { companion object { fun getInstance(project: Project) = project.service() + val pendingSerializedChatRequests = ConcurrentHashMap>() + fun completeSerializedChatResponse(requestId: String, content: String) { + pendingSerializedChatRequests.remove(requestId)?.complete(GetSerializedChatResult((content))) + } + fun convertToJsonToSendToChat(command: String, tabId: String, params: String, isPartialResult: Boolean): String = """ { @@ -73,6 +80,6 @@ class ChatCommunicationManager { "command":"$command", "params": ${if (params != null) Gson().toJson(params) else "{}"} } - """.trimIndent() + """.trimIndent() } } diff --git a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/ExtendedClientMetadata.kt b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/ExtendedClientMetadata.kt index b88bb7c51f7..ab390212952 100644 --- a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/ExtendedClientMetadata.kt +++ b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/ExtendedClientMetadata.kt @@ -16,7 +16,7 @@ data class AwsMetadata( data class AwsClientCapabilities( val q: DeveloperProfiles, - val window: WindowSettings + val window: WindowSettings, ) data class DeveloperProfiles( @@ -24,7 +24,7 @@ data class DeveloperProfiles( ) data class WindowSettings( - val showSaveFileDialog: Boolean + val showSaveFileDialog: Boolean, ) data class ClientInfoMetadata( diff --git a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/FlareChatCommands.kt b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/FlareChatCommands.kt index b0f2f4113c2..cdea3d52f02 100644 --- a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/FlareChatCommands.kt +++ b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/FlareChatCommands.kt @@ -24,7 +24,7 @@ const val CHAT_COPY_CODE_TO_CLIPBOARD = "copyToClipboard" const val CHAT_COPY_CODE_TO_CLIPBOARD_NOTIFICATION = "aws/chat/copyCodeToClipboard" const val CHAT_INSERT_TO_CURSOR = "insertToCursorPosition" const val CHAT_INSERT_TO_CURSOR_NOTIFICATION = "aws/chat/insertToCursorPosition" -const val CHAT_TAB_BAR_ACTIONS="aws/chat/tabBarAction" +const val CHAT_TAB_BAR_ACTIONS = "aws/chat/tabBarAction" const val CHAT_CREATE_PROMPT = "aws/chat/createPrompt" const val SHOW_SAVE_FILE_DIALOG_REQUEST_METHOD = "aws/showSaveFileDialog" const val GET_SERIALIZED_CHAT_REQUEST_METHOD = "aws/chat/getSerializedChat" diff --git a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/GetSerializedChatParams.kt b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/GetSerializedChatParams.kt index f16b450fcdd..d8750e9d591 100644 --- a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/GetSerializedChatParams.kt +++ b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/GetSerializedChatParams.kt @@ -5,26 +5,25 @@ package software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat data class GetSerializedChatParams( val tabId: String, - val format : String + val format: String, ) { companion object { - fun create(tabId: String, format: SerializedChatFormat): GetSerializedChatParams { - return GetSerializedChatParams(tabId, format.value) - } + fun create(tabId: String, format: SerializedChatFormat): GetSerializedChatParams = + GetSerializedChatParams(tabId, format.value) } } enum class SerializedChatFormat(val value: String) { HTML("html"), - MARKDOWN("markdown"); + MARKDOWN("markdown"), + ; - override fun toString(): String { - return name.lowercase() - } + override fun toString(): String = + name.lowercase() } data class GetSerializedChatResult( - val content: String + val content: String, ) data class GetSerializedChatRequest( @@ -35,7 +34,7 @@ data class GetSerializedChatRequest( data class GetSerializedChatResponseParams( val success: Boolean, - val result: GetSerializedChatResult + val result: GetSerializedChatResult, ) data class GetSerializedChatResponse( diff --git a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/ShowSaveFileDialogParams.kt b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/ShowSaveFileDialogParams.kt index 658e71e7afa..56d4d3c66ea 100644 --- a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/ShowSaveFileDialogParams.kt +++ b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/ShowSaveFileDialogParams.kt @@ -3,13 +3,11 @@ package software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat -import java.net.URI - data class ShowSaveFileDialogParams( val supportedFormats: List, - val defaultURI: String? + val defaultUri: String?, ) data class ShowSaveFileDialogResult( - val target: String + val targetUri: String, ) diff --git a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/TabBarActionParams.kt b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/TabBarActionParams.kt index ff928c292d3..1bbc445115c 100644 --- a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/TabBarActionParams.kt +++ b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/model/aws/chat/TabBarActionParams.kt @@ -5,31 +5,27 @@ package software.aws.toolkits.jetbrains.services.amazonq.lsp.model.aws.chat data class TabBarActionParams( val tabId: String?, - val action: String + val action: String, ) { companion object { - fun create(tabId: String?, action: TabBarAction): TabBarActionParams { - return TabBarActionParams(tabId, action.value) - } + fun create(tabId: String?, action: TabBarAction): TabBarActionParams = + TabBarActionParams(tabId, action.value) } } - enum class TabBarAction(val value: String) { - EXPORT("export"); - - override fun toString(): String { - return name.lowercase() - } + EXPORT("export"), + ; + override fun toString(): String = + name.lowercase() } data class TabBarActionResult( - val success: Boolean + val success: Boolean, ) data class TabBarActionRequest( override val command: String, override val params: TabBarActionParams, ) : ChatNotification - From fe10a85ee68e5fa56cc656c0a82e3ed23b81fcaf Mon Sep 17 00:00:00 2001 From: Manodnya Bhoite Date: Wed, 30 Apr 2025 18:03:04 -0700 Subject: [PATCH 7/8] compile --- .../jetbrains/services/amazonq/webview/BrowserConnector.kt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/plugins/amazonq/chat/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/webview/BrowserConnector.kt b/plugins/amazonq/chat/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/webview/BrowserConnector.kt index 91f7a4152f7..8b82e65f92f 100644 --- a/plugins/amazonq/chat/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/webview/BrowserConnector.kt +++ b/plugins/amazonq/chat/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/webview/BrowserConnector.kt @@ -350,7 +350,7 @@ class BrowserConnector( GET_SERIALIZED_CHAT_REQUEST_METHOD -> { val response = serializer.deserializeChatMessages(node) - AmazonQLanguageClientImpl.completeSerializedChatResponse( + ChatCommunicationManager.completeSerializedChatResponse( response.requestId, response.params.result.content ) From fc3dab78e434d2a0b000593ec82cd0136b8983d8 Mon Sep 17 00:00:00 2001 From: Manodnya Bhoite Date: Wed, 30 Apr 2025 22:54:48 -0700 Subject: [PATCH 8/8] feedback --- .../amazonq/webview/BrowserConnector.kt | 1 - .../amazonq/lsp/AmazonQLanguageClientImpl.kt | 40 ++++++------------- 2 files changed, 13 insertions(+), 28 deletions(-) diff --git a/plugins/amazonq/chat/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/webview/BrowserConnector.kt b/plugins/amazonq/chat/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/webview/BrowserConnector.kt index 8b82e65f92f..c00b81f21f9 100644 --- a/plugins/amazonq/chat/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/webview/BrowserConnector.kt +++ b/plugins/amazonq/chat/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/webview/BrowserConnector.kt @@ -27,7 +27,6 @@ import software.aws.toolkits.core.utils.getLogger import software.aws.toolkits.core.utils.warn import software.aws.toolkits.jetbrains.services.amazonq.apps.AppConnection import software.aws.toolkits.jetbrains.services.amazonq.commands.MessageSerializer -import software.aws.toolkits.jetbrains.services.amazonq.lsp.AmazonQLanguageClientImpl import software.aws.toolkits.jetbrains.services.amazonq.lsp.AmazonQLanguageServer import software.aws.toolkits.jetbrains.services.amazonq.lsp.AmazonQLspService import software.aws.toolkits.jetbrains.services.amazonq.lsp.encryption.JwtEncryptionManager diff --git a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageClientImpl.kt b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageClientImpl.kt index 3c32fc01d64..e2edc11b04a 100644 --- a/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageClientImpl.kt +++ b/plugins/amazonq/shared/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/lsp/AmazonQLanguageClientImpl.kt @@ -6,7 +6,6 @@ package software.aws.toolkits.jetbrains.services.amazonq.lsp import com.google.gson.Gson import com.intellij.notification.NotificationType import com.intellij.openapi.application.ApplicationManager -import com.intellij.openapi.application.invokeAndWaitIfNeeded import com.intellij.openapi.fileChooser.FileChooserFactory import com.intellij.openapi.fileChooser.FileSaverDescriptor import com.intellij.openapi.fileEditor.FileEditorManager @@ -124,25 +123,19 @@ class AmazonQLanguageClientImpl(private val project: Project) : AmazonQLanguageC CompletableFuture.completedFuture(OpenTabResult("")) override fun showSaveFileDialog(params: ShowSaveFileDialogParams): CompletableFuture { - val filters = mutableMapOf() - val formatMappings = listOf( - FormatMapping("markdown", "Markdown", "md"), - FormatMapping("html", "HTML", "html") - ) + val filters = mutableListOf() + val formatMappings = mapOf("markdown" to "md", "html" to "html") params.supportedFormats.forEach { format -> - formatMappings.find { it.format == format }?.let { mapping -> - filters[mapping.key] = mapping.extensions - } + formatMappings[format]?.let { filters.add(it) } } - - val saveAtUri = params.defaultUri ?: "export-chat.html" - - return CompletableFuture.supplyAsync { - return@supplyAsync invokeAndWaitIfNeeded { + val defaultUri = params.defaultUri ?: "export-chat.md" + val saveAtUri = defaultUri.substring(defaultUri.lastIndexOf("/")) + return CompletableFuture.supplyAsync( + { val descriptor = FileSaverDescriptor("Export", "Choose a location to export").apply { withFileFilter { file -> - filters.values.any { ext -> + filters.any { ext -> file.name.endsWith(".$ext") } } @@ -151,11 +144,12 @@ class AmazonQLanguageClientImpl(private val project: Project) : AmazonQLanguageC val chosenFile = FileChooserFactory.getInstance().createSaveFileDialog(descriptor, project).save(saveAtUri) chosenFile?.let { - return@invokeAndWaitIfNeeded ShowSaveFileDialogResult(chosenFile.file.path) + ShowSaveFileDialogResult(chosenFile.file.path) // TODO: Add error state shown in chat ui instead of throwing } ?: throw Error("Export failed") - } - } + }, + ApplicationManager.getApplication()::invokeLater + ) } override fun getSerializedChat(params: GetSerializedChatParams): CompletableFuture { @@ -175,9 +169,7 @@ class AmazonQLanguageClientImpl(private val project: Project) : AmazonQLanguageC result.orTimeout(30000, TimeUnit.MILLISECONDS) .whenComplete { _, error -> - if (error != null) { - ChatCommunicationManager.pendingSerializedChatRequests.remove(requestId) - } + ChatCommunicationManager.pendingSerializedChatRequests.remove(requestId) } return result @@ -240,9 +232,3 @@ class AmazonQLanguageClientImpl(private val project: Project) : AmazonQLanguageC private val LOG = getLogger() } } - -data class FormatMapping( - val format: String, - val key: String, - val extensions: String, -)