Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -125,8 +125,8 @@ target/release/rcl fmt examples/tags.rcl

RCL is usable and useful, well-tested, and well-documented. It is still pre-1.0,
though backwards-incompatible changes have been rare in the past years. Syntax
highlighting is available for major editors like Vim, Emacs, Helix, and Zed.
RCL is a community project without commercial support.
highlighting is available for major editors like Vim, Emacs, Helix, VSCode, and
Zed. RCL is a community project without commercial support.

## Support RCL

Expand Down
16 changes: 16 additions & 0 deletions build.rcl
Original file line number Diff line number Diff line change
Expand Up @@ -17,12 +17,28 @@ let target_toml = contents => {
contents = contents,
};

let target_json = contents => {
format = "json",
contents = contents,
};

{
"Cargo.toml": target_toml(import "//Cargo.rcl"),
"fuzz/Cargo.toml": target_toml(import "//fuzz/Cargo.rcl"),
"grammar/tree-sitter-rcl/Cargo.toml": target_toml(
import "//grammar/tree-sitter-rcl/Cargo.rcl",
),
"grammar/vscode/language-configuration.json": target_json(
import "//grammar/vscode/language-configuration.rcl",
),
// TODO: Maybe instead of checking these generated json files
// in to the repository, we can just generate them at package build time.
"grammar/vscode/package.json": target_json(
import "//grammar/vscode/package.rcl",
),
"grammar/vscode/rcl.tmLanguage.json": target_json(
import "//grammar/vscode/rcl.tmLanguage.rcl",
),
"grammar/zed/extension.toml": target_toml(
import "//grammar/zed/extension.rcl",
),
Expand Down
20 changes: 20 additions & 0 deletions docs/grammars.md
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,26 @@ to use for highlighting, similar to scopes for Tree Sitter.

[vim-groups]: https://vimhelp.org/syntax.txt.html#group-name

## Visual Studio Code

The `vscode` directory contains the Visual Studio Code plugin including TextMate
grammar. The json version of the grammar is generated with <abbr>RCL</abbr>. The
TextMate documentation has [a section on scope naming conventions][tm-scopes].
Some helpful links:

* [TextMate language grammar documentation][tm-docs]
* [Helpful _lessons learned_ blog post][tm-lessons]
* [VSCode syntax highlighting docs][vscode-highlight]

[tm-docs]: https://macromates.com/manual/en/language_grammars
[tm-scopes]: https://macromates.com/manual/en/language_grammars#naming_conventions
[tm-lessons]: https://www.apeth.com/nonblog/stories/textmatebundle.html
[vscode-highlight]: https://code.visualstudio.com/api/language-extensions/syntax-highlight-guide

The Nix flake includes a <abbr>VSIX</abbr> extension package. To build it:

nix build .#vscode-extension

## Zed

The `zed` directory contains the Zed plugin. This directory is the source of
Expand Down
4 changes: 2 additions & 2 deletions docs/index.md
Original file line number Diff line number Diff line change
Expand Up @@ -53,8 +53,8 @@ For an interactive demo in your browser, see <https://rcl-lang.org>.

RCL is usable and useful, well-tested, and well-documented. It is still pre-1.0,
though backwards-incompatible changes have been rare in the past years. Syntax
highlighting is available for major editors like Vim, Emacs, Helix, and Zed.
RCL is a community project without commercial support.
highlighting is available for major editors like Vim, Emacs, Helix, VSCode, and
Zed. RCL is a community project without commercial support.

## License

Expand Down
13 changes: 13 additions & 0 deletions docs/syntax_highlighting.md
Original file line number Diff line number Diff line change
Expand Up @@ -91,6 +91,19 @@ The directory `grammar/rcl.vim` contains support for highlighting in Vim.
You can symlink the contents into your `~/.vim`, or use a plugin manager like
Pathogen and symlink the directory into `~/.vim/bundle`.

## Visual Studio Code

The [Visual Studio Code extension][vscode-ext] is available from the Visual
Studio marketplace.

If you want to install a development version of the extension, the extension
is developed in the main repository. See [the section in the grammars
chapter][grammars-vscode] for how to build it, then install the extension using
_Extensions: Install from <abbr>VSIX</abbr>…_ from the command panel.

[vscode-ext]: https://marketplace.visualstudio.com/items?itemName=rcl-lang.rcl
[grammars-vscode]: grammars.md#visual-studio-code

## Zed

The [Zed extension](https://github.com/rcl-lang/zed-rcl) is available from the
Expand Down
33 changes: 28 additions & 5 deletions flake.nix
Original file line number Diff line number Diff line change
Expand Up @@ -158,7 +158,7 @@

pythonSources = pkgs.lib.sourceFilesBySuffices ./. [ ".py" ".pyi" ];

rclTomlSources = pkgs.lib.sourceFilesBySuffices ./. [ ".rcl" ".toml" ];
rclGeneratedSources = pkgs.lib.sourceFilesBySuffices ./. [ ".rcl" ".toml" ".json" ];

goldenSources = ./golden;

Expand Down Expand Up @@ -412,6 +412,29 @@
RUSTFLAGS = "-C instrument-coverage -C link-dead-code -C debug-assertions";
});

