#2183: dynamically generate form fields for selected commandlet - #2233
#2183: dynamically generate form fields for selected commandlet#2233Hiepiscus wants to merge 25 commits into
Conversation
…let-view' into 2182-basic-structure-for-commandlet-view
… selected commandlet
quando632
left a comment
There was a problem hiding this comment.
Nice split into PropertyFormFieldFactory, that keeps the controller readable. Checking KeywordProperty before BooleanProperty is easy to get wrong since one extends the other, and it is correct here. All three tasks from #2183 are covered.
One theme runs through the findings: runCommandlet executes a different order than AbstractIdeContext.applyAndRun (reset, assign, validate, run), while working on the commandlet singletons that CommandletManagerImpl shares with the CLI context.
Still open from the DoD checklist: the CHANGELOG.adoc entry, and tests. The gui module already has AppBaseTest and HeadlessApplicationTest, and PropertyFormFieldFactory is a static factory, so "property type maps to expected node type" should be cheap to assert.
| property) { | ||
| for (javafx.scene.Node child : hbox.getChildren()) { | ||
| if (child instanceof javafx.scene.control.TextField textField) { | ||
| property.setValueAsString(textField.getText(), context); |
There was a problem hiding this comment.
Blank fields are assigned as well, and ToolProperty.parse("") throws, so pressing Run on install without input ends in the default uncaught exception handler. Skipping blank input leaves the property unset, which is what the CLI does for a missing optional argument.
| property.setValueAsString(textField.getText(), context); | |
| String value = textField.getText(); | |
| if (!value.isBlank()) { | |
| property.assignValueAsString(value, this.context, this.selectedCommandlet); | |
| } |
| } | ||
| } | ||
|
|
||
| this.selectedCommandlet.run(); |
There was a problem hiding this comment.
Without validate() a missing required value reaches run(), for example create would start with an empty project name. validate() gives us the message to show instead. Needs imports of com.devonfw.tools.ide.validation.ValidationResult and com.devonfw.ide.gui.modal.IdeDialog.
| this.selectedCommandlet.run(); | |
| ValidationResult result = this.selectedCommandlet.validate(); | |
| if (!result.isValid()) { | |
| new IdeDialog(IdeDialog.AlertType.ERROR, result.getErrorMessage()).showAndWait(); | |
| return; | |
| } | |
| this.selectedCommandlet.run(); |
| } | ||
|
|
||
| this.selectedCommandlet.run(); | ||
| } |
There was a problem hiding this comment.
applyAndRun also calls ensureLicenseAgreement(cmd) and checks isIdeHomeRequired() and isIdeRootRequired() before running. Skipping the license gate means a tool can be installed from the GUI without the agreement the CLI asks for.
There was a problem hiding this comment.
Addressed. I added the validate() check before running the commandlet, but moved the validation logic into a dedicated method.
| Parent root = loader.load(); | ||
|
|
||
| Stage stage = (Stage) selectedProject.getScene().getWindow(); | ||
| stage.setScene(new Scene(root)); |
There was a problem hiding this comment.
Replacing the scene of the primary stage leaves no way back to the main view, so the app has to be restarted after opening the commandlet view. A back button in commandlet-view.fxml or a separate Stage for the view would solve it.
There was a problem hiding this comment.
Thanks for the suggestion. I've updated the navigation logic so that the commandlet view is displayed in the existing window by replacing the center content of the BorderPane. A back button was added to the commandlet view, allowing users to return to the main view without restarting the application.
| } | ||
| } | ||
|
|
||
| this.selectedCommandlet.run(); |
There was a problem hiding this comment.
The result of the run never reaches the view. A success writes everything to the console and leaves the window unchanged, and a failure escapes as an uncaught exception, for example build outside a project throws CliException: Could not find build descriptor straight out of the handler. Wrapping run() in a try/catch and reporting both outcomes in the view would close the loop.
| commandletSelector.getItems().clear(); | ||
| commandletSelector.getItems().addAll(context.getCommandletManager().getCommandlets().stream() | ||
| .map(Commandlet::getName) | ||
| .toList()); |
There was a problem hiding this comment.
nit: .sorted() was dropped in 8f8f191, so the combo box lists about 40 commandlets unsorted. Was that intentional?
There was a problem hiding this comment.
The removal was intentional. I was considering a future approach where frequently used commandlets would be shown first. However, the current unsorted order is not predictable, so I've added .sorted() back for now.
| return name; | ||
| } | ||
|
|
||
| if (name.isEmpty() && alias != null) { |
There was a problem hiding this comment.
nit: the non option branch reimplements Property#getNameOrAlias().
Co-authored-by: quando632 <quang-hieu.do@capgemini.com>
Co-authored-by: quando632 <quang-hieu.do@capgemini.com>
Co-authored-by: quando632 <quang-hieu.do@capgemini.com>
Co-authored-by: quando632 <quang-hieu.do@capgemini.com>
pane with back button
This PR fixes #2183
Introduces dynamic form generation for commandlets. Instead of using a static input field, the UI now creates appropriate form fields based on the properties of the selected commandlet for a more flexible configuration experience.
Show more lines
Implemented changes:
PropertyFormFieldFactory(new): create appropriate UI based on commandlet:TextFieldfor positional parameters and named optionsCheckBoxfor boolean flagsTextFieldwith aScrollPane+VBoxin the FXML layoutonCommandletSelected()listener to regenerate the form on selection changerunCommandlet()to read property values from generated form fieldsTesting instructions
Please add conscise, understandable instructions on how a reviewer can test/verify the functionality of your contribution here:
AppLauncherCommandletsRunChecklist for this PR
Make sure everything is checked before merging this PR. For further info please also see
our DoD.
mvn clean testlocally all tests pass and build is successful#«issue-id»: «brief summary»(e.g.#921: fixed setup.bat). If no issue ID exists, title only.In Progressand assigned to you or there is no issue (might happen for very small PRs)with
internal