diff --git a/java/debugger/openapi/resources/messages/JavaDebuggerBundle.properties b/java/debugger/openapi/resources/messages/JavaDebuggerBundle.properties
index 8eb34d48bcf8..19caed5c0b69 100644
--- a/java/debugger/openapi/resources/messages/JavaDebuggerBundle.properties
+++ b/java/debugger/openapi/resources/messages/JavaDebuggerBundle.properties
@@ -272,8 +272,6 @@ user.renderers.configurable.display.name=Java Type Renderers
async.stacktraces.configurable.display.name=Async Stack Traces
label.user.renderers.configurable.renderer.name=Renderer name:
text.user.renderers.configurable.no.renderers=No renderers
-debugger.collection.visualizer.title=Collection Presentation
-debugger.collection.visualizer.title.0=Collection Presentation: {0}
button.copy=Copy
user.renderers.configurable.button.description.copy=Copy selected renderer
label.generic.debugger.parameters.patcher.configurable.shmem=Shared &memory
diff --git a/java/plugin/plugin-content.yaml b/java/plugin/plugin-content.yaml
index df2d0ba30875..207ac5e91d7e 100644
--- a/java/plugin/plugin-content.yaml
+++ b/java/plugin/plugin-content.yaml
@@ -79,7 +79,6 @@
- name: intellij.java.performancePlugin
- name: intellij.java.terminal
- name: intellij.java.debugger.impl.backend
- - name: intellij.debugger.collections.visualizer.jvm
- name: intellij.jvm.dfa.analysis.ui
- name: lib/javac2.jar
modules:
@@ -143,6 +142,9 @@
module: intellij.java.aetherDependencyResolver
files:
- name: $MAVEN_REPOSITORY$/org/apache/maven/resolver/maven-resolver-transport-http/1/maven-resolver-transport-http-1.jar
+- name: lib/modules/intellij.debugger.collections.visualizer.jvm.backend.jar
+ contentModules:
+ - name: intellij.debugger.collections.visualizer.jvm.backend
- name: lib/modules/intellij.java.debugger.impl.frontend.jar
contentModules:
- name: intellij.java.debugger.impl.frontend
diff --git a/java/plugin/resources/META-INF/plugin.xml b/java/plugin/resources/META-INF/plugin.xml
index fdfe05ba6a56..bb8e6e78d2d6 100644
--- a/java/plugin/resources/META-INF/plugin.xml
+++ b/java/plugin/resources/META-INF/plugin.xml
@@ -59,7 +59,6 @@
-
diff --git a/platform/xdebugger-impl/backend/src/com/intellij/platform/debugger/impl/backend/BackendXDebuggerEvaluatorApi.kt b/platform/xdebugger-impl/backend/src/com/intellij/platform/debugger/impl/backend/BackendXDebuggerEvaluatorApi.kt
index 01dd59fb9b7a..444d76ff7e60 100644
--- a/platform/xdebugger-impl/backend/src/com/intellij/platform/debugger/impl/backend/BackendXDebuggerEvaluatorApi.kt
+++ b/platform/xdebugger-impl/backend/src/com/intellij/platform/debugger/impl/backend/BackendXDebuggerEvaluatorApi.kt
@@ -9,29 +9,19 @@ import com.intellij.openapi.application.readAction
import com.intellij.openapi.project.Project
import com.intellij.openapi.util.NlsContexts
import com.intellij.platform.debugger.impl.rpc.*
-import com.intellij.platform.debugger.impl.rpc.XFullValueEvaluatorDto.FullValueEvaluatorLinkAttributes
import com.intellij.xdebugger.XDebuggerBundle
import com.intellij.xdebugger.evaluation.ExpressionInfo
import com.intellij.xdebugger.evaluation.XDebuggerEvaluator
import com.intellij.xdebugger.evaluation.XDebuggerEvaluator.XEvaluationCallback
-import com.intellij.xdebugger.impl.evaluate.XEvaluationOrigin
-import com.intellij.xdebugger.frame.XNamedValue
import com.intellij.xdebugger.frame.XValue
import com.intellij.xdebugger.impl.XDebugSessionImpl
+import com.intellij.xdebugger.impl.evaluate.XEvaluationOrigin
import com.intellij.xdebugger.impl.evaluate.quick.XDebuggerDocumentOffsetEvaluator
import com.intellij.xdebugger.impl.evaluate.quick.common.ValueHintType
-import com.intellij.xdebugger.impl.pinned.items.PinToTopValue
import com.intellij.xdebugger.impl.rpc.XStackFrameId
import com.intellij.xdebugger.impl.rpc.models.*
-import com.intellij.xdebugger.impl.ui.XValueTextProvider
import com.intellij.xdebugger.impl.ui.tree.nodes.XEvaluationCallbackWithOrigin
-import fleet.rpc.core.RpcFlow
-import fleet.rpc.core.toRpc
import kotlinx.coroutines.*
-import kotlinx.coroutines.flow.Flow
-import kotlinx.coroutines.flow.distinctUntilChanged
-import kotlinx.coroutines.flow.map
-import kotlinx.coroutines.future.asDeferred
import kotlinx.coroutines.future.await
import org.jetbrains.concurrency.asDeferred
@@ -111,36 +101,6 @@ internal class BackendXDebuggerEvaluatorApi : XDebuggerEvaluatorApi {
}
}
-internal suspend fun BackendXValueModel.toXValueDto(): XValueDto {
- val xValueModel = this
- val xValue = this.xValue
- val valueMarkupFlow: RpcFlow = xValueModel.marker.toRpc()
-
- val textProvider = (xValue as? XValueTextProvider)
- ?.let {
- xValueModel.presentation.map {
- XValueTextProviderDto(
- xValue.shouldShowTextValue(),
- xValue.valueText,
- )
- }.distinctUntilChanged()
- }
-
- return XValueDto(
- xValueModel.id,
- xValue.xValueDescriptorAsync?.asDeferred(),
- canNavigateToSource = xValue.canNavigateToSource(),
- canNavigateToTypeSource = xValue.canNavigateToTypeSourceAsync().asDeferred(),
- canBeModified = xValue.modifierAsync.thenApply { modifier -> modifier != null }.asDeferred(),
- valueMarkupFlow,
- xValueModel.presentation.toRpc(),
- xValueModel.getEvaluatorDtoFlow().toRpc(),
- (xValue as? XNamedValue)?.name,
- textProvider?.toRpc(),
- (xValue as? PinToTopValue)?.pinToTopDataFuture?.asDeferred(),
- )
-}
-
internal fun BackendXValueGroupModel.toXValueGroupDto(): XValueGroupDto {
return XValueGroupDto(
id,
@@ -153,22 +113,6 @@ internal fun BackendXValueGroupModel.toXValueGroupDto(): XValueGroupDto {
)
}
-private fun BackendXValueModel.getEvaluatorDtoFlow(): Flow {
- return fullValueEvaluator.map {
- if (it == null) {
- return@map null
- }
- XFullValueEvaluatorDto(
- it.linkText,
- it.isEnabled,
- it.isShowValuePopup,
- it.linkAttributes?.let { attributes ->
- FullValueEvaluatorLinkAttributes(attributes.linkIcon?.rpcId(), attributes.linkTooltipText, attributes.shortcutSupplier?.get())
- }
- )
- }
-}
-
internal fun newXValueModel(
stackFrameModel: XStackFrameModel,
xValue: XValue,
diff --git a/platform/xdebugger-impl/backend/src/com/intellij/platform/debugger/impl/backend/BackendXValueApi.kt b/platform/xdebugger-impl/backend/src/com/intellij/platform/debugger/impl/backend/BackendXValueApi.kt
index 5c028bf079c3..1c440f0b79a6 100644
--- a/platform/xdebugger-impl/backend/src/com/intellij/platform/debugger/impl/backend/BackendXValueApi.kt
+++ b/platform/xdebugger-impl/backend/src/com/intellij/platform/debugger/impl/backend/BackendXValueApi.kt
@@ -17,6 +17,7 @@ import com.intellij.xdebugger.impl.rpc.XValueId
import com.intellij.xdebugger.impl.rpc.models.BackendXValueModel
import com.intellij.xdebugger.impl.rpc.models.findValue
import com.intellij.xdebugger.impl.rpc.models.getOrStoreGlobally
+import com.intellij.xdebugger.impl.rpc.models.toXValueDto
import fleet.rpc.core.toRpc
import kotlinx.coroutines.*
import kotlinx.coroutines.channels.*
diff --git a/platform/xdebugger-impl/src/com/intellij/xdebugger/impl/collection/visualizer/XDebuggerNodeLinkActionProvider.kt b/platform/xdebugger-impl/src/com/intellij/xdebugger/impl/collection/visualizer/XDebuggerNodeLinkActionProvider.kt
index eea851f92874..3cf7678e582c 100644
--- a/platform/xdebugger-impl/src/com/intellij/xdebugger/impl/collection/visualizer/XDebuggerNodeLinkActionProvider.kt
+++ b/platform/xdebugger-impl/src/com/intellij/xdebugger/impl/collection/visualizer/XDebuggerNodeLinkActionProvider.kt
@@ -4,7 +4,6 @@ package com.intellij.xdebugger.impl.collection.visualizer
import com.intellij.openapi.extensions.ExtensionPointName
import com.intellij.openapi.project.Project
import com.intellij.xdebugger.frame.XDebuggerTreeNodeHyperlink
-import com.intellij.xdebugger.impl.XDebuggerSuspendScopeProvider
import com.intellij.xdebugger.impl.frame.XDebugView
import com.intellij.xdebugger.impl.ui.tree.nodes.XValueNodeImpl
import kotlinx.coroutines.CoroutineScope
@@ -23,9 +22,6 @@ interface XDebuggerNodeLinkActionProvider {
/**
* Compute a hyperlink for the given [node].
*
- * Passed [CoroutineScope] restricts the lifetime of the link action to a current debugger session state.
- * Refer to [XDebuggerSuspendScopeProvider.provideSuspendScope] for more details.
- *
* @see [XDebuggerNodeLinkActionProvider.computeHyperlink]
*/
suspend fun CoroutineScope.provideHyperlink(project: Project, node: XValueNodeImpl): XDebuggerTreeNodeHyperlink?
@@ -37,7 +33,8 @@ interface XDebuggerNodeLinkActionProvider {
fun computeHyperlink(project: Project, node: XValueNodeImpl) {
if (node.hasLinks()) return
- val scope = XDebugView.getSessionProxy(node.tree)?.currentSuspendContextCoroutineScope?: return
+ val sessionProxy = XDebugView.getSessionProxy(node.tree) ?: return
+ val scope = sessionProxy.currentSuspendContextCoroutineScope ?: return
scope.launch(Dispatchers.Default) {
for (provider in EP_NAME.extensionList) {
diff --git a/platform/xdebugger-impl/src/com/intellij/xdebugger/impl/rpc/models/BackendXValueModel.kt b/platform/xdebugger-impl/src/com/intellij/xdebugger/impl/rpc/models/BackendXValueModel.kt
index 1e5b34ddb2fc..b77c7c0d3b48 100644
--- a/platform/xdebugger-impl/src/com/intellij/xdebugger/impl/rpc/models/BackendXValueModel.kt
+++ b/platform/xdebugger-impl/src/com/intellij/xdebugger/impl/rpc/models/BackendXValueModel.kt
@@ -1,11 +1,16 @@
// Copyright 2000-2025 JetBrains s.r.o. and contributors. Use of this source code is governed by the Apache 2.0 license.
package com.intellij.xdebugger.impl.rpc.models
+import com.intellij.ide.ui.icons.rpcId
import com.intellij.openapi.components.Service
import com.intellij.openapi.components.service
import com.intellij.openapi.project.Project
+import com.intellij.platform.debugger.impl.rpc.XFullValueEvaluatorDto
+import com.intellij.platform.debugger.impl.rpc.XFullValueEvaluatorDto.FullValueEvaluatorLinkAttributes
+import com.intellij.platform.debugger.impl.rpc.XValueDto
import com.intellij.platform.debugger.impl.rpc.XValueMarkerDto
import com.intellij.platform.debugger.impl.rpc.XValueSerializedPresentation
+import com.intellij.platform.debugger.impl.rpc.XValueTextProviderDto
import com.intellij.platform.kernel.ids.BackendValueIdType
import com.intellij.platform.kernel.ids.deleteValueById
import com.intellij.platform.kernel.ids.findValueById
@@ -13,16 +18,24 @@ import com.intellij.platform.kernel.ids.storeValueGlobally
import com.intellij.util.AwaitCancellationAndInvoke
import com.intellij.util.awaitCancellationAndInvoke
import com.intellij.xdebugger.frame.XFullValueEvaluator
+import com.intellij.xdebugger.frame.XNamedValue
import com.intellij.xdebugger.frame.XValue
import com.intellij.xdebugger.frame.XValuePlace
import com.intellij.xdebugger.impl.XDebugSessionImpl
+import com.intellij.xdebugger.impl.pinned.items.PinToTopValue
import com.intellij.xdebugger.impl.rpc.XValueId
+import com.intellij.xdebugger.impl.ui.XValueTextProvider
import com.intellij.xdebugger.impl.ui.tree.ValueMarkup
+import fleet.rpc.core.RpcFlow
+import fleet.rpc.core.toRpc
import kotlinx.collections.immutable.toImmutableSet
import kotlinx.coroutines.CoroutineScope
+import kotlinx.coroutines.Deferred
import kotlinx.coroutines.channels.BufferOverflow
import kotlinx.coroutines.flow.*
+import kotlinx.coroutines.future.asDeferred
import org.jetbrains.annotations.ApiStatus
+import org.jetbrains.concurrency.asDeferred
/**
* Model which holds reference to the [XValue].
@@ -112,6 +125,57 @@ class BackendXValueModel internal constructor(
}
}
+@ApiStatus.Internal
+suspend fun BackendXValueModel.toXValueDto(): XValueDto {
+ val xValueModel = this
+ val xValue = this.xValue
+ val valueMarkupFlow: RpcFlow = xValueModel.marker.toRpc()
+
+ val textProvider = getTextProviderFlow(xValue, xValueModel)
+
+ return XValueDto(
+ xValueModel.id,
+ xValue.xValueDescriptorAsync?.asDeferred(),
+ canNavigateToSource = xValue.canNavigateToSource(),
+ canNavigateToTypeSource = xValue.canNavigateToTypeSourceAsync().asDeferred(),
+ canBeModified = xValue.modifierAsync.thenApply { modifier -> modifier != null }.asDeferred(),
+ valueMarkupFlow,
+ xValueModel.presentation.toRpc(),
+ xValueModel.getEvaluatorDtoFlow().toRpc(),
+ (xValue as? XNamedValue)?.name,
+ textProvider?.toRpc(),
+ (xValue as? PinToTopValue)?.pinToTopDataFuture?.asDeferred(),
+ )
+}
+
+private fun BackendXValueModel.getEvaluatorDtoFlow(): Flow {
+ return fullValueEvaluator.map {
+ if (it == null) {
+ return@map null
+ }
+ XFullValueEvaluatorDto(
+ it.linkText,
+ it.isEnabled,
+ it.isShowValuePopup,
+ it.linkAttributes?.let { attributes ->
+ FullValueEvaluatorLinkAttributes(attributes.linkIcon?.rpcId(), attributes.linkTooltipText, attributes.shortcutSupplier?.get())
+ }
+ )
+ }
+}
+
+private fun getTextProviderFlow(
+ xValue: XValue,
+ xValueModel: BackendXValueModel,
+): Flow? = (xValue as? XValueTextProvider)
+ ?.let {
+ xValueModel.presentation.map {
+ XValueTextProviderDto(
+ xValue.shouldShowTextValue(),
+ xValue.valueText,
+ )
+ }.distinctUntilChanged()
+ }
@ApiStatus.Internal
@Service(Service.Level.PROJECT)
diff --git a/platform/xdebugger-impl/src/com/intellij/xdebugger/impl/ui/tree/nodes/XValueNodeImpl.java b/platform/xdebugger-impl/src/com/intellij/xdebugger/impl/ui/tree/nodes/XValueNodeImpl.java
index e3619b6f251e..41a814e9f40d 100644
--- a/platform/xdebugger-impl/src/com/intellij/xdebugger/impl/ui/tree/nodes/XValueNodeImpl.java
+++ b/platform/xdebugger-impl/src/com/intellij/xdebugger/impl/ui/tree/nodes/XValueNodeImpl.java
@@ -173,7 +173,7 @@ public class XValueNodeImpl extends XValueContainerNode implements XValu
public void addAdditionalHyperlink(@NotNull XDebuggerTreeNodeHyperlink link) {
invokeNodeUpdate(() -> {
if (!myAdditionalHyperLink.compareAndSet(null, link)) {
- LOG.warn("Additional hyperlink already set; having more than one is discouraged");
+ LOG.warn("Additional hyperlink already set; having more than one is not supported");
}
fireNodeChanged();
});