Command Line Interface

Purpose and Scope

Visual Studio Code exposes two related command surfaces. The first is the external code executable documented for users: it opens files and folders, prints help and version information, installs extensions, changes display language, and emits diagnostics through command-line switches. The second is the in-product command system that runs after VS Code has opened an editor window. The repository evidence for this page is concentrated on that second layer: concrete editor commands, command identifiers, command arguments, keybindings, and edit-operation objects that make command invocations predictable inside the workbench.

For a developer reading the Code - OSS repository, the useful mental model is that launching VS Code and invoking editor features are separate phases with a common user-facing vocabulary: commands. A terminal invocation such as code . selects a workspace and starts the workbench. Once the workbench is active, commands such as Quick Fix, inline suggestion navigation, line commenting, line copying, and line moving are represented as TypeScript classes or exported command IDs. These command implementations are the source-backed examples on this page, and they show how commands translate user intent into model edits or controller calls.

Sources: src/vs/editor/contrib/codeAction/browser/codeActionCommands.ts, src/vs/editor/contrib/inlineCompletions/browser/controller/commandIds.ts

Relevant Source Files

  • src/vs/editor/contrib/comment/browser/lineCommentCommand.ts - Implements LineCommentCommand, including preflight analysis for language-specific line comment tokens and edit generation for toggling, adding, or removing line comments.
  • src/vs/editor/contrib/insertFinalNewLine/browser/insertFinalNewLineCommand.ts - Implements InsertFinalNewLineCommand and the insertFinalNewLine(model) helper that produces a final newline edit only when the last line needs one.
  • src/vs/editor/contrib/codeAction/browser/codeActionCommands.ts - Registers code-action commands such as Quick Fix, defines command argument schema fields, and connects command invocations to CodeActionController.manualTriggerAtCurrentPosition.
  • src/vs/editor/contrib/inlineCompletions/browser/controller/commandIds.ts - Exports public command ID strings for inline suggestion actions including commit, show previous, show next, jump, hide, toggle collapsed display, and rename symbol.
  • src/vs/editor/contrib/linesOperations/browser/copyLinesCommand.ts - Implements CopyLinesCommand, which duplicates selected lines up or down and restores cursor selection state after edits.
  • src/vs/editor/contrib/linesOperations/browser/moveLinesCommand.ts - Implements MoveLinesCommand, which moves selected lines while respecting document boundaries, model options, language configuration, and auto-indentation support.

External code Command Orientation

The public CLI entrypoint is the code command. User-facing documentation describes code --help as the fastest way to inspect supported switches, including help, version, new-window, and reuse-window options. In normal use, a developer navigates to a project folder and runs code . to open that folder in VS Code. On macOS, users may need to install the shell command into PATH; Windows and Linux installations typically add the binary location during setup. Insiders builds use the separate code-insiders command so stable and preview installations can coexist.

That external launcher should not be confused with the integrated terminal. The CLI controls how the editor is launched; the integrated terminal runs shells and tools inside the opened workbench. This distinction matters when diagnosing behavior. If a flag changes startup, window reuse, or the initial file and folder set, the issue belongs to launcher and workbench startup paths. If a command changes text, opens a Quick Fix picker, commits an inline suggestion, or rearranges selected lines, the behavior belongs to the editor command layer represented by the source files on this page.

In-Product Command Architecture

Editor commands are small objects that convert an invocation into a safe operation against an ITextModel or editor controller. Several source files implement ICommand, whose two-stage contract separates edit creation from cursor recovery: getEditOperations(model, builder) adds the edits, and computeCursorState(model, helper) returns the selection after the edits are applied. This design lets command implementations reason in terms of immutable ranges, tracked selections, language metadata, and model options rather than directly mutating editor state.

InsertFinalNewLineCommand is the simplest example. It stores the current Selection, calls insertFinalNewLine(model), adds the resulting edit only when needed, and tracks the selection so the cursor remains stable. The helper inspects the model line count, reads the last line, treats an empty or whitespace-only last line as already acceptable, and otherwise inserts the model end-of-line sequence at the last line's maximum column. The command therefore behaves idempotently: repeated invocation does not keep adding blank lines once the file already ends with an empty or whitespace-only final line.

Sources: src/vs/editor/contrib/insertFinalNewLine/browser/insertFinalNewLineCommand.ts

CopyLinesCommand and MoveLinesCommand show the richer end of the same contract. Copying gathers line contents from the active selection, adjusts selections that end at column one, handles empty-line duplication, chooses whether to insert text above or below, and restores selection direction. Moving lines guards against moving past the start or end of the document, normalizes selections that visually include the next line, and builds indentation helpers from tab size, indent size, and insert-spaces model options. These command objects preserve editor feel by coupling text edits with cursor semantics.

Sources: src/vs/editor/contrib/linesOperations/browser/copyLinesCommand.ts, src/vs/editor/contrib/linesOperations/browser/moveLinesCommand.ts

Command IDs, Palette Entries, and Arguments