vscode-extension = pkgs.stdenv.mkDerivation {
pname = "rcl-vscode";
inherit version;
src = ./grammar/vscode;
nativeBuildInputs = [ pkgs.vsce ];
doCheck = false;
buildPhase =
''
# We want only the json files, not the RCL sources. Also, the
# `vsce` tool complains if there is no LICENSE file, so copy it
# in.
rm *.rcl
cp ${./LICENSE} LICENSE

# TODO: The VSIX file is just a zip file of the directory, with
# two additional XML files in it. One of them may be kind of a
# pain to generate, but on the other hand, we could skip nodejs
# if we build the zip file ourselves.
mkdir -p $out
vsce package --no-dependencies --out $out/rcl-${version}.vsix
'';
};

in
rec {
devShells.default = pkgs.mkShell {
Expand Down Expand Up @@ -503,14 +526,14 @@
"check-fmt-rcl"
{ buildInputs = [ debugBuild ]; }
''
rcl format --check ${rclTomlSources}/**.rcl | tee $out
rcl format --check ${rclGeneratedSources}/**.rcl | tee $out
'';

buildRcl = pkgs.runCommand
"check-rcl-build"
{ buildInputs = [ debugBuild ]; }
''
rcl build --check --directory ${rclTomlSources} | tee $out
rcl build --check --directory ${rclGeneratedSources} | tee $out
'';

# Build documentation with warnings denied, so the check fails if
Expand Down Expand Up @@ -545,7 +568,7 @@
};

packages = {
inherit fuzzers-coverage rcl pyrcl pyrcl-wheel treeSitterRcl website;
inherit fuzzers-coverage rcl pyrcl pyrcl-wheel treeSitterRcl vscode-extension website;

default = rcl;
binaries = rcl-binaries;
Expand All @@ -561,7 +584,7 @@
RCL_BIN=${coverageBuild}/bin/rcl python3 ${goldenSources}/run.py

# Also run `rcl build` to make sure we cover that part of the application.
${coverageBuild}/bin/rcl build --check --directory ${rclTomlSources}
${coverageBuild}/bin/rcl build --check --directory ${rclGeneratedSources}

# Copy in the .profraw files from the tests.
cp ${coverageBuild}/prof/*.profraw .
Expand Down
2 changes: 2 additions & 0 deletions grammar/vscode/CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
Changes to the VSCode extension are listed as part of
[the regular RCL changelog](https://docs.ruuda.nl/rcl/changelog/).
26 changes: 26 additions & 0 deletions grammar/vscode/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
# The RCL Configuration Language

This extension provides support for the [RCL configuration language][rcl-lang].
The RCL configuration language is a domain-specific language that extends json
into a simple, gradually typed, functional language that resembles Python and
Nix. It reduces configuration boilerplate by enabling abstraction and reuse.

* [Website and online playground][rcl-lang]
* [General documentation][docs]

[rcl-lang]: https://rcl-lang.org/
[docs]: https://docs.ruuda.nl/rcl/

# About

This extension is official. It is developed upstream as part of the main
repository, in the `grammar/vscode` directory. It is available from the
following mirrors:

* <https://codeberg.org/ruuda/rcl>
* <https://github.com/ruuda/rcl>

For hacking on the extension itself, see the [Grammars][docs-grammars] chapter
of the documentation.

[docs-grammars]: https://docs.ruuda.nl/rcl/grammars/#visual-studio-code
12 changes: 12 additions & 0 deletions grammar/vscode/language-configuration.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
{
"autoCloseBefore": ":.,",
"autoClosingPairs": [
{"close": "}", "open": "{"},
{"close": "]", "open": "["},
{"close": ")", "open": "("},
{"close": "\"", "notIn": ["string"], "open": "\""}
],
"brackets": [["{", "}"], ["[", "]"], ["(", ")"]],
"comments": {"lineComment": "//"},
"surroundingPairs": [["\"", "\""], ["(", ")"], ["[", "]"], ["{", "}"]]
}
29 changes: 29 additions & 0 deletions grammar/vscode/language-configuration.rcl
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
// RCL -- A reasonable configuration language.
// Copyright 2025 Ruud van Asseldonk

// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// A copy of the License has been included in the root of the repository.

let brackets = [
["{", "}"],
["[", "]"],
["(", ")"],
];

{
comments = { lineComment = "//" },
brackets = brackets,
autoClosingPairs = [
for b in brackets: { open = b[0], close = b[1] },
{ open = "\"", close = "\"", notIn = ["string"] },
],
autoCloseBefore = ":.,",
surroundingPairs = {
for b in brackets: b,
["\"", "\""],
},
// TODO: Add `folding`?
// TODO: Add `wordPattern`?
// TODO: Add `indentationRules`? I can't make sense of the example regex.
}
34 changes: 34 additions & 0 deletions grammar/vscode/package.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
{
"author": {"name": "Ruud van Asseldonk"},
"categories": ["Programming Languages"],
"contributes": {
"configurationDefaults": {
"[rcl]": {"editor.insertSpaces": true, "editor.tabSize": 2}
},
"grammars": [
{
"language": "rcl",
"path": "./rcl.tmLanguage.json",
"scopeName": "source.rcl"
}
],
"languages": [
{
"aliases": ["RCL"],
"configuration": "./language-configuration.json",
"extensions": [".rcl"],
"id": "rcl"
}
]
},
"description": "Support for the RCL configuration language.",
"displayName": "RCL",
"engines": {"vscode": "^1.100.0"},
"homepage": "https://rcl-lang.org",
"license": "Apache-2.0",
"name": "rcl",
"preview": true,
"publisher": "rcl-lang",
"repository": {"type": "git", "url": "https://github.com/ruuda/rcl.git"},
"version": "0.13.0"
}
43 changes: 43 additions & 0 deletions grammar/vscode/package.rcl
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
let root = import "//Cargo.rcl";

{
name = "rcl",
displayName = "RCL",
description = "Support for the RCL configuration language.",
// TODO: Remove the preview designation once the extension is ready.
preview = true,
version = root.package.version,
license = root.package.license,
author = { name = "Ruud van Asseldonk" },
publisher = "rcl-lang",

engines = { vscode = "^1.100.0" },
categories = ["Programming Languages"],

repository = { type = "git", url = "https://github.com/ruuda/rcl.git" },
homepage = "https://rcl-lang.org",

contributes = {
languages = [
{
id = "rcl",
aliases = ["RCL"],
extensions = [".rcl"],
configuration = "./language-configuration.json",
},
],
grammars = [
{
language = "rcl",
scopeName = "source.rcl",
path = "./rcl.tmLanguage.json",
},
],
configurationDefaults = {
"[rcl]": {
"editor.tabSize": 2,
"editor.insertSpaces": true,
},
},
},
}
Loading