diff --git a/flake.nix b/flake.nix index 2bc7ae8c..6e4ae51d 100644 --- a/flake.nix +++ b/flake.nix @@ -35,10 +35,49 @@ (system: let pkgs = import nixpkgs { inherit system; }; + extractRustAnalyzer = { stdenv, pkgs }: stdenv.mkDerivation { + pname = "extract_rust_analyzer"; + version = "master"; + + dontUnpack = true; + dontBuild = true; + + buildInputs = [ pkgs.python3 ]; + + installPhase = '' + ls -la + mkdir -p $out/bin + cp ${./helpers/extract_rust_analyzer.py} $out/bin/extract_rust_analyzer.py + ''; + }; + extractRustAnalyzerPkg = pkgs.callPackage extractRustAnalyzer { }; in { - packages.docs = pkgs.callPackage (import ./docs.nix) { - modules = nixvimModules; + packages = { + docs = pkgs.callPackage (import ./docs.nix) { + modules = nixvimModules; + }; + runUpdates = pkgs.callPackage + ({ pkgs, stdenv }: stdenv.mkDerivation { + pname = "run-updates"; + version = pkgs.rust-analyzer.version; + + src = pkgs.rust-analyzer.src; + + nativeBuildInputs = with pkgs; [extractRustAnalyzerPkg alejandra nixpkgs-fmt]; + + buildPhase = '' + extract_rust_analyzer.py editors/code/package.json | + alejandra --quiet | + nixpkgs-fmt > rust-analyzer-config.nix + ''; + + installPhase = '' + mkdir -p $out/share + cp rust-analyzer-config.nix $out/share + ''; + }) + { }; }; legacyPackages = rec { makeNixvimWithModule = import ./wrappers/standalone.nix pkgs modules; diff --git a/helpers/extract_rust_analyzer.py b/helpers/extract_rust_analyzer.py new file mode 100755 index 00000000..4c88826a --- /dev/null +++ b/helpers/extract_rust_analyzer.py @@ -0,0 +1,229 @@ +#!/usr/bin/env python3 + +import sys +import json + +ra_package_json = sys.argv[1] +with open(ra_package_json) as f: + ra_package = json.load(f) + +config = ra_package["contributes"]["configuration"]["properties"] + +config_dict = {} + +in_common_block = False + + +def py_to_nix(obj): + if obj is None: + return "null" + + if obj is False: + return "false" + + if obj is True: + return "true" + + if isinstance(obj, str): + s = f'"{obj}"' + if "${" in s: + s = s.replace("${", "$\\{") + return s + + if isinstance(obj, int): + return f"{obj}" + + if isinstance(obj, dict): + val = "{" + for key in obj: + key_val = py_to_nix(obj[key]) + val += f'"{key}" = {key_val};\n' + val += "}" + + return val + + if isinstance(obj, list): + return "[" + " ".join(py_to_nix(val) for val in obj) + "]" + + print(f"Unhandled value: {obj}") + sys.exit(1) + + +def ty_to_nix(ty): + if ty == "boolean": + return "types.bool" + + if ty == "string": + return "types.str" + + # This is an object without any additional properties + if ty == "object": + return "types.attrsOf types.anything" + + if isinstance(ty, list) and ty[0] == "null": + if len(ty) > 2: + print("Unhandled type", ty) + sys.exit() + + nullable_ty = ty_to_nix(ty[1]) + return f"types.nullOr ({nullable_ty})" + + if isinstance(ty, list): + either_types = (ty_to_nix(t) for t in ty) + either_types = " ".join(f"({t})" for t in either_types) + return f"types.oneOf ([{either_types}])" + + print(f"Unhandled type: {ty}") + sys.exit(1) + + +def prop_ty_to_nix(prop_info): + if "type" in prop_info: + if "enum" in prop_info: + enum = "[" + " ".join(f'"{member}"' for member in prop_info["enum"]) + "]" + if prop_info["type"] == "string": + return f"types.enum {enum}" + + print("TODO: with unknown enum type", prop_info["type"]) + sys.exit() + + if "additionalProperties" in prop_info or "properties" in prop_info: + print("TODO: with (additional)Properties", prop_info) + sys.exit() + + if "minimum" in prop_info or "maximum" in prop_info: + can_be_null = False + if "null" in prop_info["type"]: + can_be_null = True + if len(prop_info["type"]) > 2: + print("Unhandled int type", prop_info["type"]) + sys.exit() + prop_info["type"] = prop_info["type"][1] + + if prop_info["type"] == "number": + int_ty = "types.number" + elif prop_info["type"] == "integer": + int_ty = "types.int" + else: + print("Unhandled int type", prop_info["type"]) + sys.exit() + + if "minimum" in prop_info and "maximum" in prop_info: + min = prop_info["minimum"] + max = prop_info["maximum"] + int_ty = f"{int_ty}s.between {min} {max}" + elif "minimum" in prop_info: + min = prop_info["minimum"] + int_ty = f"types.addCheck {int_ty} (x: x >= {min})" + else: + print("TODO: max number", prop_info) + sys.exit() + + if can_be_null: + return f"types.nullOr ({int_ty})" + else: + return int_ty + + if "array" in prop_info["type"] or prop_info["type"] == "array": + if "items" not in prop_info: + print("Array without items") + sys.exit() + + items_ty = prop_ty_to_nix(prop_info["items"]) + array_ty = f"types.listOf ({items_ty})" + if prop_info["type"] == "array": + return array_ty + elif prop_info["type"] == ["null", "array"]: + return f"types.nullOr ({array_ty})" + else: + print("Unhandled array type", prop_info) + sys.exit() + + return ty_to_nix(prop_info["type"]) + elif "anyOf" in prop_info: + can_be_null = False + if {"type": "null"} in prop_info["anyOf"]: + can_be_null = True + prop_info["anyOf"].remove({"type": "null"}) + + types = (prop_ty_to_nix(prop) for prop in prop_info["anyOf"]) + one_of = " ".join(f"({ty})" for ty in types) + one_of_ty = f"types.oneOf ([{one_of}])" + + if can_be_null: + return f"types.nullOr ({one_of_ty})" + else: + return one_of_ty + else: + print("TODO: no *type*", prop_info) + sys.exit() + + +for opt in config: + if opt.startswith("$"): + in_common_block = True + continue + + if not in_common_block: + continue + + opt_path = opt.split(".") + if opt_path[0] != "rust-analyzer": + print("ERROR: expected all options to start with 'rust-analyzer'") + sys.exit(1) + + path = opt_path[1:-1] + option = opt_path[-1] + + top_dict = config_dict + + for p in path: + if not p in top_dict: + top_dict[p] = {} + top_dict = top_dict[p] + + prop_info = config[opt] + + is_optional = False + + ty = prop_ty_to_nix(prop_info) + + default = py_to_nix(prop_info["default"]) + + if "markdownDescription" in prop_info: + desc = prop_info["markdownDescription"] + else: + desc = prop_info["description"] + + desc += f"\n\ndefault value is: \n```nix\n {default}\n```" + + top_dict[ + option + ] = """ +mkOption {{ +type = types.nullOr ({ty}); +default = null; +description = '' +{desc} +''; +}} + """.format( + ty=ty, default=default, desc=desc + ) + + +def print_dict(d): + print("{") + for key in d: + print(f'"{key}" = ') + if isinstance(d[key], str): + print(d[key]) + else: + print_dict(d[key]) + print(";") + print("}") + + +print("# THIS FILE IS AUTOGENERATED DO NOT EDIT") +print("lib: with lib;") +print_dict(config_dict) diff --git a/plugins/nvim-lsp/basic-servers.nix b/plugins/nvim-lsp/basic-servers.nix index 0208bbdc..ce496b0f 100644 --- a/plugins/nvim-lsp/basic-servers.nix +++ b/plugins/nvim-lsp/basic-servers.nix @@ -197,6 +197,9 @@ let name = "rust-analyzer"; description = "Enable rust-analyzer, for Rust."; serverName = "rust_analyzer"; + + extraOptions = import ./rust-analyzer-config.nix lib; + settings = cfg: { rust-analyzer = cfg; }; } { name = "sumneko-lua"; diff --git a/plugins/nvim-lsp/rust-analyzer-config.nix b/plugins/nvim-lsp/rust-analyzer-config.nix new file mode 100644 index 00000000..3bf0ee9c --- /dev/null +++ b/plugins/nvim-lsp/rust-analyzer-config.nix @@ -0,0 +1,1560 @@ +# THIS FILE IS AUTOGENERATED DO NOT EDIT +lib: with lib; { + "assist" = { + "expressionFillDefault" = mkOption { + type = types.nullOr (types.enum [ "todo" "default" ]); + default = null; + description = '' + Placeholder expression to use for missing expressions in assists. + + default value is: + ```nix + "todo" + ``` + ''; + }; + }; + "cachePriming" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Warm up caches on project load. + + default value is: + ```nix + true + ``` + ''; + }; + "numThreads" = mkOption { + type = types.nullOr (types.numbers.between 0 255); + default = null; + description = '' + How many worker threads to handle priming caches. The default `0` means to pick automatically. + + default value is: + ```nix + 0 + ``` + ''; + }; + }; + "cargo" = { + "autoreload" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Automatically refresh project info via `cargo metadata` on + `Cargo.toml` or `.cargo/config.toml` changes. + + default value is: + ```nix + true + ``` + ''; + }; + "buildScripts" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Run build scripts (`build.rs`) for more precise code analysis. + + default value is: + ```nix + true + ``` + ''; + }; + "overrideCommand" = mkOption { + type = types.nullOr (types.nullOr (types.listOf (types.str))); + default = null; + description = '' + Override the command rust-analyzer uses to run build scripts and + build procedural macros. The command is required to output json + and should therefore include `--message-format=json` or a similar + option. + + By default, a cargo invocation will be constructed for the configured + targets and features, with the following base command line: + + ```bash + cargo check --quiet --workspace --message-format=json --all-targets + ``` + . + + default value is: + ```nix + null + ``` + ''; + }; + "useRustcWrapper" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Use `RUSTC_WRAPPER=rust-analyzer` when running build scripts to + avoid checking unnecessary things. + + default value is: + ```nix + true + ``` + ''; + }; + }; + "features" = mkOption { + type = types.nullOr (types.oneOf [ (types.enum [ "all" ]) (types.listOf (types.str)) ]); + default = null; + description = '' + List of features to activate. + + Set this to `"all"` to pass `--all-features` to cargo. + + default value is: + ```nix + [] + ``` + ''; + }; + "noDefaultFeatures" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to pass `--no-default-features` to cargo. + + default value is: + ```nix + false + ``` + ''; + }; + "noSysroot" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Internal config for debugging, disables loading of sysroot crates. + + default value is: + ```nix + false + ``` + ''; + }; + "target" = mkOption { + type = types.nullOr (types.nullOr (types.str)); + default = null; + description = '' + Compilation target override (target triple). + + default value is: + ```nix + null + ``` + ''; + }; + "unsetTest" = mkOption { + type = types.nullOr (types.listOf (types.str)); + default = null; + description = '' + Unsets `#[cfg(test)]` for the specified crates. + + default value is: + ```nix + ["core"] + ``` + ''; + }; + }; + "checkOnSave" = { + "allTargets" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Check all targets and tests (`--all-targets`). + + default value is: + ```nix + true + ``` + ''; + }; + "command" = mkOption { + type = types.nullOr (types.str); + default = null; + description = '' + Cargo command to use for `cargo check`. + + default value is: + ```nix + "check" + ``` + ''; + }; + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Run specified `cargo check` command for diagnostics on save. + + default value is: + ```nix + true + ``` + ''; + }; + "extraArgs" = mkOption { + type = types.nullOr (types.listOf (types.str)); + default = null; + description = '' + Extra arguments for `cargo check`. + + default value is: + ```nix + [] + ``` + ''; + }; + "features" = mkOption { + type = types.nullOr (types.nullOr (types.oneOf [ (types.enum [ "all" ]) (types.listOf (types.str)) ])); + default = null; + description = '' + List of features to activate. Defaults to + `#rust-analyzer.cargo.features#`. + + Set to `"all"` to pass `--all-features` to Cargo. + + default value is: + ```nix + null + ``` + ''; + }; + "noDefaultFeatures" = mkOption { + type = types.nullOr (types.nullOr (types.bool)); + default = null; + description = '' + Whether to pass `--no-default-features` to Cargo. Defaults to + `#rust-analyzer.cargo.noDefaultFeatures#`. + + default value is: + ```nix + null + ``` + ''; + }; + "overrideCommand" = mkOption { + type = types.nullOr (types.nullOr (types.listOf (types.str))); + default = null; + description = '' + Override the command rust-analyzer uses instead of `cargo check` for + diagnostics on save. The command is required to output json and + should therefor include `--message-format=json` or a similar option. + + If you're changing this because you're using some tool wrapping + Cargo, you might also want to change + `#rust-analyzer.cargo.buildScripts.overrideCommand#`. + + If there are multiple linked projects, this command is invoked for + each of them, with the working directory being the project root + (i.e., the folder containing the `Cargo.toml`). + + An example command would be: + + ```bash + cargo check --workspace --message-format=json --all-targets + ``` + . + + default value is: + ```nix + null + ``` + ''; + }; + "target" = mkOption { + type = types.nullOr (types.nullOr (types.str)); + default = null; + description = '' + Check for a specific target. Defaults to + `#rust-analyzer.cargo.target#`. + + default value is: + ```nix + null + ``` + ''; + }; + }; + "completion" = { + "autoimport" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Toggles the additional completions that automatically add imports when completed. + Note that your client must specify the `additionalTextEdits` LSP client capability to truly have this feature enabled. + + default value is: + ```nix + true + ``` + ''; + }; + }; + "autoself" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Toggles the additional completions that automatically show method calls and field accesses + with `self` prefixed to them when inside a method. + + default value is: + ```nix + true + ``` + ''; + }; + }; + "callable" = { + "snippets" = mkOption { + type = types.nullOr (types.enum [ "fill_arguments" "add_parentheses" "none" ]); + default = null; + description = '' + Whether to add parenthesis and argument snippets when completing function. + + default value is: + ```nix + "fill_arguments" + ``` + ''; + }; + }; + "postfix" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to show postfix snippets like `dbg`, `if`, `not`, etc. + + default value is: + ```nix + true + ``` + ''; + }; + }; + "privateEditable" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Enables completions of private items and fields that are defined in the current workspace even if they are not visible at the current position. + + default value is: + ```nix + false + ``` + ''; + }; + }; + "snippets" = { + "custom" = mkOption { + type = types.nullOr (types.attrsOf types.anything); + default = null; + description = '' + Custom completion snippets. + + default value is: + ```nix + {"Arc::new" = {"postfix" = "arc"; + "body" = "Arc::new($\{receiver})"; + "requires" = "std::sync::Arc"; + "description" = "Put the expression into an `Arc`"; + "scope" = "expr"; + }; + "Rc::new" = {"postfix" = "rc"; + "body" = "Rc::new($\{receiver})"; + "requires" = "std::rc::Rc"; + "description" = "Put the expression into an `Rc`"; + "scope" = "expr"; + }; + "Box::pin" = {"postfix" = "pinbox"; + "body" = "Box::pin($\{receiver})"; + "requires" = "std::boxed::Box"; + "description" = "Put the expression into a pinned `Box`"; + "scope" = "expr"; + }; + "Ok" = {"postfix" = "ok"; + "body" = "Ok($\{receiver})"; + "description" = "Wrap the expression in a `Result::Ok`"; + "scope" = "expr"; + }; + "Err" = {"postfix" = "err"; + "body" = "Err($\{receiver})"; + "description" = "Wrap the expression in a `Result::Err`"; + "scope" = "expr"; + }; + "Some" = {"postfix" = "some"; + "body" = "Some($\{receiver})"; + "description" = "Wrap the expression in an `Option::Some`"; + "scope" = "expr"; + }; + } + ``` + ''; + }; + }; + }; + "diagnostics" = { + "disabled" = mkOption { + type = types.nullOr (types.listOf (types.str)); + default = null; + description = '' + List of rust-analyzer diagnostics to disable. + + default value is: + ```nix + [] + ``` + ''; + }; + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to show native rust-analyzer diagnostics. + + default value is: + ```nix + true + ``` + ''; + }; + "experimental" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to show experimental rust-analyzer diagnostics that might + have more false positives than usual. + + default value is: + ```nix + false + ``` + ''; + }; + }; + "remapPrefix" = mkOption { + type = types.nullOr (types.attrsOf types.anything); + default = null; + description = '' + Map of prefixes to be substituted when parsing diagnostic file paths. + This should be the reverse mapping of what is passed to `rustc` as `--remap-path-prefix`. + + default value is: + ```nix + {} + ``` + ''; + }; + "warningsAsHint" = mkOption { + type = types.nullOr (types.listOf (types.str)); + default = null; + description = '' + List of warnings that should be displayed with hint severity. + + The warnings will be indicated by faded text or three dots in code + and will not show up in the `Problems Panel`. + + default value is: + ```nix + [] + ``` + ''; + }; + "warningsAsInfo" = mkOption { + type = types.nullOr (types.listOf (types.str)); + default = null; + description = '' + List of warnings that should be displayed with info severity. + + The warnings will be indicated by a blue squiggly underline in code + and a blue icon in the `Problems Panel`. + + default value is: + ```nix + [] + ``` + ''; + }; + }; + "files" = { + "excludeDirs" = mkOption { + type = types.nullOr (types.listOf (types.str)); + default = null; + description = '' + These directories will be ignored by rust-analyzer. They are + relative to the workspace root, and globs are not supported. You may + also need to add the folders to Code's `files.watcherExclude`. + + default value is: + ```nix + [] + ``` + ''; + }; + "watcher" = mkOption { + type = types.nullOr (types.enum [ "client" "server" ]); + default = null; + description = '' + Controls file watching implementation. + + default value is: + ```nix + "client" + ``` + ''; + }; + }; + "highlightRelated" = { + "breakPoints" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Enables highlighting of related references while the cursor is on `break`, `loop`, `while`, or `for` keywords. + + default value is: + ```nix + true + ``` + ''; + }; + }; + "exitPoints" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Enables highlighting of all exit points while the cursor is on any `return`, `?`, `fn`, or return type arrow (`->`). + + default value is: + ```nix + true + ``` + ''; + }; + }; + "references" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Enables highlighting of related references while the cursor is on any identifier. + + default value is: + ```nix + true + ``` + ''; + }; + }; + "yieldPoints" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Enables highlighting of all break points for a loop or block context while the cursor is on any `async` or `await` keywords. + + default value is: + ```nix + true + ``` + ''; + }; + }; + }; + "hover" = { + "actions" = { + "debug" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to show `Debug` action. Only applies when + `#rust-analyzer.hover.actions.enable#` is set. + + default value is: + ```nix + true + ``` + ''; + }; + }; + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to show HoverActions in Rust files. + + default value is: + ```nix + true + ``` + ''; + }; + "gotoTypeDef" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to show `Go to Type Definition` action. Only applies when + `#rust-analyzer.hover.actions.enable#` is set. + + default value is: + ```nix + true + ``` + ''; + }; + }; + "implementations" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to show `Implementations` action. Only applies when + `#rust-analyzer.hover.actions.enable#` is set. + + default value is: + ```nix + true + ``` + ''; + }; + }; + "references" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to show `References` action. Only applies when + `#rust-analyzer.hover.actions.enable#` is set. + + default value is: + ```nix + false + ``` + ''; + }; + }; + "run" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to show `Run` action. Only applies when + `#rust-analyzer.hover.actions.enable#` is set. + + default value is: + ```nix + true + ``` + ''; + }; + }; + }; + "documentation" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to show documentation on hover. + + default value is: + ```nix + true + ``` + ''; + }; + "keywords" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to show keyword hover popups. Only applies when + `#rust-analyzer.hover.documentation.enable#` is set. + + default value is: + ```nix + true + ``` + ''; + }; + }; + }; + "links" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Use markdown syntax for links in hover. + + default value is: + ```nix + true + ``` + ''; + }; + }; + }; + "imports" = { + "granularity" = { + "enforce" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to enforce the import granularity setting for all files. If set to false rust-analyzer will try to keep import styles consistent per file. + + default value is: + ```nix + false + ``` + ''; + }; + "group" = mkOption { + type = types.nullOr (types.enum [ "preserve" "crate" "module" "item" ]); + default = null; + description = '' + How imports should be grouped into use statements. + + default value is: + ```nix + "crate" + ``` + ''; + }; + }; + "group" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Group inserted imports by the [following order](https://rust-analyzer.github.io/manual.html#auto-import). Groups are separated by newlines. + + default value is: + ```nix + true + ``` + ''; + }; + }; + "merge" = { + "glob" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to allow import insertion to merge new imports into single path glob imports like `use std::fmt::*;`. + + default value is: + ```nix + true + ``` + ''; + }; + }; + "prefix" = mkOption { + type = types.nullOr (types.enum [ "plain" "self" "crate" ]); + default = null; + description = '' + The path structure for newly inserted paths to use. + + default value is: + ```nix + "plain" + ``` + ''; + }; + }; + "inlayHints" = { + "bindingModeHints" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to show inlay type hints for binding modes. + + default value is: + ```nix + false + ``` + ''; + }; + }; + "chainingHints" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to show inlay type hints for method chains. + + default value is: + ```nix + true + ``` + ''; + }; + }; + "closingBraceHints" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to show inlay hints after a closing `}` to indicate what item it belongs to. + + default value is: + ```nix + true + ``` + ''; + }; + "minLines" = mkOption { + type = types.nullOr (types.addCheck types.int (x: x >= 0)); + default = null; + description = '' + Minimum number of lines required before the `}` until the hint is shown (set to 0 or 1 + to always show them). + + default value is: + ```nix + 25 + ``` + ''; + }; + }; + "closureReturnTypeHints" = { + "enable" = mkOption { + type = types.nullOr (types.enum [ "always" "never" "with_block" ]); + default = null; + description = '' + Whether to show inlay type hints for return types of closures. + + default value is: + ```nix + "never" + ``` + ''; + }; + }; + "lifetimeElisionHints" = { + "enable" = mkOption { + type = types.nullOr (types.enum [ "always" "never" "skip_trivial" ]); + default = null; + description = '' + Whether to show inlay type hints for elided lifetimes in function signatures. + + default value is: + ```nix + "never" + ``` + ''; + }; + "useParameterNames" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to prefer using parameter names as the name for elided lifetime hints if possible. + + default value is: + ```nix + false + ``` + ''; + }; + }; + "maxLength" = mkOption { + type = types.nullOr (types.nullOr (types.addCheck types.int (x: x >= 0))); + default = null; + description = '' + Maximum length for inlay hints. Set to null to have an unlimited length. + + default value is: + ```nix + 25 + ``` + ''; + }; + "parameterHints" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to show function parameter name inlay hints at the call + site. + + default value is: + ```nix + true + ``` + ''; + }; + }; + "reborrowHints" = { + "enable" = mkOption { + type = types.nullOr (types.enum [ "always" "never" "mutable" ]); + default = null; + description = '' + Whether to show inlay type hints for compiler inserted reborrows. + + default value is: + ```nix + "never" + ``` + ''; + }; + }; + "renderColons" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to render leading colons for type hints, and trailing colons for parameter hints. + + default value is: + ```nix + true + ``` + ''; + }; + "typeHints" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to show inlay type hints for variables. + + default value is: + ```nix + true + ``` + ''; + }; + "hideClosureInitialization" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to hide inlay type hints for `let` statements that initialize to a closure. + Only applies to closures with blocks, same as `#rust-analyzer.inlayHints.closureReturnTypeHints.enable#`. + + default value is: + ```nix + false + ``` + ''; + }; + "hideNamedConstructor" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to hide inlay type hints for constructors. + + default value is: + ```nix + false + ``` + ''; + }; + }; + }; + "joinLines" = { + "joinAssignments" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Join lines merges consecutive declaration and initialization of an assignment. + + default value is: + ```nix + true + ``` + ''; + }; + "joinElseIf" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Join lines inserts else between consecutive ifs. + + default value is: + ```nix + true + ``` + ''; + }; + "removeTrailingComma" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Join lines removes trailing commas. + + default value is: + ```nix + true + ``` + ''; + }; + "unwrapTrivialBlock" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Join lines unwraps trivial blocks. + + default value is: + ```nix + true + ``` + ''; + }; + }; + "lens" = { + "debug" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to show `Debug` lens. Only applies when + `#rust-analyzer.lens.enable#` is set. + + default value is: + ```nix + true + ``` + ''; + }; + }; + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to show CodeLens in Rust files. + + default value is: + ```nix + true + ``` + ''; + }; + "forceCustomCommands" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Internal config: use custom client-side commands even when the + client doesn't set the corresponding capability. + + default value is: + ```nix + true + ``` + ''; + }; + "implementations" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to show `Implementations` lens. Only applies when + `#rust-analyzer.lens.enable#` is set. + + default value is: + ```nix + true + ``` + ''; + }; + }; + "references" = { + "adt" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to show `References` lens for Struct, Enum, and Union. + Only applies when `#rust-analyzer.lens.enable#` is set. + + default value is: + ```nix + false + ``` + ''; + }; + }; + "enumVariant" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to show `References` lens for Enum Variants. + Only applies when `#rust-analyzer.lens.enable#` is set. + + default value is: + ```nix + false + ``` + ''; + }; + }; + "method" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to show `Method References` lens. Only applies when + `#rust-analyzer.lens.enable#` is set. + + default value is: + ```nix + false + ``` + ''; + }; + }; + "trait" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to show `References` lens for Trait. + Only applies when `#rust-analyzer.lens.enable#` is set. + + default value is: + ```nix + false + ``` + ''; + }; + }; + }; + "run" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to show `Run` lens. Only applies when + `#rust-analyzer.lens.enable#` is set. + + default value is: + ```nix + true + ``` + ''; + }; + }; + }; + "linkedProjects" = mkOption { + type = types.nullOr (types.listOf (types.oneOf [ (types.str) (types.attrsOf types.anything) ])); + default = null; + description = '' + Disable project auto-discovery in favor of explicitly specified set + of projects. + + Elements must be paths pointing to `Cargo.toml`, + `rust-project.json`, or JSON objects in `rust-project.json` format. + + default value is: + ```nix + [] + ``` + ''; + }; + "lru" = { + "capacity" = mkOption { + type = types.nullOr (types.nullOr (types.addCheck types.int (x: x >= 0))); + default = null; + description = '' + Number of syntax trees rust-analyzer keeps in memory. Defaults to 128. + + default value is: + ```nix + null + ``` + ''; + }; + }; + "notifications" = { + "cargoTomlNotFound" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to show `can't find Cargo.toml` error message. + + default value is: + ```nix + true + ``` + ''; + }; + }; + "procMacro" = { + "attributes" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Expand attribute macros. Requires `#rust-analyzer.procMacro.enable#` to be set. + + default value is: + ```nix + true + ``` + ''; + }; + }; + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Enable support for procedural macros, implies `#rust-analyzer.cargo.buildScripts.enable#`. + + default value is: + ```nix + true + ``` + ''; + }; + "ignored" = mkOption { + type = types.nullOr (types.attrsOf types.anything); + default = null; + description = '' + These proc-macros will be ignored when trying to expand them. + + This config takes a map of crate names with the exported proc-macro names to ignore as values. + + default value is: + ```nix + {} + ``` + ''; + }; + "server" = mkOption { + type = types.nullOr (types.nullOr (types.str)); + default = null; + description = '' + Internal config, path to proc-macro server executable (typically, + this is rust-analyzer itself, but we override this in tests). + + default value is: + ```nix + null + ``` + ''; + }; + }; + "runnables" = { + "command" = mkOption { + type = types.nullOr (types.nullOr (types.str)); + default = null; + description = '' + Command to be executed instead of 'cargo' for runnables. + + default value is: + ```nix + null + ``` + ''; + }; + "extraArgs" = mkOption { + type = types.nullOr (types.listOf (types.str)); + default = null; + description = '' + Additional arguments to be passed to cargo for runnables such as + tests or binaries. For example, it may be `--release`. + + default value is: + ```nix + [] + ``` + ''; + }; + }; + "rustc" = { + "source" = mkOption { + type = types.nullOr (types.nullOr (types.str)); + default = null; + description = '' + Path to the Cargo.toml of the rust compiler workspace, for usage in rustc_private + projects, or "discover" to try to automatically find it if the `rustc-dev` component + is installed. + + Any project which uses rust-analyzer with the rustcPrivate + crates must set `[package.metadata.rust-analyzer] rustc_private=true` to use it. + + This option does not take effect until rust-analyzer is restarted. + + default value is: + ```nix + null + ``` + ''; + }; + }; + "rustfmt" = { + "extraArgs" = mkOption { + type = types.nullOr (types.listOf (types.str)); + default = null; + description = '' + Additional arguments to `rustfmt`. + + default value is: + ```nix + [] + ``` + ''; + }; + "overrideCommand" = mkOption { + type = types.nullOr (types.nullOr (types.listOf (types.str))); + default = null; + description = '' + Advanced option, fully override the command rust-analyzer uses for + formatting. + + default value is: + ```nix + null + ``` + ''; + }; + "rangeFormatting" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Enables the use of rustfmt's unstable range formatting command for the + `textDocument/rangeFormatting` request. The rustfmt option is unstable and only + available on a nightly build. + + default value is: + ```nix + false + ``` + ''; + }; + }; + }; + "semanticHighlighting" = { + "doc" = { + "comment" = { + "inject" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Inject additional highlighting into doc comments. + + When enabled, rust-analyzer will highlight rust source in doc comments as well as intra + doc links. + + default value is: + ```nix + true + ``` + ''; + }; + }; + }; + }; + "operator" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Use semantic tokens for operators. + + When disabled, rust-analyzer will emit semantic tokens only for operator tokens when + they are tagged with modifiers. + + default value is: + ```nix + true + ``` + ''; + }; + "specialization" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Use specialized semantic tokens for operators. + + When enabled, rust-analyzer will emit special token types for operator tokens instead + of the generic `operator` token type. + + default value is: + ```nix + false + ``` + ''; + }; + }; + }; + "punctuation" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Use semantic tokens for punctuations. + + When disabled, rust-analyzer will emit semantic tokens only for punctuation tokens when + they are tagged with modifiers or have a special role. + + default value is: + ```nix + false + ``` + ''; + }; + "separate" = { + "macro" = { + "bang" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + When enabled, rust-analyzer will emit a punctuation semantic token for the `!` of macro + calls. + + default value is: + ```nix + false + ``` + ''; + }; + }; + }; + "specialization" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Use specialized semantic tokens for punctuations. + + When enabled, rust-analyzer will emit special token types for punctuation tokens instead + of the generic `punctuation` token type. + + default value is: + ```nix + false + ``` + ''; + }; + }; + }; + "strings" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Use semantic tokens for strings. + + In some editors (e.g. vscode) semantic tokens override other highlighting grammars. + By disabling semantic tokens for strings, other grammars can be used to highlight + their contents. + + default value is: + ```nix + true + ``` + ''; + }; + }; + }; + "signatureInfo" = { + "detail" = mkOption { + type = types.nullOr (types.enum [ "full" "parameters" ]); + default = null; + description = '' + Show full signature of the callable. Only shows parameters if disabled. + + default value is: + ```nix + "full" + ``` + ''; + }; + "documentation" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Show documentation. + + default value is: + ```nix + true + ``` + ''; + }; + }; + }; + "typing" = { + "autoClosingAngleBrackets" = { + "enable" = mkOption { + type = types.nullOr (types.bool); + default = null; + description = '' + Whether to insert closing angle brackets when typing an opening angle bracket of a generic argument list. + + default value is: + ```nix + false + ``` + ''; + }; + }; + }; + "workspace" = { + "symbol" = { + "search" = { + "kind" = mkOption { + type = types.nullOr (types.enum [ "only_types" "all_symbols" ]); + default = null; + description = '' + Workspace symbol search kind. + + default value is: + ```nix + "only_types" + ``` + ''; + }; + "limit" = mkOption { + type = types.nullOr (types.addCheck types.int (x: x >= 0)); + default = null; + description = '' + Limits the number of items returned from a workspace symbol search (Defaults to 128). + Some clients like vs-code issue new searches on result filtering and don't require all results to be returned in the initial search. + Other clients requires all results upfront and might require a higher limit. + + default value is: + ```nix + 128 + ``` + ''; + }; + "scope" = mkOption { + type = types.nullOr (types.enum [ "workspace" "workspace_and_dependencies" ]); + default = null; + description = '' + Workspace symbol search scope. + + default value is: + ```nix + "workspace" + ``` + ''; + }; + }; + }; + }; +} diff --git a/plugins/nvim-lsp/update_ra.md b/plugins/nvim-lsp/update_ra.md new file mode 100644 index 00000000..684a32dd --- /dev/null +++ b/plugins/nvim-lsp/update_ra.md @@ -0,0 +1,13 @@ +# Updating rust-analyzer options + +Because there a large number of rust-analyzer options it's difficult to handle them by hand. + +The options can be fetched from the [rust-analyzer package.json](https://github.com/rust-lang/rust-analyzer/blob/master/editors/code/package.json). + +There is a derivation on the top-level flake that allows to build it easily, you just have to run: + +```bash +nix build .#rustAnalyzerOptions +``` + +You can then copy the `result/share/rust-analyzer-config.nix` to the correct location.