Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
- Fixed a "Warning" dialog showing raw XML content sometimes appearing at IDE startup after using a diff view

# 1.2.25 (2026-06-29)

- Fixed choice menu not appearing when option descriptions span more than 3 terminal lines
Expand Down
2 changes: 1 addition & 1 deletion pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@

<groupId>io.github.nbplugins</groupId>
<artifactId>netbeans-plugin-claude-code-gui</artifactId>
<version>1.2.25-SNAPSHOT</version>
<version>1.2.27-SNAPSHOT</version>
<packaging>nbm</packaging>
<name>Netbeans Plugin Claude Code GUI</name>
<description>NetBeans plugin that provides a GUI for Claude Code CLI — run claude code sessions directly inside the IDE.</description>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -221,13 +221,7 @@ public Writer createWriter(Difference[] conflicts) throws IOException {
// Override componentClosed() so that closing the tab without clicking
// Approve or Reject sends FILE_REJECTED — preventing Claude from hanging.
final String finalDiffTabName = diffTabName;
TopComponent diffTC = new TopComponent() {
@Override
public void componentClosed() {
super.componentClosed();
DiffTabTracker.setRejected(finalDiffTabName);
}
};
TopComponent diffTC = new DiffTopComponent(finalDiffTabName);
diffTC.setDisplayName(diffTabName);
diffTC.setLayout(new java.awt.BorderLayout());

Expand Down Expand Up @@ -305,4 +299,28 @@ public void setHandler(AsyncHandler<OpenDiffResult> handler) {
return createAsyncResponse(createErrorResult("Error opening diff: " + e.getMessage()));
}
}

/**
* Ephemeral diff-viewer tab. Must never be persisted across IDE restarts — its toolbar
* button listeners close over per-request state (file contents, async response handler)
* that is not meaningfully serializable.
*/
static final class DiffTopComponent extends TopComponent {
private final String diffTabName;

DiffTopComponent(String diffTabName) {
this.diffTabName = diffTabName;
}

@Override
public int getPersistenceType() {
return TopComponent.PERSISTENCE_NEVER;
}

@Override
public void componentClosed() {
super.componentClosed();
DiffTabTracker.setRejected(diffTabName);
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
package io.github.nbplugins.claudecodegui.mcp.tools;

import org.junit.jupiter.api.Test;
import org.openide.windows.TopComponent;

import static org.junit.jupiter.api.Assertions.assertEquals;

/**
* Unit tests for {@link OpenDiff}.
*/
class OpenDiffTest {

@Test
void diffTopComponentPersistenceTypeIsNever() {
// Reproduces the bug where the diff tab's TopComponent defaulted to PERSISTENCE_ALWAYS,
// causing the NetBeans window system to try to serialize it (and the non-serializable
// async-handler state it closes over) into a .settings file on IDE exit — producing a
// corrupted-settings "Warning" dialog with raw XML on the next startup.
OpenDiff.DiffTopComponent tc = new OpenDiff.DiffTopComponent("Diff: test");
assertEquals(TopComponent.PERSISTENCE_NEVER, tc.getPersistenceType());
}
}
Loading