Skip to content

Commit ed89600

Browse files
authored
Merge branch 'main' into transformPupTesting
2 parents 21a3414 + ae69735 commit ed89600

File tree

32 files changed

+808
-231
lines changed

32 files changed

+808
-231
lines changed

.changes/3.58.json

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
{
2+
"date" : "2025-03-06",
3+
"version" : "3.58",
4+
"entries" : [ {
5+
"type" : "bugfix",
6+
"description" : "Amazon Q: Fix data isolation between tabs to prevent interference when using /doc in multiple tabs"
7+
}, {
8+
"type" : "removal",
9+
"description" : "The Amazon Q inline suggestion popup goes back to being under the suggestions and is always showing."
10+
} ]
11+
}
Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
{
2+
"type" : "bugfix",
3+
"description" : "fix Q chat request timeout"
4+
}

CHANGELOG.md

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,7 @@
1+
# _3.58_ (2025-03-06)
2+
- **(Bug Fix)** Amazon Q: Fix data isolation between tabs to prevent interference when using /doc in multiple tabs
3+
- **(Removal)** The Amazon Q inline suggestion popup goes back to being under the suggestions and is always showing.
4+
15
# _3.57_ (2025-02-28)
26
- **(Bug Fix)** Fix suggestion not visible in remote for 2024.3
37
- **(Bug Fix)** /test: update capability card text

