Skip to content

Editor Apply button, double-click to edit, and unsaved-change guard (1.4.0) - #10

Merged
yingbo merged 9 commits into
mainfrom
claude/charmrun-publisher-verify-qz7e79
Sep 11, 2026
Merged

yingbo merged 9 commits into
mainfrom
claude/charmrun-publisher-verify-qz7e79

Conversation

@yingbo

@yingbo yingbo commented Sep 10, 2026 •

Copy link
Copy Markdown
Owner

Summary

Adds an Apply button to the run configuration editor, makes double-click open a configuration from the sidebar, and puts a confirmation between those two conveniences and losing unsaved edits. Also corrects documentation that had drifted from the code.

Version is bumped to 1.4.0. No tag is created here, so nothing publishes until v1.4.0 is tagged.

Editor: Apply and Save & Close

The editor could only be saved by closing it, so tweaking a configuration and re-running it meant reopening the editor each time.

  • Apply writes the form to launch.json and leaves the panel open, with a brief "Changes applied" note.
  • Save is renamed Save & Close so the two are distinguishable. Its behaviour is unchanged.
  • Both go through a single ConfigEditorProvider.persist(), which clears the isNew flag after the first write. Repeated Apply clicks on a new configuration therefore add it once and update it in place afterwards, instead of appending duplicates.

Tree: double-click to edit

ConfigTreeItem now carries a command that fires on every click. VS Code exposes no double-click event for tree views, so the handler measures the gap between two clicks on the same item within a 500 ms window.

One edge case is handled: when workbench.list.openMode is set to doubleClick, VS Code already withholds the command until the second click, so the handler opens the editor on the first invocation rather than demanding two double-clicks.

Unsaved-change guard

Cancel disposed the panel immediately, and opening another configuration re-rendered the same panel, so either one silently discarded whatever was typed. That was survivable when opening the editor took a context-menu click; double-click makes landing on the wrong row easy.

The extension cannot read the form, so the webview compares it against the last saved snapshot and posts dirtyState when that changes. Input and change events cover every field including rows added after load, button-driven mutations are picked up on the next tick, and the browse dialogs re-check when they write a path back. Apply re-baselines.

The provider consults the flag before Cancel closes the panel and before open() renders a different configuration, showing a modal with a Discard Changes action. Re-opening the configuration already on screen now reveals the panel untouched, so a stray double-click on the open configuration cannot cost anything.

Known limitation: VS Code cannot veto a webview panel's disposal, so closing the editor tab still discards without a prompt. This is recorded in worklog.md.

Documentation corrections

Several documents had drifted from the code:

  • FEATURE_SPEC.md and worklog.md described configurations as living in a private .vscode/python-run-configs.json. That has not been true since storage moved into .vscode/launch.json as debugpy entries tagged charmrunManaged.
  • docs/pycharm-comparison.md still listed before-launch tasks as a gap against PyCharm, but that shipped in 1.1.0.
  • worklog.md claimed 12 registered commands where 15 are registered; openConfigurationFlow and adoptLaunchConfiguration had never been listed.
  • docs/PUBLISHING.md stopped at ovsx create-namespace, which only grants contributor rights. Without a namespace owner every published version carries the "not a verified publisher" warning on open-vsx.org, so the ownership-claim step is now documented.

Authorship rules

AGENTS.md banned Co-Authored-By lines, but that was narrow enough to read as the only prohibited trailer, and other attribution slipped through. The rule is now stated once and completely: no attribution trailer, footer, badge or marker of any kind, anywhere, and the commit author and committer are always the repository owner. CLAUDE.md carries the same rule, and CONTRIBUTING.md mirrors the summary.

Screenshot

main already replaced the hand-drawn mockup with a render of the real webview, which was the right call. That render predates this branch, so it still shows a lone Save button.

This updates it to the current editor and adds scripts/screenshot.mjs so it can be regenerated on demand rather than by hand. The script bundles the editor's own HTML generator, feeds it a sample configuration, supplies the theme variables and webview API that VS Code injects at runtime, and screenshots the result in headless Chromium before framing it with the configurations sidebar. Regenerating is one command, documented in CONTRIBUTING.md.

playwright-core stays out of package.json since only this script needs it, and scripts/ is excluded from the packaged VSIX.

Testing

Typecheck, lint, and the esbuild bundle pass.

The dirty tracking was verified by driving the generated form in headless Chromium, since an extension host is not available in this environment. Eight checks, all passing: clean on load, dirty after an edit, clean again when the edit is reverted, an empty new env row stays clean while filling its key goes dirty, and Cancel carries the right state both before and after Apply.

Not yet verified by hand: how the modal reads and how the double-click timing feels in a real Extension Development Host. Worth a pass with F5 before merging.

Note on history

This branch was built before main was force-updated to a rewritten history, so it originally shared no ancestor with it. It has been rebased onto the current main; the only conflict was the screenshot, resolved in favour of the version that shows the new buttons. main's README install section is preserved intact.

The Open VSX setup steps stopped at 'ovsx create-namespace', which only
grants contributor rights. Without an owner the namespace is unverified
and every published version carries the 'not a verified publisher'
warning on open-vsx.org. Add the ownership-claim step (GitHub issue on
EclipseFdn/open-vsx.org, Option 1) and explain why the warning appears.
The configuration editor could only be saved by closing it, so tweaking a
config and re-running meant reopening the editor each time. Add an Apply
button that writes the form to launch.json and leaves the panel open, and
rename Save to Save & Close so the two are distinguishable.