Not every command is represented only by an edit object. Code actions are registered as editor actions and commands with IDs, labels, preconditions, keybindings, menus, icons, and argument schemas. codeActionCommands.ts imports command IDs such as quickFixCommandId, refactorCommandId, sourceActionCommandId, organizeImportsCommandId, fixAllCommandId, and autoFixCommandId. The Quick Fix action uses a localized title, the lightbulb icon, the Ctrl/Cmd+. keybinding when text input has focus, and a precondition requiring a writable editor with a code action provider.

The argument schema in the code-action command file is important for automation and extension authors because it defines what a command can accept. It exposes kind as the code action kind to run, apply as the auto-apply policy, and preferred as a boolean filter for preferred actions. The allowed apply values are first, ifSingle, and never through the CodeActionAutoApply enum. When invoked against an editor with a model, command handling resolves the CodeActionController and calls manualTriggerAtCurrentPosition with the message, source, filter, and auto-apply behavior.

Sources: src/vs/editor/contrib/codeAction/browser/codeActionCommands.ts

Inline completions use an even more explicit command-ID module. commandIds.ts exports stable string constants such as editor.action.inlineSuggest.commit, editor.action.inlineSuggest.commitAlternativeAction, editor.action.inlineSuggest.showPrevious, editor.action.inlineSuggest.showNext, editor.action.inlineSuggest.jump, editor.action.inlineSuggest.hide, editor.action.inlineSuggest.toggleShowCollapsed, and editor.action.inlineSuggest.renameSymbol. Keeping these IDs in one file gives other inline-completion components a single source of truth for binding commands, menus, keybindings, telemetry, and tests to the same public action names.

Sources: src/vs/editor/contrib/inlineCompletions/browser/controller/commandIds.ts

Editing Command Execution Flow

Line commenting illustrates a command that depends on language configuration before it can generate edits. LineCommentCommand accepts an ILanguageConfigurationService, a Selection, indentation size, command type, spacing behavior, empty-line behavior, and an optional first-line ignore flag. Its preflight path tokenizes cheaply, reads the language ID at the start position, asks the language configuration for comment metadata, and returns unsupported when the language has no line comment token. That prevents the command from pretending every file can be line-commented with the same prefix.

The command type enum distinguishes toggle, force-add, and force-remove behavior. After preflight, the command can analyze each selected line for whether it should be ignored, where the comment string belongs, and how much text must be inserted or removed. This source-backed flow explains why the same user command behaves naturally across JavaScript, CSS, shell scripts, and languages with different comment syntax: the command is not hardcoded to a token; it derives token and placement data from language configuration before editing the text model.

Sources: src/vs/editor/contrib/comment/browser/lineCommentCommand.ts

Compact Reference

ComponentPublic or source-level contractBehavior shown in source
LineCommentCommandConstructor accepts language configuration service, Selection, indent size, Type, insert-space flag, ignore-empty-lines flag, and optional ignore-first-line flag.Gathers line comment tokens from language configuration, supports toggle/add/remove modes, and returns unsupported when line comments are unavailable.
TypeToggle, ForceAdd, ForceRemove.Selects whether line comments are toggled, always inserted, or always removed.
InsertFinalNewLineCommandImplements ICommand with getEditOperations and computeCursorState.Adds one end-of-line edit at the final line only when the document does not already end with an empty or whitespace-only final line.
insertFinalNewLine(model)Function returning `ISingleEditOperationundefined`.
QuickFixActionEditorAction2 registered with quickFixCommandId.Uses title Quick Fix..., lightbulb icon, Ctrl/Cmd+. keybinding, and editor/provider preconditions.
Code-action command argskind, apply, preferred.Filters action kinds, controls auto-apply with first/if-single/never behavior, and optionally restricts to preferred actions.
Inline suggestion command IDsExported constants beginning with editor.action.inlineSuggest..Names commit, alternative commit, previous/next navigation, jump, hide, collapsed display toggle, and rename-symbol actions.
CopyLinesCommandConstructor accepts Selection, copy direction, and optional noop flag.Duplicates selected line text up or down, handles empty lines, tracks selection, and restores selection direction.
MoveLinesCommandConstructor accepts Selection, direction, auto-indent strategy, and language configuration service.Prevents out-of-document moves and prepares indentation support from model options and language configuration.

Practical Next Steps

When you are using VS Code as a user, start with code --help, then try code ., code --new-window ., and code --reuse-window <file> to understand launch behavior. When you are extending or debugging command behavior in Code - OSS, search for the command ID first, then inspect the EditorAction, EditorCommand, or ICommand implementation that owns the edit or controller call. For editing commands, verify both halves of the contract: the generated operations and the resulting cursor state.

For source changes, keep the command-palette guidance in mind: command names should be clear, grouped by category where appropriate, and paired with keyboard shortcuts only when they are useful and not conflicting. Add or update tests around the command's observable behavior rather than only checking that the command ID exists. The most reliable review path is to exercise the command from keyboard, Command Palette, and programmatic invocation, then compare the text model edits and selections with the implementation's explicit contract.