CONTRIBUTING.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,7 @@ reported the issue. Please try to include as much information as you can. Detail
3131
brew install dotnet@6
3232
```
3333
* If Gradle cannot find `dotnet`, run `./gradlew --stop` and `./gradlew projects` to reload the daemon. Note that this should be done in your terminal as invoking Gradle through the IDE will use the IDE's cached PATH.
34+
* It is recommended to [launch your IDE from the terminal](https://www.jetbrains.com/help/idea/working-with-the-ide-features-from-command-line.html) due to a known issue with Gradle/Java 21 where the Gradle daemon does not respect your PATH variable when the IDE is started from the desktop/Toolbox.
3435
3536
### Instructions
3637

buildspec/linuxIntegrationTests.yml

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -15,10 +15,6 @@ phases:
1515
install:
1616
commands:
1717
- startDocker.sh
18-
# login to DockerHub so we don't get throttled
19-
- export DOCKER_USERNAME=`echo $DOCKER_HUB_TOKEN | jq -r '.username'`
20-
- export DOCKER_PASSWORD=`echo $DOCKER_HUB_TOKEN | jq -r '.password'`
21-
- docker login --username $DOCKER_USERNAME --password $DOCKER_PASSWORD || true
2218
# should probably be managed as an extension/rule in any tests that need a screen available
2319
- /usr/bin/Xvfb :22 -screen 0 1920x1080x24 &
2420

buildspec/linuxUiTests.yml

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -21,11 +21,6 @@ phases:
2121
commands:
2222
- dnf install -y marco mate-media e2fsprogs
2323
- startDesktop.sh
24-
25-
# login to DockerHub so we don't get throttled
26-
- export DOCKER_USERNAME=`echo $DOCKER_HUB_TOKEN | jq -r '.username'`
27-
- export DOCKER_PASSWORD=`echo $DOCKER_HUB_TOKEN | jq -r '.password'`
28-
- docker login --username $DOCKER_USERNAME --password $DOCKER_PASSWORD || true
2924
- export PATH="$PATH:$HOME/.dotnet/tools"
3025
- dotnet codeartifact-creds install
3126

gradle.properties

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22
# SPDX-License-Identifier: Apache-2.0
33

44
# Toolkit Version
5-
toolkitVersion=3.58-SNAPSHOT
5+
toolkitVersion=3.59-SNAPSHOT
66

77
# Publish Settings
88
publishToken=

gradle/libs.versions.toml

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -24,10 +24,10 @@ kotlin = "2.0.0"
2424
kotlinCoroutines = "1.8.0"
2525
mockito = "5.12.0"
2626
mockitoKotlin = "5.4.0"
27-
mockk = "1.13.10"
27+
mockk = "1.13.17"
2828
nimbus-jose-jwt = "9.40"
2929
node-gradle = "7.0.2"
30-
telemetryGenerator = "1.0.297"
30+
telemetryGenerator = "1.0.307"
3131
testLogger = "4.0.0"
3232
testRetry = "1.5.10"
3333
# test-only; platform provides slf4j transitively at runtime

plugins/amazonq/chat/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonq/webview/BrowserConnector.kt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -67,7 +67,7 @@ class BrowserConnector(
6767
it.elementId(source.asText())
6868
}
6969
} else if (module != null && trigger != null) {
70-
Telemetry.toolkit.openModule.use {
70+
Telemetry.toolkit.willOpenModule.use {
7171
it.module(module.asText())
7272
it.source(trigger.asText())
7373
}

plugins/amazonq/chat/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonqCodeTest/CodeWhispererUTGChatManager.kt

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -55,6 +55,7 @@ import software.aws.toolkits.jetbrains.utils.isQConnected
5555
import software.aws.toolkits.resources.message
5656
import software.aws.toolkits.telemetry.AmazonqTelemetry
5757
import software.aws.toolkits.telemetry.MetricResult
58+
import software.aws.toolkits.telemetry.Status
5859
import java.io.ByteArrayInputStream
5960
import java.io.ByteArrayOutputStream
6061
import java.io.File
@@ -583,7 +584,8 @@ class CodeWhispererUTGChatManager(val project: Project, private val cs: Coroutin
583584
artifactsUploadDuration = session.artifactUploadDuration,
584585
buildPayloadBytes = session.srcPayloadSize,
585586
buildZipFileBytes = session.srcZipFileSize,
586-
requestId = session.startTestGenerationRequestId
587+
requestId = session.startTestGenerationRequestId,
588+
status = if (e.message == message("testgen.message.cancelled")) Status.CANCELLED else Status.FAILED,
587589
)
588590
session.isGeneratingTests = false
589591
} finally {

plugins/amazonq/chat/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonqCodeTest/controller/CodeTestChatController.kt

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -98,6 +98,7 @@ import software.aws.toolkits.telemetry.AmazonqTelemetry
9898
import software.aws.toolkits.telemetry.FeatureId
9999
import software.aws.toolkits.telemetry.InteractionType
100100
import software.aws.toolkits.telemetry.MetricResult
101+
import software.aws.toolkits.telemetry.Status
101102
import software.aws.toolkits.telemetry.UiTelemetry
102103
import java.io.File
103104
import java.nio.file.Files
@@ -310,7 +311,8 @@ class CodeTestChatController(
310311
credentialStartUrl = getStartUrl(project),
311312
result = MetricResult.Succeeded,
312313
perfClientLatency = (Instant.now().toEpochMilli() - session.startTimeOfTestGeneration),
313-
requestId = id
314+
requestId = id,
315+
status = Status.ACCEPTED,
314316
)
315317
}
316318
session.isGeneratingTests = false
@@ -682,7 +684,8 @@ class CodeTestChatController(
682684
artifactsUploadDuration = session.artifactUploadDuration,
683685
buildPayloadBytes = session.srcPayloadSize,
684686
buildZipFileBytes = session.srcZipFileSize,
685-
requestId = session.startTestGenerationRequestId
687+
requestId = session.startTestGenerationRequestId,
688+
status = Status.ACCEPTED,
686689
)
687690
codeTestChatHelper.addAnswer(
688691
CodeTestChatMessageContent(
@@ -878,7 +881,8 @@ class CodeTestChatController(
878881
artifactsUploadDuration = session.artifactUploadDuration,
879882
buildPayloadBytes = session.srcPayloadSize,
880883
buildZipFileBytes = session.srcZipFileSize,
881-
requestId = session.startTestGenerationRequestId
884+
requestId = session.startTestGenerationRequestId,
885+
status = Status.REJECTED,
882886
)
883887
sessionCleanUp(message.tabId)
884888
}

plugins/amazonq/chat/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonqDoc/controller/DocController.kt

Lines changed: 28 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -132,9 +132,8 @@ class DocController(
132132
private val authController: AuthController = AuthController(),
133133
) : InboundAppMessagesHandler {
134134
val messenger = context.messagesFromAppToUi
135-
var mode: Mode = Mode.CREATE
136135
val toolWindow = ToolWindowManager.getInstance(context.project).getToolWindow(AmazonQToolWindowFactory.WINDOW_ID)
137-
var docGenerationTask = DocGenerationTask()
136+
private val docGenerationTasks = DocGenerationTasks()
138137

139138
override suspend fun processPromptChatMessage(message: IncomingDocMessage.ChatPrompt) {
140139
handleChat(
@@ -148,7 +147,7 @@ class DocController(
148147
}
149148

150149
override suspend fun processTabRemovedMessage(message: IncomingDocMessage.TabRemoved) {
151-
docGenerationTask.reset()
150+
docGenerationTasks.deleteTask(message.tabId)
152151
chatSessionStorage.deleteSession(message.tabId)
153152
}
154153

@@ -160,6 +159,7 @@ class DocController(
160159

161160
override suspend fun processFollowupClickedMessage(message: IncomingDocMessage.FollowupClicked) {
162161
val session = getSessionInfo(message.tabId)
162+
val docGenerationTask = docGenerationTasks.getTask(message.tabId)
163163

164164
session.preloader(message.followUp.pillText, messenger) // also stores message in session history
165165

@@ -173,7 +173,7 @@ class DocController(
173173
FollowUpTypes.CLOSE_SESSION -> closeSession(message.tabId)
174174
FollowUpTypes.CREATE_DOCUMENTATION -> {
175175
docGenerationTask.interactionType = DocInteractionType.GENERATE_README
176-
mode = Mode.CREATE
176+
docGenerationTask.mode = Mode.CREATE
177177
promptForDocTarget(message.tabId)
178178
}
179179

@@ -183,19 +183,19 @@ class DocController(
183183
}
184184

185185
FollowUpTypes.CANCEL_FOLDER_SELECTION -> {
186-
docGenerationTask.folderLevel = DocFolderLevel.ENTIRE_WORKSPACE
186+
docGenerationTask.reset()
187187
newTask(message.tabId)
188188
}
189189

190-
FollowUpTypes.PROCEED_FOLDER_SELECTION -> if (mode == Mode.EDIT) makeChanges(message.tabId) else onDocsGeneration(message)
190+
FollowUpTypes.PROCEED_FOLDER_SELECTION -> if (docGenerationTask.mode == Mode.EDIT) makeChanges(message.tabId) else onDocsGeneration(message)
191191
FollowUpTypes.ACCEPT_CHANGES -> {
192192
docGenerationTask.userDecision = DocUserDecision.ACCEPT
193193
sendDocAcceptanceTelemetry(message.tabId)
194194
acceptChanges(message)
195195
}
196196

197197
FollowUpTypes.MAKE_CHANGES -> {
198-
mode = Mode.EDIT
198+
docGenerationTask.mode = Mode.EDIT
199199
makeChanges(message.tabId)
200200
}
201201

@@ -206,12 +206,12 @@ class DocController(
206206
}
207207

208208
FollowUpTypes.SYNCHRONIZE_DOCUMENTATION -> {
209-
mode = Mode.SYNC
209+
docGenerationTask.mode = Mode.SYNC
210210
promptForDocTarget(message.tabId)
211211
}
212212

213213
FollowUpTypes.EDIT_DOCUMENTATION -> {
214-
mode = Mode.EDIT
214+
docGenerationTask.mode = Mode.EDIT
215215
docGenerationTask.interactionType = DocInteractionType.EDIT_README
216216
promptForDocTarget(message.tabId)
217217
}
@@ -241,7 +241,6 @@ class DocController(
241241
session.sessionState.token?.cancel()
242242
}
243243

244-
docGenerationTask.reset()
245244
newTask(message.tabId)
246245
}
247246

@@ -307,13 +306,14 @@ class DocController(
307306

308307
private suspend fun promptForDocTarget(tabId: String) {
309308
val session = getSessionInfo(tabId)
309+
val docGenerationTask = docGenerationTasks.getTask(tabId)
310310

311311
val currentSourceFolder = session.context.selectedSourceFolder
312312

313313
try {
314314
messenger.sendFolderConfirmationMessage(
315315
tabId = tabId,
316-
message = if (mode == Mode.CREATE) message("amazonqDoc.prompt.create.confirmation") else message("amazonqDoc.prompt.update"),
316+
message = if (docGenerationTask.mode == Mode.CREATE) message("amazonqDoc.prompt.create.confirmation") else message("amazonqDoc.prompt.update"),
317317
folderPath = currentSourceFolder.name,
318318
followUps = listOf(
319319
FollowUp(
@@ -452,6 +452,9 @@ class DocController(
452452
var session: DocSession? = null
453453
try {
454454
session = getSessionInfo(tabId)
455+
val docGenerationTask = docGenerationTasks.getTask(tabId)
456+
docGenerationTask.mode = Mode.NONE
457+
455458
logger.debug { "$FEATURE_NAME: Session created with id: ${session.tabID}" }
456459

457460
val credentialState = authController.getAuthNeededStates(context.project).amazonQ
@@ -528,7 +531,7 @@ class DocController(
528531
}
529532

530533
private suspend fun newTask(tabId: String) {
531-
docGenerationTask = DocGenerationTask()
534+
docGenerationTasks.deleteTask(tabId)
532535
chatSessionStorage.deleteSession(tabId)
533536

534537
messenger.sendAnswer(
@@ -577,7 +580,7 @@ class DocController(
577580
)
578581

579582
messenger.sendChatInputEnabledMessage(tabId = tabId, enabled = false)
580-
docGenerationTask.reset()
583+
docGenerationTasks.deleteTask(tabId)
581584
}
582585

583586
private suspend fun provideFeedbackAndRegenerateCode(tabId: String) {
@@ -728,6 +731,7 @@ class DocController(
728731
message: String,
729732
) {
730733
var session: DocSession? = null
734+
val docGenerationTask = docGenerationTasks.getTask(tabId)
731735
try {
732736
logger.debug { "$FEATURE_NAME: Processing message: $message" }
733737
session = getSessionInfo(tabId)
@@ -746,7 +750,7 @@ class DocController(
746750

747751
when (session.sessionState.phase) {
748752
SessionStatePhase.CODEGEN -> {
749-
onCodeGeneration(session, message, tabId, mode)
753+
onCodeGeneration(session, message, tabId, docGenerationTask.mode)
750754
}
751755

752756
else -> null
@@ -756,7 +760,7 @@ class DocController(
756760
is PrepareDocGenerationState -> state.filePaths
757761
else -> emptyList()
758762
}
759-
sendDocGenerationTelemetry(filePaths, session)
763+
sendDocGenerationTelemetry(filePaths, session, docGenerationTask)
760764
broadcastQEvent(QFeatureEvent.INVOCATION)
761765

762766
if (filePaths.isNotEmpty()) {
@@ -767,7 +771,7 @@ class DocController(
767771
} catch (err: Exception) {
768772
// For non edit mode lock the chat input until they explicitly click one of the follow-ups
769773
var isEnableChatInput = false
770-
if (err is DocException && Mode.EDIT == mode) {
774+
if (err is DocException && docGenerationTask.mode == Mode.EDIT) {
771775
isEnableChatInput = err.remainingIterations != null && err.remainingIterations > 0
772776
}
773777

@@ -779,15 +783,16 @@ class DocController(
779783
messenger.sendUpdatePromptProgress(tabId = followUpMessage.tabId, inProgress(progress = 10, message("amazonqDoc.progress_message.scanning")))
780784

781785
val session = getSessionInfo(followUpMessage.tabId)
786+
val docGenerationTask = docGenerationTasks.getTask(followUpMessage.tabId)
782787

783788
messenger.sendAnswer(
784-
message = docGenerationProgressMessage(DocGenerationStep.UPLOAD_TO_S3, this.mode),
789+
message = docGenerationProgressMessage(DocGenerationStep.UPLOAD_TO_S3, docGenerationTask.mode),
785790
messageType = DocMessageType.AnswerPart,
786791
tabId = followUpMessage.tabId,
787792
)
788793

789794
try {
790-
val sessionMessage: String = when (mode) {
795+
val sessionMessage: String = when (docGenerationTask.mode) {
791796
Mode.CREATE -> message("amazonqDoc.session.create")
792797
else -> message("amazonqDoc.session.sync")
793798
}
@@ -821,10 +826,10 @@ class DocController(
821826
return
822827
}
823828

824-
sendDocGenerationTelemetry(filePaths, session)
829+
sendDocGenerationTelemetry(filePaths, session, docGenerationTask)
825830

826831
messenger.sendAnswer(
827-
message = docGenerationProgressMessage(DocGenerationStep.COMPLETE, mode),
832+
message = docGenerationProgressMessage(DocGenerationStep.COMPLETE, docGenerationTask.mode),
828833
messageType = DocMessageType.AnswerPart,
829834
tabId = followUpMessage.tabId,
830835
)
@@ -907,7 +912,6 @@ class DocController(
907912

908913
private suspend fun retryRequests(tabId: String) {
909914
var session: DocSession? = null
910-
docGenerationTask = DocGenerationTask()
911915
try {
912916
messenger.sendAsyncEventProgress(
913917
tabId = tabId,
@@ -954,6 +958,7 @@ class DocController(
954958
val session = getSessionInfo(tabId)
955959
val currentSourceFolder = session.context.selectedSourceFolder
956960
val projectRoot = session.context.projectRoot
961+
val docGenerationTask = docGenerationTasks.getTask(tabId)
957962

958963
withContext(EDT) {
959964
messenger.sendAnswer(
@@ -1017,7 +1022,7 @@ class DocController(
10171022
}
10181023
}
10191024

1020-
private fun sendDocGenerationTelemetry(filePaths: List<NewFileZipInfo>, session: DocSession) {
1025+
private fun sendDocGenerationTelemetry(filePaths: List<NewFileZipInfo>, session: DocSession, docGenerationTask: DocGenerationTask) {
10211026
docGenerationTask.conversationId = session.conversationId
10221027
val (totalGeneratedChars, totalGeneratedLines, totalGeneratedFiles) = session.countedGeneratedContent(filePaths, docGenerationTask.interactionType)
10231028
docGenerationTask.numberOfGeneratedChars = totalGeneratedChars
@@ -1030,6 +1035,7 @@ class DocController(
10301035

10311036
private fun sendDocAcceptanceTelemetry(tabId: String) {
10321037
val session = getSessionInfo(tabId)
1038+
val docGenerationTask = docGenerationTasks.getTask(tabId)
10331039
var filePaths: List<NewFileZipInfo> = emptyList()
10341040

10351041
when (val state = session.sessionState) {

plugins/amazonq/chat/jetbrains-community/src/software/aws/toolkits/jetbrains/services/amazonqDoc/controller/DocControllerExtensions.kt

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -31,7 +31,7 @@ suspend fun DocController.onCodeGeneration(session: DocSession, message: String,
3131
messenger.sendAsyncEventProgress(tabId, inProgress = true)
3232
messenger.sendUpdatePromptProgress(tabId, inProgress(progress = 10, message("amazonqDoc.progress_message.scanning")))
3333
messenger.sendAnswer(
34-
message = docGenerationProgressMessage(DocGenerationStep.UPLOAD_TO_S3, this.mode),
34+
message = docGenerationProgressMessage(DocGenerationStep.UPLOAD_TO_S3, mode),
3535
messageType = DocMessageType.AnswerPart,
3636
tabId = tabId,
3737
)
@@ -108,7 +108,7 @@ suspend fun DocController.onCodeGeneration(session: DocSession, message: String,
108108
messenger.sendAnswer(
109109
tabId = tabId,
110110
messageType = DocMessageType.Answer,
111-
message = if (this.mode === Mode.CREATE) {
111+
message = if (mode === Mode.CREATE) {
112112
message("amazonqDoc.answer.readmeCreated")
113113
} else {
114114
"${message("amazonqDoc.answer.readmeUpdated")} ${message("amazonqDoc.answer.codeResult")}"

0 commit comments

Comments
 (0)