Saving is factored into ConfigEditorProvider.persist(), which clears the
isNew flag after the first write. Repeated Apply clicks on a new
configuration therefore add it once and update it thereafter, instead of
appending duplicates.

Tree items now carry a command so a double-click opens the editor. VS Code
exposes no double-click event for tree views, so the handler measures the
gap between two clicks on the same item. When workbench.list.openMode is
set to doubleClick, VS Code already withholds the command until the second
click, so the handler opens the editor on the first invocation instead.
Bump the version to 1.4.0 for the Apply button and double-click-to-edit
changes, and date the changelog section that was left as Unreleased.

FEATURE_SPEC.md still described the editor as offering only Save and
Cancel, and the configurations panel without a double-click action; both
sections now match the shipped behaviour.

worklog.md claimed 12 registered commands while 15 are registered. Add
the new charmrun.treeItemActivated row along with openConfigurationFlow
and adoptLaunchConfiguration, which were already missing, correct the
count, and describe the editor and tree changes in a 1.4.0 section
alongside the existing per-version notes.
FEATURE_SPEC.md and worklog.md still described configurations as living in
a private .vscode/python-run-configs.json file. That has not been true
since 0b84b9b, which moved storage into .vscode/launch.json as debugpy
entries tagged charmrunManaged.

Rewrite the storage section with the shape the code actually writes,
including the charmrun-prefixed keys and the fact that unmanaged entries
are left alone, and fix the multi-root and data-model references.

No code change; the version stays at 1.4.0.
docs/pycharm-comparison.md still listed before-launch tasks as a gap
against PyCharm, but that shipped in 1.1.0 as the Before Launch section
and charmrunPreRun. Rewrite the entry the way the env-file gap was
already rewritten, and note in the intro that two of the five gaps are
closed.

docs/ARCHITECTURE.md gains the UI surfaces added since it was written:
double-click to edit on the tree, and the editor's Apply / Save & Close /
Cancel buttons.
docs/images/config-editor.png dated from March and was four releases
behind: it showed a Save button with no Apply, and none of the Before
Launch section, Env File field, or multi-line argument editors added in
1.1.0 through 1.4.0. It was also a hand-drawn mockup, so it drifted from
the code every time the editor changed.

Replace it with a render of the real markup. The editor webview is plain
HTML from configEditorHtml.ts, so scripts/screenshot.mjs bundles that
generator, feeds it a sample configuration, supplies the theme variables
and webview API that VS Code injects at runtime, and screenshots the
result in headless Chromium before framing it with the configurations
sidebar.

Regenerating is now a single command, documented in CONTRIBUTING.md, so
the image can be refreshed with the UI instead of going stale. The script
needs playwright-core, which stays out of package.json since nothing else
uses it, and scripts/ is excluded from the packaged VSIX.
Cancel disposed the panel immediately, and opening another configuration
re-rendered the same panel, so either one silently threw away whatever
was typed. That was survivable when opening the editor took a
context-menu click; double-click makes landing on the wrong row easy,
and Apply sets the expectation that saving is explicit.

The extension cannot read the form, so the webview compares it against
the last saved snapshot and posts dirtyState when that changes. Input
and change events cover every field, including rows added after load;
button-driven mutations are picked up on the next tick, and the browse
dialogs re-check when they write a path back. Apply re-baselines.

ConfigEditorProvider consults the flag before Cancel closes the panel
and before open() renders a different configuration, showing a modal
with a Discard Changes action. Re-opening the configuration already on
screen now reveals the panel untouched rather than re-rendering, so a
stray double-click on the open configuration cannot cost anything.

VS Code cannot veto a webview panel's disposal, so closing the tab still
discards without a prompt; that limitation is noted in worklog.md.

Also declare charmrun.treeItemActivated in the manifest and hide it from
the palette, matching how the other tree-only commands are declared.

Verified by driving the generated form in headless Chromium: a clean
load, an edit, an edit reverted, an added env row, Cancel before and
after Apply all report the expected state.
README.md and docs/ARCHITECTURE.md described the editor's buttons but not
the confirmation that now stands between Cancel, or switching
configurations, and losing edits.

The 1.4.0 changelog heading was dated the day the section was opened.
Remote tags stop at v1.3.0, so the release has not gone out and work
continued past that date; move it to today.
@yingbo
yingbo force-pushed the claude/charmrun-publisher-verify-qz7e79 branch from fa2089a to efdcddd Compare September 11, 2026 03:39
The repository already banned one attribution trailer, but that was narrow
enough to read as the only prohibited one. Session links, generated-by
footers and the commit author identity itself all slipped through.

State the rule once and completely: no attribution trailer, footer, badge
or marker of any kind, in commits, pull requests, comments, tags, release
notes, code or documentation, and the commit author and committer are
always the owner. Add the two commands that verify it before a push.

Add CLAUDE.md carrying the same rule, since some tooling reads that
filename rather than AGENTS.md, and mirror the summary in CONTRIBUTING.md.
The rule covers crediting a tool as a contributor, not naming these
instruction files, which are repository configuration. Exclude CLAUDE.md
from the packaged VSIX alongside AGENTS.md.
@yingbo
yingbo force-pushed the claude/charmrun-publisher-verify-qz7e79 branch from efdcddd to 990cffe Compare September 11, 2026 03:40
@yingbo
yingbo merged commit 8ffbcd6 into main Sep 11, 2026
1 check passed
@yingbo
yingbo deleted the claude/charmrun-publisher-verify-qz7e79 branch September 11, 2026 16:03
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant