Completions
A completions definition can be used to add static and symbolic completions to a syntax language in the editor. Completion definitions are written using XML.
One or more XML files may be provided in the Completions/
folder of an extension. The name of a file does not matter, but it most often reflects the set of the completions being added. If the completions are the base set for a language, the file will often be named after the syntax (such as HTML.xml
for the set of HTML completions).
Completion files declare a top-level <completions>
tag that contains the entirety of the rules for the definition, and are composed of two major components: Providers and Completions Sets. They may define multiple providers and multiple completion sets as needed.
As a convenience, the <completions>
element of a completions file may instead be included as a child of the top-level <syntax>
element of a syntax file if all of the following conditions are met:
- The element contains only
<provider>
elements, and not<set>
elements. - The provider elements are scoped only to the syntax in which they are defined.
This allows a syntax to add symbolic completion providers easily inline in its file without creating a separate completions file. Additionally, an extension may provide both of these (an inline <completions>
element and a completions file) if needed.
Completions files may also be defined in one extension and contribute completions to languages defined in another, and even built-in languages like HTML.
Completion sets may be divided into two types: Static Completions and Symbolic Completions
Providers
A completion provider determines where specific completions should be offered based on logical rules about the document.
While typing, the editor will evaluate each provider against the current cursor location in a document. The providers that match will then have their completions filtered and offered in the completion list.
Providers are defined using a <provider>
element within the top-level element, which may then contain several other types of sub-elements for matching rules and determining which completion sets will be used.
A provider may optionally provide a name
attribute. This attribute is not used for any rule matching, and instead is provided for debugging purposes.
<provider name="css.attributes">
<syntax>css</syntax>
<match-selector>style.attribute-list, style.attribute.name</match-selector>
<expression>(\b|-)[a-zA-Z0-9-]*</expression>
<set>css.properties</set>
</provider>
Scoping Providers
A provider may provide attribute which help the completion engine scope it to only appear within specific parts of a document (or specificaly not in part of a document).
Syntax
The <syntax>
element defines the name of a syntax in which the provider will be valid, such as html
. Multiple syntax elements may be provided if the provider is valid within more than one syntax.
<syntax>html</syntax>
<syntax>markdown</syntax>
A provider may provide attributes which describe in what syntax-highlighting regions it should be offered.
Trigger Characters
By default, completion providers are triggered (have their completions requested) when the user types an identifier character (such as alphanumerics) or by manually invoking the completions list (such as by pressing the Escape key).
If a completion provider should be triggered on more specific characters (such as a period .
for method suggestions), you can provide the trigger
element. The textual contents of this element provides additional characters that should trigger completion.
<trigger>.([</trigger>
Expression
The <expression>
element defines a regular expression that is evaluated anchored to the end of the text preceding the cursor position. If the expression does not match, the provider will not be used.
The text matched by the expression will be used as the range to be used when filtering completions, and the range replaced or modified by inserting a completion. As such, the text matched by the expression must contain all the characters that will be valid to be replaced by the completion.
Any text that an extension author wishes to match using this expression that should not be considered part of the completing text should be matched within regular expression look-behinds or a simliar mechanism.
Expressions may successfully match and evaluate to an zero-length string, at which point all completions for a provider will be offered.
Match Selector
The <match-selector>
element defines one or more simple selectors which must match an ancestor containing the completion position. The selector names are the same as those use by syntax highlighting, such as tag.name
.
Multiple selectors may be separated by commas. All whitespace is ignored.
<match-selector>style.attribute.name, style.attribute.value</match-selector>
Exclude Selector
The <exclude-selector>
element defines one or more simple selectors which, if matched, will exclude the provider from matching. The selector names are the same as those use by syntax highlighting, such as tag.name
. Alone or in tandem with the <match-selector>
element, this allows certain cases to be ignored.
Multiple selectors may be separated by commas. All whitespace is ignored.
<exclude-selector>string, comment</exclude-selector>
Query
The <query>
element defines a Tree-sitter query which must be matched at the completion position.
Note: The
<query>
element is only compatible with Tree-sitter-based grammars.
<query>
(start_tag)
(self_closing_tag)
</query>
This query defines that the provider should match when the cursor is within nodes named either start_tag
or self_closing_tag
within the Tree-sitter parse tree.
Query Captures
Captures may be specified using the Tree-sitter query capture format, where an identifier beginning with an @
sign succeeds a node.
<query>
(start_tag (tag_name) @tag)
(self_closing_tag (tag_name) @tag)
</query>
This query captures the contents of the tag_name
tree node as “tag”, which may then be used in completion sets (see below).
Query captures beginning with provider.
are reserved for special provider attributes:
Capture | Description |
---|---|
@provider.start | Begin the provider’s region after this node |
@provider.start.before | Begin the provider’s region before this node |
@provider.end | End the provider’s region before this node |
@provider.end.after | End the provider’s region after this node |
@provider.subtree | Define the provider’s region as this node’s subtree |
Provider Region
The query may narrow the region of the parse tree in which the provider is valid by using special captures on nodes.
For example, when defining a provider query for a CSS ruleset block, you might have:
<query>
(rule_set
(block
"{" @provider.start
"}" @provider.end))
</query>
To scope completions for CSS attributes, such as border
, to within the ruleset’s block (inside the curly braces), the @provider.start
and @provider.end
captures are used to define the nodes on which the provider’s region is defined. This way, the provider will match within the ruleset’s block, but not within its selector or within the whitespace outside of its curly braces.
Query Predicates
In addition to standard predicate such as eq?
and match?
, provider queries may use a special set of predicates tailored specifically to completions:
cursor-in?
Enforces that the cursor is positioned within the specified capture.
Syntax: (#cursor-in? capture)
Since a provider query can match regardless of where the cursor is within its region, it can be useful to narrow the requirement further by enforcing that the cursor is within a specific capture of the query’s matched subtree.
<query>
((start_tag (tag_name) @tag
(attribute (attribute_name) @attr-name)+ @attr)
(#cursor-in? @attr)
(#not-match? @attr-name "(?i)^(class|id)$")
)
</query>
This query matches within HTML attributes, capturing the values tag
and attr-name
to represent the tag and attribute names, respectively.
It also captures the attribute node as attr
and uses the cursor-in?
predicate to ensure that the cursor is within the attribute. Finally, it uses the not-match?
to ensure that the matched attribute is not the HTML “class” or “id” attributes.
Combinator Selector
The <selector>
element defines a compound CSS-style selector expression which may use combinator operators for regular expression-based. A provider may only define a single selector element.
Note: The
<selector>
element is only compatible with Regular Expression-based grammars.
Several combinator operators and pseudo-selectors inspired by CSS are supported:
Operator | Description |
---|---|
, | Multiple selectors |
(space) | Indirect inheritance |
> | Direct inheritance |
+ | Direct adjacency |
~ | Indirect adjacency |
:has-child(selector) | Child detection |
:not(selector) | Negation / exclusion |
:capture(variable) | Captures |
When utilizing any inheritance operators, the inheritance tree referenced is the parse tree of the document.
Combinator Captures
Using a :capture(variable)
pseudo-selector on a specific component of the selector will “capture” its textual contents using a key named variable
. This key may be any valid alphanumeric identifier, including underscores and dashes:
<selector>mylang.attribute.name:capture(attr-name)</selector>
When defining completion sets (see “Static Completions” below), these variables may then be used in a string formatting syntax to change the completion set used.
Requesting Completion Sets
A provider may define one or more <set>
elements to declare which static completion sets are filtered and shown to the user when matched. The text of the element should be the name of a static completion set defined by any completions definition.
<provider>
<syntax>mylang</syntax>
<set>mylang.values</set>
</provider>
A completion set may be specified using string substitution, in which variables are replaced by text captured from the document:
<provider>
<syntax>mylang</syntax>
<query>
(rule_set
(rule_name) @rule-name
(block
"{" @provider.start
"}" @provider.end))
</query>
<set>mylang.${rule-name}</set>
</provider>
This provider requests a completion set which uses string substitution: mylang.${rule-name}
. The contents of the text captured by the rule-name
capture will be substituted when requesting it.
If the contents of the rule-name
capture within the document was border
, then the completion set requested would be mylang.border
.
Captures are provided differently for the two types of syntax: via <query>
for Tree-sitter-based grammars and <selector>
for Regular Expression-based grammars (see above).
Requesting Symbols
A provider may define one or more <symbols>
elements to declare which symbolic completion sets are filtered and shown to the user when matched.
See Symbolic Completions for more information.
Static Completions
Static completions are those that have predefined definitions unrelated to the documents in a user’s project, such as the standard library of a language or framework.
A <set>
element within the top-level completions element of the definition defines a set of related completions and how they behave when inserted.
Each completion set defines a name
attribute, used to reference the set in completion providers. Set names may contain the same set of characters as Scope names: alphanumeric characters, as well as the period, underscore, and dash.
Note: Static completion set names are defined globally to the parse and completion engine, much like syntax names.
As such, it is highly recommended that you name them in a specific way that is unlikely to confict with other languages and those provided by built-in and third-party extensions. It is common to name a completion set using the syntax or framework name in which they are valid, such as css.attributes.border
or react-framework.stdlib
.
<set name="javascript.classes">
<completion string="Array" />
<completion string="BigInt" />
<completion string="BigInt64Array" />
<completion string="BigUint64Array" />
<completion string="Boolean" />
[…additional completions…]
</set>
This completion set defines JavaScript built-in class names. The <set>
element contains multiple <completion>
elements that define each completion item.
Each <completion>
element within a static completion set defines one item that will be offered to a user in the completions list.
The string
attribute of the element is the base text that will be used when filtering based on the originating provider’s expression, as well as the base text inserted if the item is chosen.
The behavior of how completion items are inserted when chosen may be further modified using Behaviors.
The visual appearance of a completion may be further modified by several attributes of the completion element:
Attributes
Symbol Type
The symbol
attribute declares the type of symbol icon displayed to the user for the item:
<set name="javascript.classes">
<completion string="Array" symbol="class" />
<completion string="BigInt" symbol="class" />
<completion string="BigInt64Array" symbol="class" />
<completion string="BigUint64Array" symbol="class" />
<completion string="Boolean" symbol="class" />
[…additional completions…]
</set>
A completion that does not declare a symbol will not show a corresponding icon.
For convenience, this attribute may also be set on the <set>
element to apply to all completion items within that do not otherwise override it:
<set name="javascript.classes" symbol="class">
<completion string="Array" />
<completion string="BigInt" />
<completion string="BigInt64Array" />
<completion string="BigUint64Array" />
<completion string="Boolean" />
[…additional completions…]
</set>
Case Insensitivity
The case-insensitive
attribute may be applied with a value of "true"
to make the completion case-insensitive for matching. In this way, the completion will match text behind the cursor regardless of the case of that text.
Using |
as the cursor, a case-insensitive completion using the string "Array"
will match these expressions:
ar|
Ar|
AR|
Deprecation
The deprecated
element may be applied with a value of "true"
to mark the completion as deprecated in the completions list. Deprecated completions are deemphasized to the user, allowing them to be available but denoting that their use is discouraged.
Behaviors
Behaviors are a conditional feature that allow completions to define how they are presented and inserted into the document based on the text around them.
A <completion>
element may contain one or more <behavior>
elements. This forms an ordered array of behaviors that will be matched against the state of the document where the insertion is to take place. The first behavior (if any) that matches will be used. In this way, behaviors should be ordered most-specific to least-specific. If no behavior matches, the completion will be inserted without modifications.
Consider the following completion item for the CSS rgb()
function:
<completion string="rgb" symbol="function">
<behavior suffix="\(">
<append>($[])</append>
</behavior>
</completion>
The item defines the rgb
string that will be completed from user typing. There is one behavior defined within the item, indicating how the inserted text should be manipulated, using a suffix
attribute and an <append>
element (indicating the text will be appended to the completed text).
The suffix
attribute defines that the behavior should only be used if the provided regular expression matches at the end of the completing text position. This can allow behaviors to be applied only when certain text is (or isn’t) ahead of the cursor. Here, the behavior is only applied if there is no (
parenthesis after the cursor.
The $[]
is a shorthand syntax used in behaviors that indicates the editor should insert a token. When the completion is inserted, the cursor will automatically jump and select this token. By default, the token will be rendered using a simple ...
ellipses icon. Placing text inside of the square brackets, such as $[colors]
will render the token with that string within.
In this case, the behavior above appends a set of parenthesis with an insertion token inside, resulting in rgb(…)
being inserted into the editor.
Static completion behaviors support several option attributes:
prefix
: A regular expression pattern that must match text preceding the completion point for the behavior to be usedsuffix
: A regular expression pattern that must match text succeeding the completion point for the behavior to be used.symbol
: Behaves exactly as the same attribute on the completion item, but allows overriding of the symbol type displayed for insertion when matching this behavior.deprecated
: Behaves exactly as the same attribute on the completion item. When set totrue
, the item will be marked asdeprecated
when matching this behavior.shouldCompleteOnConfirm
: When set totrue
, completion will be attempted immediately after inserting the completion, as if the user had typed additional characters. This is most often useful for completion providers that do not require matching characters to be present.
Static completion behaviors support several text manipulation options elements:
<append>
: Text to append after the completion is inserted<prepend>
: Text to prepend before the completion is inserted
As a convenience, <behavior>
elements may be added to the <set>
element (generally at the top, but this is not enforced) to apply those behaviors to all completion items within that do not provide their own behaviors.
Symbolic Completions
Symbolic completions are those defined from the Symbols in the parse tree as well as the IDE’s workspace index.
Consider the following provider:
<provider name="javascript.string-formatting">
<syntax>javascript</syntax>
<match-selector>javascript.string-template</match-selector>
<expression>(?<=$\{)\b[a-zA-Z_][a-zA-Z0-9_]*</expression>
<symbols type="variable,constant" />
</provider>
This provider defines completions for string formatting expressions within a JavaScript string, which take the form "this is a ${adjective} string!"
.
Here, the <symbols>
element defines the types variable
and constant
. If this provider matches, it will offer all JavaScript variables and constants that are in currently in scope.
The full set of valid symbolic type identifiers are defined in the Symbol API reference.
More complex symbolic completions that affect how they are inserted into the document may be offered using Behaviors within each <symbols>
element:
<provider name="javascript.properties">
<syntax>javascript</syntax>
<exclude-selector>string,comment</exclude-selector>
<expression>(?<=\.)@?@?([a-zA-Z_][a-zA-Z0-9_]*)?</expression>
<symbols type="function">
<behavior>
<arguments prefix="(" suffix=")" separator=", " />
</behavior>
</symbols>
<symbols type="method">
<behavior>
<arguments prefix="(" suffix=")" separator=", " />
</behavior>
</symbols>
<symbols type="property,getter,setter" />
<set>javascript.properties</set>
</provider>
This provider will offer completions of JavaScript functions, methods, properties, getters, and setters.
For functions and methods, the behaviors define how indexed arguments for those symbols are written out into the document, including prepended and appended text and separators between tokens. See the Behaviors section for more information.
Behaviors
Behaviors are a conditional feature that allow completions to define how they are presented and inserted into the document based on the text around them.
A <symbols>
element may contain one or more <behavior>
elements. This forms an ordered array of behaviors that will be matched against the state of the document where the insertion is to take place. The first behavior (if any) that matches will be used. In this way, behaviors should be ordered most-specific to least-specific. If no behavior matches, the completion will be inserted without modifications.
Consider the following completion item for the CSS rgb()
function:
<symbols type="method">
<behavior prefix="(?<=def\s)">
<arguments prefix="(self" suffix=")" separator=", " prepend-separator="true" />
</behavior>
<behavior>
<arguments prefix="(" suffix=")" separator=", " />
</behavior>
</symbols>
The symbols element above defines symbolic completions for methods in Python. There are two behaviors defined within, indicating how the inserted text should be manipulated based on what text is after the cursor.
The prefix
attribute defines that the behavior should only be used if the provided regular expression matches at the head of the completing text position using a regular expression lookbehind. This can allow behaviors to be applied only when certain text is (or isn’t) ahead of the cursor. Here, the first behavior is used if the literal text def
appears befor the completion point. This affects how the arguments of the method are completed.
If the text def
precedes the cursor, a method foo
with two arguments (arg1
and arg2
) will be inserted as def foo(self, arg1, arg2)
(as in a method definition). If that text does not precede the cursor, it will be inserted as foo(arg1, arg2)
(as in a method invocation).
Symbolic completion behaviors support several option attributes:
prefix
: A regular expression pattern that must match text preceding the completion point for the behavior to be usedsuffix
: A regular expression pattern that must match text succeeding the completion point for the behavior to be used.shouldCompleteOnConfirm
: When set totrue
, completion will be attempted immediately after inserting the completion, as if the user had typed additional characters. This is most often useful for completion providers that do not require matching characters to be present.
Symbolic completion behaviors support several text manipulation options elements:
<append>
: Text to append after the completion is inserted<prepend>
: Text to prepend before the completion is inserted<arguments>
: How the argument list should be formatted for symbol types which apply, with the following attribute options:prefix
: Text to prepend to the arguments list (such as an opening parenthesis)suffix
: Text to append to the arguments list (such as a closing parenthesis)separator
: Text to insert between each argument (such as a comma and whitespace)prepend-separator
: Whether to prepend the separator before the first argument (false by default)prefix-each
: Text to prepend before each argument, after the separatorsuffix-each
: Text to append after each argument, before the separatorappend-empty
: Whether to append an empty argument list if there are zero arguments (true by default)tokenize
: Whether argument names should be turned into editor tokens (true by default)