Skip to content

Commit 76dc893

Browse files
malsynedHannia Valera
andauthored
Add new files directly to CMakeLists.txt (#2132) (#4454)
* add sourceFileExtensions to CodeModelToolchain * add backtraceGraph to CodeModelTarget * Add cmakeParser.ts to parse CMakeLists.txt files This parser accepts the grammar described in [cmake-language(7)](https://cmake.org/cmake/help/latest/manual/cmake-language.7.html#syntax). It is somewhat more lenient than that parser, in that it permits comments in places that the official grammar would reject them. * Add new files directly to CMakeLists.txt (#2132) Adds two new commands that scan the Code Model and CMakeLists.txt for command invocations that add source files to targets or certain variables. * cmake.addFileToCMakeLists: Present the user with options for which command invocation to modify, and then edit that command invocation to add a new source file to its arguments. * cmake.removeFileFromCMakeLists: Edit any command invocations that include a source file, removing it from their argument lists. These commands can optionally be triggered when a source file is created or deleted. Quick Pick items for targets and invocations are carefully sorted to make the first option very likely to be the desired one, and settings exist to automatically choose the best option rather than asking. * Exclude invocations from unrelated in-project folders * Fix "value is never read" smoke test failure * Guess at indentation, to avoid UI flicker. `window.showTextDocument()` allows access to more accurate indentation settings, but it creates jarring flashes in the UI, and for the corner cases where it makes a difference, I don't think it's worth it. * fix typo: variableSourceLists → varSourceLists * fix typo: negating file set name in sort key * cmakeParser: fix value regex for bracket-quoted arguments * localization entries for the new commands and the settings * addressing necessary suggestions, bounds checking and indentation, and others * fixing ui experience and refactoring * enhance CMakeListsModifier and add tests for parsing and argument handling * fixing lint errors * refactor: update import paths and rename isDelete to isDeletion in CMakeListsModifier * refactor: replace sameFile with platformPathEquivalent and update tests accordingly - took in more feedback * fixing small ux bugs * Refactor CMakeListsModifier and CMakeParser for improved functionality and clarity * fixed a nested directory issue + stale backtrace bug * Enhance source list handling in CMakeListsModifier to address structural mismatches and improve insertion logic * refactoring the automatic source file management in CMakeLists.txt and taking account the new settings and commands * include clrf endings for parser in the case of ai-generated projects * bring back Refactor Preview for source file edits and improve candidate selection logic --------- Co-authored-by: Hannia Valera <[email protected]>
1 parent 4ae46c6 commit 76dc893

16 files changed

Lines changed: 3226 additions & 11 deletions

CHANGELOG.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33
## 1.23
44

55
Features:
6+
- Automatically add new source files to `CMakeLists.txt` and remove deleted source files from `CMakeLists.txt`. Two new commands (`cmake.addFileToCMakeLists` and `cmake.removeFileFromCMakeLists`) and nine new `cmake.modifyLists.*` settings provide full control over target selection, variable handling, and confirmation behavior. [#2132](https://github.com/microsoft/vscode-cmake-tools/issues/2132) [#4454](https://github.com/microsoft/vscode-cmake-tools/pull/4454) [@malsyned](https://github.com/malsyned)
67
- Allow specifying a custom debug adapter type in `cmake.debugConfig` via the `type` property. When set, automatic debugger detection is skipped and any debug adapter (e.g., `codelldb`, `lldb`) can be used with arbitrary configuration properties. [#4818](https://github.com/microsoft/vscode-cmake-tools/pull/4818)
78
- Add `${cmake.testEnvironment}` placeholder for launch.json that resolves to the CTest `ENVIRONMENT` test property, and automatically include CTest environment variables when debugging tests without a launch configuration. [#4572](https://github.com/microsoft/vscode-cmake-tools/issues/4572) [#4821](https://github.com/microsoft/vscode-cmake-tools/pull/4821)
89
- Add "Delete Build Directory and Reconfigure" command that removes the entire build directory before reconfiguring, ensuring a completely clean state. [#4826](https://github.com/microsoft/vscode-cmake-tools/pull/4826)

docs/cmake-settings.md

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -64,6 +64,15 @@ Options that support substitution, in the table below, allow variable references
6464
| `cmake.loggingLevel` | A string setting that specifies how much output CMake Tools produces in its output channel. Set to one of `"trace"`, `"debug"`, `"info"`, `"note"`, `"warning"`, `"error"`, or `"fatal"`. `"trace"` is the most verbose.</br></br>Regardless of the logging level, CMake Tools writes all levels of logging to the CMake Tools log file. This file is useful if you need to [troubleshoot CMake Tools](troubleshoot.md) | `"info"` | no |
6565
| `cmake.mergedCompileCommands` | Path where to create a merged compile_commands.json file. | `null` | no |
6666
| `cmake.mingwSearchDirs` | **DEPRECATED**. List of paths to search for MinGW. Use `cmake.additionalCompilerSearchDirs` instead. | `[]` | no |
67+
| `cmake.modifyLists.addNewSourceFiles` | Add source files to CMake lists when they are created. `"no"` disables, `"yes"` applies automatically, `"ask"` shows a preview of proposed changes to apply. | `"ask"` | no |
68+
| `cmake.modifyLists.removeDeletedSourceFiles` | Remove source files from CMake lists when they are deleted. `"no"` disables, `"yes"` applies automatically, `"ask"` shows a preview of proposed changes to apply. | `"ask"` | no |
69+
| `cmake.modifyLists.variableSelection` | How to choose which `set()` or `list(APPEND/PREPEND/INSERT)` command invocation to edit when adding source files to CMake lists. | `"never"` | no |
70+
| `cmake.modifyLists.sourceVariables` | Variables to add source files to. Variables appearing earlier in this list will be given higher priority. Only used if `cmake.modifyLists.variableSelection` is not `"never"`. Supports glob patterns. | `["SRC", "SRCS", "SOURCES", "SOURCE_FILES", "*_SRC", "*_SRCS", "*_SOURCES", "*_SOURCE_FILES"]` | no |
71+
| `cmake.modifyLists.targetSelection` | How to choose which target to add new source files to when adding source files to CMake lists. | `"askParentSourceDirs"` | no |
72+
| `cmake.modifyLists.targetCommandInvocationSelection` | How to choose which of a target's source command invocations to edit when adding source files to CMake lists. | `"askParentDirs"` | no |
73+
| `cmake.modifyLists.targetSourceCommands` | Commands to treat as target source commands when adding source files to CMake lists. Commands appearing earlier in this list will be given higher priority. Supports glob patterns. | `["target_sources", "add_executable", "add_library"]` | no |
74+
| `cmake.modifyLists.scopeSelection` | How to choose which of a target's visibility scopes, file sets, or source keyword parameters to edit when adding source files to CMake lists. | `"ask"` | no |
75+
| `cmake.modifyLists.sourceListKeywords` | Keyword arguments to user-defined functions and macros which introduce lists of source files. If left empty, all arguments consisting of only upper-case letters and underscores will be considered. Supports glob patterns. | `[]` | no |
6776
| `cmake.options.advanced` | Advanced options for CMake Tools. | See package.json | no |
6877
| `cmake.options.statusBarVisibility` | Controls visibility of the status bar. | `hidden` | no |
6978
| `cmake.outputLogEncoding` | Encoding to use for tool output. | `auto` | no |

package.json

Lines changed: 148 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -763,6 +763,16 @@
763763
"title": "%cmake-tools.command.cmake.quickStart.title%",
764764
"category": "CMake"
765765
},
766+
{
767+
"command": "cmake.addFileToCMakeLists",
768+
"title": "%cmake-tools.command.cmake.addFileToCMakeLists.title%",
769+
"category": "CMake"
770+
},
771+
{
772+
"command": "cmake.removeFileFromCMakeLists",
773+
"title": "%cmake-tools.command.cmake.removeFileFromCMakeLists.title%",
774+
"category": "CMake"
775+
},
766776
{
767777
"command": "cmake.debugTarget",
768778
"title": "%cmake-tools.command.cmake.debugTarget.title%",
@@ -4133,11 +4143,147 @@
41334143
"description": "%cmake-tools.configuration.cmake.useFolderPropertyInBuildTargetDropdown.description%",
41344144
"scope": "resource"
41354145
},
4136-
"cmake.setBuildTargetSameAsLaunchTarget": {
4146+
"cmake.setBuildTargetSameAsLaunchTarget": {
41374147
"type": "boolean",
41384148
"default": false,
41394149
"description": "%cmake-tools.configuration.cmake.setBuildTargetSameAsLaunchTarget.description%",
41404150
"scope": "resource"
4151+
},
4152+
"cmake.modifyLists.addNewSourceFiles": {
4153+
"type": "string",
4154+
"default": "ask",
4155+
"enum": [
4156+
"no",
4157+
"yes",
4158+
"ask"
4159+
],
4160+
"description": "%cmake-tools.configuration.cmake.modifyLists.addNewSourceFiles.description%",
4161+
"enumDescriptions": [
4162+
"%cmake-tools.configuration.cmake.modifyLists.addNewSourceFiles.no.description%",
4163+
"%cmake-tools.configuration.cmake.modifyLists.addNewSourceFiles.yes.description%",
4164+
"%cmake-tools.configuration.cmake.modifyLists.addNewSourceFiles.ask.description%"
4165+
],
4166+
"scope": "resource"
4167+
},
4168+
"cmake.modifyLists.removeDeletedSourceFiles": {
4169+
"type": "string",
4170+
"default": "ask",
4171+
"enum": [
4172+
"no",
4173+
"yes",
4174+
"ask"
4175+
],
4176+
"description": "%cmake-tools.configuration.cmake.modifyLists.removeDeletedSourceFiles.description%",
4177+
"enumDescriptions": [
4178+
"%cmake-tools.configuration.cmake.modifyLists.removeDeletedSourceFiles.no.description%",
4179+
"%cmake-tools.configuration.cmake.modifyLists.removeDeletedSourceFiles.yes.description%",
4180+
"%cmake-tools.configuration.cmake.modifyLists.removeDeletedSourceFiles.ask.description%"
4181+
],
4182+
"scope": "resource"
4183+
},
4184+
"cmake.modifyLists.variableSelection": {
4185+
"type": "string",
4186+
"enum": [
4187+
"never",
4188+
"auto",
4189+
"askFirstParentDir",
4190+
"askParentDirs"
4191+
],
4192+
"default": "never",
4193+
"markdownDescription": "%cmake-tools.configuration.cmake.modifyLists.variableSelection.markdownDescription%",
4194+
"markdownEnumDescriptions": [
4195+
"%cmake-tools.configuration.cmake.modifyLists.variableSelection.never.description%",
4196+
"%cmake-tools.configuration.cmake.modifyLists.variableSelection.auto.description%",
4197+
"%cmake-tools.configuration.cmake.modifyLists.variableSelection.askFirstParentDir.description%",
4198+
"%cmake-tools.configuration.cmake.modifyLists.variableSelection.askParentDirs.description%"
4199+
],
4200+
"scope": "resource"
4201+
},
4202+
"cmake.modifyLists.sourceVariables": {
4203+
"type": "array",
4204+
"items": {
4205+
"type": "string"
4206+
},
4207+
"default": [
4208+
"SRC",
4209+
"SRCS",
4210+
"SOURCES",
4211+
"SOURCE_FILES",
4212+
"*_SRC",
4213+
"*_SRCS",
4214+
"*_SOURCES",
4215+
"*_SOURCE_FILES"
4216+
],
4217+
"markdownDescription": "%cmake-tools.configuration.cmake.modifyLists.sourceVariables.markdownDescription%",
4218+
"scope": "resource"
4219+
},
4220+
"cmake.modifyLists.targetSelection": {
4221+
"type": "string",
4222+
"enum": [
4223+
"auto",
4224+
"askNearestSourceDir",
4225+
"askParentSourceDirs"
4226+
],
4227+
"default": "askParentSourceDirs",
4228+
"description": "%cmake-tools.configuration.cmake.modifyLists.targetSelection.description%",
4229+
"enumDescriptions": [
4230+
"%cmake-tools.configuration.cmake.modifyLists.targetSelection.auto.description%",
4231+
"%cmake-tools.configuration.cmake.modifyLists.targetSelection.askNearestSourceDir.description%",
4232+
"%cmake-tools.configuration.cmake.modifyLists.targetSelection.askParentSourceDirs.description%"
4233+
],
4234+
"scope": "resource"
4235+
},
4236+
"cmake.modifyLists.targetCommandInvocationSelection": {
4237+
"type": "string",
4238+
"enum": [
4239+
"auto",
4240+
"askFirstParentDir",
4241+
"askParentDirs"
4242+
],
4243+
"default": "askParentDirs",
4244+
"description": "%cmake-tools.configuration.cmake.modifyLists.targetCommandInvocationSelection.description%",
4245+
"enumDescriptions": [
4246+
"%cmake-tools.configuration.cmake.modifyLists.targetCommandInvocationSelection.auto.description%",
4247+
"%cmake-tools.configuration.cmake.modifyLists.targetCommandInvocationSelection.askFirstParentDir.description%",
4248+
"%cmake-tools.configuration.cmake.modifyLists.targetCommandInvocationSelection.askParentDirs.description%"
4249+
],
4250+
"scope": "resource"
4251+
},
4252+
"cmake.modifyLists.targetSourceCommands": {
4253+
"type": "array",
4254+
"items": {
4255+
"type": "string"
4256+
},
4257+
"default": [
4258+
"target_sources",
4259+
"add_executable",
4260+
"add_library"
4261+
],
4262+
"markdownDescription": "%cmake-tools.configuration.cmake.modifyLists.targetSourceCommands.markdownDescription%",
4263+
"scope": "resource"
4264+
},
4265+
"cmake.modifyLists.scopeSelection": {
4266+
"type": "string",
4267+
"enum": [
4268+
"auto",
4269+
"ask"
4270+
],
4271+
"default": "ask",
4272+
"description": "%cmake-tools.configuration.cmake.modifyLists.scopeSelection.description%",
4273+
"enumDescriptions": [
4274+
"%cmake-tools.configuration.cmake.modifyLists.scopeSelection.auto.description%",
4275+
"%cmake-tools.configuration.cmake.modifyLists.scopeSelection.ask.description%"
4276+
],
4277+
"scope": "resource"
4278+
},
4279+
"cmake.modifyLists.sourceListKeywords": {
4280+
"type": "array",
4281+
"items": {
4282+
"type": "string"
4283+
},
4284+
"default": [],
4285+
"markdownDescription": "%cmake-tools.configuration.cmake.modifyLists.sourceListKeywords.markdownDescription%",
4286+
"scope": "resource"
41414287
}
41424288
}
41434289
},
@@ -4253,7 +4399,7 @@
42534399
"endToEndTestsSuccessfulBuild": "yarn run pretest && node ./out/test/end-to-end-tests/successful-build/runTest.js",
42544400
"endToEndTestsSingleRoot": "yarn run pretest && node ./out/test/end-to-end-tests/single-root-UI/runTest.js",
42554401
"endToEndTestsMultiRoot": "yarn run pretest && node ./out/test/end-to-end-tests/multi-root-UI/runTest.js",
4256-
"backendTests": "node ./node_modules/mocha/bin/_mocha -u tdd --timeout 999999 --colors -r ts-node/register -r tsconfig-paths/register ./test/unit-tests/backend/**/*.test.ts",
4402+
"backendTests": "node ./node_modules/mocha/bin/_mocha -u tdd --timeout 999999 --colors -r ts-node/register -r tsconfig-paths/register -r test/unit-tests/backend/setup-vscode-mock.ts ./test/unit-tests/backend/**/*.test.ts",
42574403
"build-product-icon-font": "yarn --cwd ./tools/product-icon-font-generator/ install && yarn --cwd ./tools/product-icon-font-generator/ build && node ./tools/product-icon-font-generator/dist/index.js --source-directory ./res/product-icons/ --output-directory ./res/ --woff2"
42584404
},
42594405
"devDependencies": {

package.nls.json

Lines changed: 56 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,6 @@
11
{
2+
"cmake-tools.command.cmake.addFileToCMakeLists.title": "Add File to CMake Lists",
3+
"cmake-tools.command.cmake.removeFileFromCMakeLists.title": "Remove File from CMake Lists",
24
"cmake-tools.command.cmake.openCMakePresets.title": "Open CMakePresets.json",
35
"cmake-tools.command.cmake.addConfigurePreset.title": "Add Configure Preset",
46
"cmake-tools.command.cmake.addBuildPreset.title": "Add Build Preset",
@@ -435,5 +437,58 @@
435437
"cmake-tools.debugger.label": "CMake Debugger",
436438
"cmake-tools.command.cmake.appendBuildDirectoryToWorkspace.title": "Append Build Directory to Current Workspace",
437439
"cmake-tools.command.workbench.action.tasks.configureTaskRunner.title":"Configure Task",
438-
"cmake-tools.command.workbench.action.tasks.runTask.title":"Run Task"
440+
"cmake-tools.command.workbench.action.tasks.runTask.title":"Run Task",
441+
"cmake-tools.configuration.cmake.modifyLists.addNewSourceFiles.description": "Add source files to CMake lists when they are created.",
442+
"cmake-tools.configuration.cmake.modifyLists.addNewSourceFiles.no.description": "Do not automatically add source files to CMake lists",
443+
"cmake-tools.configuration.cmake.modifyLists.addNewSourceFiles.yes.description": "Automatically add source files to CMake lists",
444+
"cmake-tools.configuration.cmake.modifyLists.addNewSourceFiles.ask.description": "Show a preview panel of proposed changes to apply",
445+
"cmake-tools.configuration.cmake.modifyLists.removeDeletedSourceFiles.description": "Remove source files from CMake lists when they are deleted.",
446+
"cmake-tools.configuration.cmake.modifyLists.removeDeletedSourceFiles.no.description": "Do not automatically remove source files from CMake lists",
447+
"cmake-tools.configuration.cmake.modifyLists.removeDeletedSourceFiles.yes.description": "Automatically remove source files from CMake lists",
448+
"cmake-tools.configuration.cmake.modifyLists.removeDeletedSourceFiles.ask.description": "Show a preview panel of proposed changes to apply",
449+
"cmake-tools.configuration.cmake.modifyLists.variableSelection.markdownDescription": {
450+
"message": "How to choose which `set()` or `list(APPEND/PREPEND/INSERT)` command invocation to edit when adding source files to CMake lists.",
451+
"comment": [
452+
"Markdown text between `` should not be translated or localized (they represent literal text) and the capitalization, spacing, and punctuation (including the ``) should not be altered."
453+
]
454+
},
455+
"cmake-tools.configuration.cmake.modifyLists.variableSelection.never.description": "Do not look for variable modification command invocations, only look for source command invocations.",
456+
"cmake-tools.configuration.cmake.modifyLists.variableSelection.auto.description": "Choose the best candidate automatically.",
457+
"cmake-tools.configuration.cmake.modifyLists.variableSelection.askFirstParentDir.description": {
458+
"message": "Present a Quick Pick with options from the first `CMakeLists.txt` found when searching up from the location of the new source file.",
459+
"comment": [
460+
"Markdown text between `` should not be translated or localized (they represent literal text) and the capitalization, spacing, and punctuation (including the ``) should not be altered."
461+
]
462+
},
463+
"cmake-tools.configuration.cmake.modifyLists.variableSelection.askParentDirs.description": {
464+
"message": "Present a Quick Pick with options from all `CMakeLists.txt` files found when searching up from the location of the new source file.",
465+
"comment": [
466+
"Markdown text between `` should not be translated or localized (they represent literal text) and the capitalization, spacing, and punctuation (including the ``) should not be altered."
467+
]
468+
},
469+
"cmake-tools.configuration.cmake.modifyLists.sourceVariables.markdownDescription": {
470+
"message": "Variables to add source files to. Variables appearing earlier in this list will be given higher priority. Only used if `#cmake.modifyLists.variableSelection#` is not `never`. Supports glob patterns.",
471+
"comment": [
472+
"Markdown text between `` should not be translated or localized (they represent literal text) and the capitalization, spacing, and punctuation (including the ``) should not be altered."
473+
]
474+
},
475+
"cmake-tools.configuration.cmake.modifyLists.targetSelection.description": "How to choose which target to add new source files to when adding source files to CMake lists.",
476+
"cmake-tools.configuration.cmake.modifyLists.targetSelection.auto.description": "Choose the best candidate automatically.",
477+
"cmake-tools.configuration.cmake.modifyLists.targetSelection.askNearestSourceDir.description": "Present a Quick Pick with targets whose source directories are closest to location of the new source file.",
478+
"cmake-tools.configuration.cmake.modifyLists.targetSelection.askParentSourceDirs.description": "Present a Quick Pick with targets whose source directories contain the location of the new source file.",
479+
"cmake-tools.configuration.cmake.modifyLists.targetCommandInvocationSelection.description": "How to choose which of a target's source command invocations to edit when adding source files to CMake lists.",
480+
"cmake-tools.configuration.cmake.modifyLists.targetCommandInvocationSelection.auto.description": "Choose the best candidate automatically.",
481+
"cmake-tools.configuration.cmake.modifyLists.targetCommandInvocationSelection.askFirstParentDir.description": "Present a Quick Pick with options from the CMake list file in the parent directory closest to the location of the new source file.",
482+
"cmake-tools.configuration.cmake.modifyLists.targetCommandInvocationSelection.askParentDirs.description": "Present a Quick Pick with options from all CMake list files in the parent directories of the new source file.",
483+
"cmake-tools.configuration.cmake.modifyLists.targetSourceCommands.markdownDescription": {
484+
"message": "Commands to treat as target source commands when adding source files CMake lists. Commands appearing earlier in this list will be given higher priority. Supports glob patterns.\n\nIf you are using the File API (see `#cmake.cmakeCommunicationMode#`), user-defined functions and macros which call the commands in this list are detected automatically and added to it.",
485+
"comment": [
486+
"Markdown text between `` should not be translated or localized (they represent literal text) and the capitalization, spacing, and punctuation (including the ``) should not be altered."
487+
]
488+
},
489+
"cmake-tools.configuration.cmake.modifyLists.scopeSelection.description": "How to choose which of a target's visibility scopes, file sets, or source keyword parameters to edit when adding source files to CMake lists.",
490+
"cmake-tools.configuration.cmake.modifyLists.scopeSelection.auto.description": "Choose the best candidate automatically.",
491+
"cmake-tools.configuration.cmake.modifyLists.scopeSelection.ask.description": "Present a Quick Pick with options from the selected target source command invocation.",
492+
"cmake-tools.configuration.cmake.modifyLists.sourceListKeywords.markdownDescription": "Keyword arguments to user-defined functions and macros which introduce lists of source files. If left empty, all arguments consisting of only upper-case letters and underscores will be considered. Supports glob patterns.",
493+
"update.code.model.for.list.modifier": "Update code model for automatic list file modifier"
439494
}

0 commit comments

Comments
 (0)