This project uses a considerable amount of jargon, some adopted from the Language Server Protocol and some specific to Lexical.
This glossary attempts to define jargon used in this codebase. Though it is not exhaustive, we hope it helps contributors more easily navigate and understand existing code and the goal, and that it provides some guidance for naming new things.
You can help! If you run across a new term while working on Lexical and you think it should be defined here, please open an issue suggesting it!
This section covers features, names, and abstractions used by Lexical that have a correspondence to the Language Server Protocol. For a definitive reference, see the LSP Specification.
LSP defines a general heirarchy of the types of messages langauge servers and clients and may exchange, and the expected behaviours associated with them.
There's 3 top-level types of messages: Requests, Responses, and Notifications:
-
Requests are sent from client to server and vice versa, and must always be answered with a Response.
-
Notifications are likewise bi-directional and work like events. They expressly do not receive responses per LSP's specification.
From these 3 top-level types, LSP defines more specific more concrete, actionable messages such as:
... and many more. These can serve as good reference for the specific features you're working on.
Lexical maps these in the modules Lexical.Protocol.Requests
, Lexical.Protocol.Responses
, and Lexical.Protocol.Notifications
.
Finally, it's worth noting all messages are JSON, specifically JSON-RPC version 2.0.
A single file identified by a URI and contains textual content. Formally referred to as Text Documents in LSP and modeled as Lexical.Document
structs in Lexical.
Represents a diagnostic, such as a compiler error or warning. Diagnostic objects are only valid in the scope of a resource.
Auto-completion suggestions that appear in an editor's IntelliSense. For example, a user that's typed IO.in|
may be suggested IO.inspect(|)
as one of a few possible completions.
A code action represents a change that can be performed in code. In VSCode they typically appear as "quick fixes" next to an error or warning, but they aren't exclusive to that. In fact, VSCode frequently requests available code actions while users are browsing and editing code.
LSP defines a protocol for language servers to tell clients what actions they're capable of performing, and for clients to request those actions be taken. See for example LSP's CodeActionClientCapabilities interface.
This section briefly summarizes abstractions introduced by Lexical. Detailed information can be found in the respective moduledocs.
An Elixir struct that represents the current state of an elixir project. See Lexical.Project
.
Some LSP data structures cannot be trivially converted to Elixir terms.
The Lexical.Convertible
protocol helps centralize the necessary conversion logic where this is the case.
A behaviour responsible for reading, writing, serializing, and deserializing messages between the LSP client and Lexical language server.
The behaviour is defined in Lexical.Server.Transport
, with the implementation for stdio in Lexical.Server.Transport.StdIO
.
The Lexical.Completion.Translatable
protocol specifies how Elixir language constructs (such as behaviour callbacks) are converted into LSP constructs (such as completion items).
See Lexical.Server.CodeIntelligence.Completion.Translations
for various implementations.
A variety of modules that change existing code in some way. They take a document, modify it, and return diffs.
Examples of code mods include:
- Formatting code in a file (
> Format Document
/shift
+alt
+f
in VSCode). - Prefixing unused variables with an
_
.
Code mods are defined in the remote_control
sub-app and are executed in the project's virutal machine.