Merge branch 'main' into codewindow-open-by-default

This commit is contained in:
Yoni Firroloni 2026-01-27 20:00:03 +13:00
commit a7d81331d0
185 changed files with 8088 additions and 5270 deletions

View file

@ -8,7 +8,7 @@
## Preface ## Preface
[LICENSE]: ../LICENSE [LICENSE]: /LICENSE
I am glad you are thinking about contributing to nvf! The project is shaped by I am glad you are thinking about contributing to nvf! The project is shaped by
contributors and user feedback, and all contributions are appreciated. contributors and user feedback, and all contributions are appreciated.
@ -30,7 +30,7 @@ personally.
## Contributing Process ## Contributing Process
[pull request template]: ./PULL_REQUEST_TEMPLATE.md [pull request template]: /.github/PULL_REQUEST_TEMPLATE.md
The contribution process is mostly documented in the [pull request template]. The contribution process is mostly documented in the [pull request template].
When you create a pull request, you will find a checklist of items to complete When you create a pull request, you will find a checklist of items to complete

View file

@ -24,8 +24,8 @@ it above in your description.
--> -->
[editorconfig]: https://editorconfig.org [editorconfig]: https://editorconfig.org
[changelog]: https://github.com/NotAShelf/nvf/tree/main/docs/release-notes [changelog]: https://github.com/NotAShelf/nvf/tree/main/docs/manual/release-notes
[hacking nvf]: https://notashelf.github.io/nvf/index.xhtml#sec-guidelines [hacking nvf]: https://nvf.notashelf.dev/hacking.html#sec-guidelines
- [ ] I have updated the [changelog] as per my changes - [ ] I have updated the [changelog] as per my changes
- [ ] I have tested, and self-reviewed my code - [ ] I have tested, and self-reviewed my code

View file

@ -1,11 +1,7 @@
version: 2 version: 2
updates: updates:
- package-ecosystem: github-actions - package-ecosystem: github-actions
open-pull-requests-limit: 15
directory: "/" directory: "/"
schedule: schedule:
interval: daily interval: daily
open-pull-requests-limit: 15
reviewers:
- NotAShelf
assignees:
- NotAShelf

3
.github/typos.toml vendored
View file

@ -6,6 +6,9 @@ default.extend-ignore-words-re = [
"annote", "annote",
"viw", "viw",
"typ", "typ",
"edn",
"esy",
"BA", # somehow "BANanaD3V" is valid, but BA is not... "BA", # somehow "BANanaD3V" is valid, but BA is not...
"Emac"
] ]

View file

@ -17,13 +17,13 @@ jobs:
if: | if: |
github.event.pull_request.merged == true && startsWith(github.event.label.name, 'backport-') github.event.pull_request.merged == true && startsWith(github.event.label.name, 'backport-')
steps: steps:
- uses: actions/checkout@v5 - uses: actions/checkout@v6
with: with:
ref: ${{ github.event.pull_request.head.sha }} ref: ${{ github.event.pull_request.head.sha }}
token: ${{ steps.app-token.outputs.token }} token: ${{ steps.app-token.outputs.token }}
- name: Backport Action - name: Backport Action
uses: korthout/backport-action@v3 uses: korthout/backport-action@v4
with: with:
# Regex pattern for labels that should trigger a backport AND extracts the target branch # Regex pattern for labels that should trigger a backport AND extracts the target branch
# from the name (e.g. v0.x or v0.x.y; we use zerover). This action will ONLY proceed if # from the name (e.g. v0.x or v0.x.y; we use zerover). This action will ONLY proceed if

View file

@ -21,11 +21,16 @@ jobs:
- nix - nix
- maximal - maximal
steps: steps:
- uses: actions/checkout@v5 - uses: actions/checkout@v6
name: Checkout name: Checkout
- name: Install Nix - name: Install Nix
uses: DeterminateSystems/nix-installer-action@main uses: cachix/install-nix-action@v31.9.0
with:
nix_path: nixpkgs=channel:nixos-unstable
extra_nix_config: |
substituters = https://cache.nixos.org/ https://feel-co.cachix.org
trusted-public-keys = cache.nixos.org-1:6NCHdD59X431o0gWypbMrAURkbJ16ZPMQFGspcDShjY= feel-co.cachix.org-1:nwEFNnwZvtl4KKSH5LDg+/+K7bV0vcs6faMHAJ6xx0w=
- uses: cachix/cachix-action@v16 - uses: cachix/cachix-action@v16
with: with:

View file

@ -17,24 +17,32 @@ jobs:
if: "!contains(github.event.pull_request.title, '[skip ci]')" if: "!contains(github.event.pull_request.title, '[skip ci]')"
steps: steps:
- name: Checkout - name: Checkout
uses: actions/checkout@v5 uses: actions/checkout@v6
- uses: cachix/install-nix-action@v31.9.0
- name: Install Nix with:
uses: DeterminateSystems/nix-installer-action@main nix_path: nixpkgs=channel:nixos-unstable
extra_nix_config: |
substituters = https://cache.nixos.org/ https://feel-co.cachix.org
trusted-public-keys = cache.nixos.org-1:6NCHdD59X431o0gWypbMrAURkbJ16ZPMQFGspcDShjY= feel-co.cachix.org-1:nwEFNnwZvtl4KKSH5LDg+/+K7bV0vcs6faMHAJ6xx0w=
- name: Check Flake - name: Check Flake
run: nix flake check run: nix flake check
format-with-alejandra: format-sources:
name: "Check formatting" name: "Check formatting"
runs-on: ubuntu-latest runs-on: ubuntu-latest
if: "!contains(github.event.pull_request.title, '[skip ci]')" if: "!contains(github.event.pull_request.title, '[skip ci]')"
steps: steps:
- name: Checkout - name: Checkout
uses: actions/checkout@v5 uses: actions/checkout@v6
- name: Install Nix - name: Install Nix
uses: DeterminateSystems/nix-installer-action@main uses: cachix/install-nix-action@v31.9.0
with:
nix_path: nixpkgs=channel:nixos-unstable
extra_nix_config: |
substituters = https://cache.nixos.org/ https://feel-co.cachix.org
trusted-public-keys = cache.nixos.org-1:6NCHdD59X431o0gWypbMrAURkbJ16ZPMQFGspcDShjY= feel-co.cachix.org-1:nwEFNnwZvtl4KKSH5LDg+/+K7bV0vcs6faMHAJ6xx0w=
- name: Check formatting via Alejandra - name: Check formatting via Alejandra
run: nix run nixpkgs#alejandra -- --check . --exclude npins run: nix run nixpkgs#alejandra -- --check . --exclude npins
@ -56,7 +64,7 @@ jobs:
if: "!contains(github.event.pull_request.title, '[skip ci]')" if: "!contains(github.event.pull_request.title, '[skip ci]')"
steps: steps:
- name: Checkout - name: Checkout
uses: actions/checkout@v5 uses: actions/checkout@v6
- name: Check for typos - name: Check for typos
uses: crate-ci/typos@master uses: crate-ci/typos@master
@ -83,11 +91,14 @@ jobs:
- docs-manpages - docs-manpages
- docs-json - docs-json
steps: steps:
- name: Install Nix
uses: DeterminateSystems/nix-installer-action@main
- name: Checkout - name: Checkout
uses: actions/checkout@v5 uses: actions/checkout@v6
- uses: cachix/install-nix-action@v31.9.0
with:
nix_path: nixpkgs=channel:nixos-unstable
extra_nix_config: |
substituters = https://cache.nixos.org/ https://feel-co.cachix.org
trusted-public-keys = cache.nixos.org-1:6NCHdD59X431o0gWypbMrAURkbJ16ZPMQFGspcDShjY= feel-co.cachix.org-1:nwEFNnwZvtl4KKSH5LDg+/+K7bV0vcs6faMHAJ6xx0w=
- name: Set default git branch (to reduce log spam) - name: Set default git branch (to reduce log spam)
run: git config --global init.defaultBranch main run: git config --global init.defaultBranch main
@ -101,7 +112,7 @@ jobs:
run: echo "date=$(date +'%Y-%m-%d-%H%M%S')" >> ${GITHUB_OUTPUT} run: echo "date=$(date +'%Y-%m-%d-%H%M%S')" >> ${GITHUB_OUTPUT}
- name: Upload doc artifacts - name: Upload doc artifacts
uses: actions/upload-artifact@v5 uses: actions/upload-artifact@v6
with: with:
name: "${{ matrix.package }}" name: "${{ matrix.package }}"
path: result/share/doc/nvf path: result/share/doc/nvf
@ -109,13 +120,16 @@ jobs:
flake-docs-linkcheck: flake-docs-linkcheck:
name: "Validate hyperlinks in documentation sources" name: "Validate hyperlinks in documentation sources"
runs-on: ubuntu-latest runs-on: ubuntu-latest
if: "!contains(github.event.pull_request.title, '[skip ci]')" if: false # disabled until we fix ndg docs
steps: steps:
- name: Install Nix
uses: DeterminateSystems/nix-installer-action@main
- name: Checkout - name: Checkout
uses: actions/checkout@v5 uses: actions/checkout@v6
- uses: cachix/install-nix-action@v31.9.0
with:
nix_path: nixpkgs=channel:nixos-unstable
extra_nix_config: |
substituters = https://cache.nixos.org/ https://feel-co.cachix.org
trusted-public-keys = cache.nixos.org-1:6NCHdD59X431o0gWypbMrAURkbJ16ZPMQFGspcDShjY= feel-co.cachix.org-1:nwEFNnwZvtl4KKSH5LDg+/+K7bV0vcs6faMHAJ6xx0w=
- name: Build linkcheck package - name: Build linkcheck package
run: nix build .#docs-linkcheck -Lv run: nix build .#docs-linkcheck -Lv
@ -126,7 +140,7 @@ jobs:
if: "!contains(github.event.pull_request.title, '[skip ci]')" if: "!contains(github.event.pull_request.title, '[skip ci]')"
steps: steps:
- name: Checkout - name: Checkout
uses: actions/checkout@v5 uses: actions/checkout@v6
with: with:
fetch-depth: 2 # slows down checkout, but we need to compare against the previous commit on push events fetch-depth: 2 # slows down checkout, but we need to compare against the previous commit on push events
@ -148,7 +162,12 @@ jobs:
cat "$HOME/changed_files" cat "$HOME/changed_files"
- name: Install Nix - name: Install Nix
uses: DeterminateSystems/nix-installer-action@main uses: cachix/install-nix-action@v31.9.0
with:
nix_path: nixpkgs=channel:nixos-unstable
extra_nix_config: |
substituters = https://cache.nixos.org/ https://feel-co.cachix.org
trusted-public-keys = cache.nixos.org-1:6NCHdD59X431o0gWypbMrAURkbJ16ZPMQFGspcDShjY= feel-co.cachix.org-1:nwEFNnwZvtl4KKSH5LDg+/+K7bV0vcs6faMHAJ6xx0w=
- name: Checking Editorconfig conformance - name: Checking Editorconfig conformance
shell: bash shell: bash

View file

@ -14,7 +14,7 @@ jobs:
runs-on: ubuntu-latest runs-on: ubuntu-latest
steps: steps:
- name: "Checkout" - name: "Checkout"
uses: actions/checkout@v5 uses: actions/checkout@v6
- name: "Delete old branches" - name: "Delete old branches"
uses: beatlabs/delete-old-branches-action@v0.0.11 uses: beatlabs/delete-old-branches-action@v0.0.11

View file

@ -3,7 +3,7 @@ name: Build and Preview Manual
on: on:
workflow_dispatch: workflow_dispatch:
pull_request_target: pull_request_target:
types: [opened, synchronize, reopened, closed] types: [opened, synchronize, reopened, labeled, unlabeled, edited]
paths: paths:
- ".github/workflows/docs-preview.yml" - ".github/workflows/docs-preview.yml"
- "modules/**" - "modules/**"
@ -24,11 +24,13 @@ jobs:
build-preview: build-preview:
runs-on: ubuntu-latest runs-on: ubuntu-latest
steps: steps:
- name: Install Nix - uses: actions/checkout@v6
uses: DeterminateSystems/nix-installer-action@main - uses: cachix/install-nix-action@v31.9.0
with:
- name: Checkout nix_path: nixpkgs=channel:nixos-unstable
uses: actions/checkout@v5 extra_nix_config: |
substituters = https://cache.nixos.org/ https://feel-co.cachix.org
trusted-public-keys = cache.nixos.org-1:6NCHdD59X431o0gWypbMrAURkbJ16ZPMQFGspcDShjY= feel-co.cachix.org-1:nwEFNnwZvtl4KKSH5LDg+/+K7bV0vcs6faMHAJ6xx0w=
- name: Set default git branch (to reduce log spam) - name: Set default git branch (to reduce log spam)
run: git config --global init.defaultBranch main run: git config --global init.defaultBranch main
@ -49,7 +51,7 @@ jobs:
mkdir -p $PREVIEW_DIR mkdir -p $PREVIEW_DIR
# Copy the build files to the preview subdirectory # Copy the build files to the preview subdirectory
cp -rvf ../result/share/doc/nvf/* ./$PREVIEW_DIR cp -rvf ../result/share/doc/* ./$PREVIEW_DIR
# Configure git to use the GitHub Actions token for authentication # Configure git to use the GitHub Actions token for authentication
git config --global user.name "GitHub Actions" git config --global user.name "GitHub Actions"
@ -71,7 +73,7 @@ jobs:
id: prelude id: prelude
run: | run: |
PR_NUMBER=${{ github.event.pull_request.number }} PR_NUMBER=${{ github.event.pull_request.number }}
URL="https://${{ github.repository_owner }}.github.io/nvf/docs-preview-${PR_NUMBER}/" URL="https:///nvf.notashelf.dev/docs-preview-${PR_NUMBER}/"
# Propagate non-interpolatable environment vars # Propagate non-interpolatable environment vars
echo "URL=$URL" >> "$GITHUB_OUTPUT" echo "URL=$URL" >> "$GITHUB_OUTPUT"
@ -127,7 +129,7 @@ jobs:
runs-on: ubuntu-latest runs-on: ubuntu-latest
steps: steps:
- name: Checkout repository - name: Checkout repository
uses: actions/checkout@v5 uses: actions/checkout@v6
- name: Delete preview for closed/merged PR - name: Delete preview for closed/merged PR
run: | run: |
@ -164,7 +166,7 @@ jobs:
runs-on: ubuntu-latest runs-on: ubuntu-latest
steps: steps:
- name: Checkout repository - name: Checkout repository
uses: actions/checkout@v5 uses: actions/checkout@v6
- name: Double check preview directory deletion - name: Double check preview directory deletion
run: | run: |

View file

@ -28,7 +28,7 @@ jobs:
outputs: outputs:
should_run: ${{ steps.should_run.outputs.should_run }} should_run: ${{ steps.should_run.outputs.should_run }}
steps: steps:
- uses: actions/checkout@v5 - uses: actions/checkout@v6
- name: print latest_commit - name: print latest_commit
run: echo ${{ github.sha }} run: echo ${{ github.sha }}
@ -43,12 +43,20 @@ jobs:
if: ${{ needs.check_date.outputs.should_run != 'false' }} if: ${{ needs.check_date.outputs.should_run != 'false' }}
runs-on: ubuntu-latest runs-on: ubuntu-latest
steps: steps:
- uses: actions/checkout@v5 - uses: actions/checkout@v6
- uses: DeterminateSystems/nix-installer-action@main - uses: cachix/install-nix-action@v31.9.0
with:
nix_path: nixpkgs=channel:nixos-unstable
extra_nix_config: |
substituters = https://cache.nixos.org/ https://feel-co.cachix.org
trusted-public-keys = cache.nixos.org-1:6NCHdD59X431o0gWypbMrAURkbJ16ZPMQFGspcDShjY= feel-co.cachix.org-1:nwEFNnwZvtl4KKSH5LDg+/+K7bV0vcs6faMHAJ6xx0w=
- run: | - run: |
nix build .#docs -Lv nix build .#docs -Lv
cp -r result/share/doc/nvf public cp -r result/share/doc public
- uses: peaceiris/actions-gh-pages@v4 - uses: peaceiris/actions-gh-pages@v4
with: with:
github_token: ${{ secrets.GITHUB_TOKEN }} github_token: ${{ secrets.GITHUB_TOKEN }}
publish_dir: ./public publish_dir: ./public
cname: nvf.notashelf.dev

91
.github/workflows/update.yml vendored Normal file
View file

@ -0,0 +1,91 @@
name: Weekly Dependency Updates
on:
workflow_dispatch:
schedule:
# 8 PM UTC every Friday
- cron: '0 20 * * 5'
jobs:
update-dependencies:
runs-on: ubuntu-latest
steps:
- name: Checkout repository
uses: actions/checkout@v6
- name: "Install Nix"
uses: cachix/install-nix-action@v31.9.0
- name: Set up Git
run: |
git config user.name "GitHub Actions Bot"
git config user.email "actions@github.com"
- name: Create branch for updates
run: |
DATE=$(date +%Y-%m-%d)
BRANCH_NAME="update/dependencies-$DATE"
git checkout -b $BRANCH_NAME
echo "BRANCH_NAME=$BRANCH_NAME" >> $GITHUB_ENV
- name: Update npins
run: nix run nixpkgs#npins update
# Only update Nixpkgs. mnw might break on update, better to track it manually to avoid
# unexpected breakage.
- name: Update nixpkgs
run: nix flake update nixpkgs
- name: Check for changes
id: check_changes
run: |
if git diff --quiet; then
echo "No changes detected"
echo "changes_detected=false" >> "$GITHUB_OUTPUT"
exit 0
else
echo "Changes detected"
echo "changes_detected=true" >> "$GITHUB_OUTPUT"
fi
# FIXME: Worth adding additional checks for, e.g., fragile plugins
# or modules
# nix build .#checks.<system>.<check-name>
# We'll probably want to handle this with machine tests
- name: Verify changes
if: steps.check_changes.outputs.changes_detected == 'true'
run: |
# Run verification tests to ensure updates don't break anything
nix flake check
- name: Set date variable
run: echo "DATE=$(date +%Y-%m-%d)" >> "$GITHUB_ENV"
- name: Commit and push changes
if: steps.check_changes.outputs.changes_detected == 'true'
run: |
git add .
git commit -m "pins: bump all plugins (${{ env.DATE }})"
git push -u origin $BRANCH_NAME
- name: Create Pull Request
if: steps.check_changes.outputs.changes_detected == 'true'
uses: peter-evans/create-pull-request@v8
with:
branch: ${{ env.BRANCH_NAME }}
base: main
labels: dependencies,automated pr
token: ${{ secrets.GITHUB_TOKEN }}
commit-message: "npins: bump all plugins (${{ env.DATE }})"
title: "Weekly Dependency Updates: ${{ env.DATE }}"
body: |
> [!NOTE]
> This PR was automatically generated by the Weekly Dependency Updates workflow. Please wait
> for all CI steps to complete, and test any major changes personally.
Updates Performed:
- Updated dependencies using `npins update`
- Updated nixpkgs using `nix flake update nixpkgs`
If the verification steps have passed, updates should be safe to merge. For failing CI steps
submit a Pull Request targetting ${{ env.BRANCH_NAME }}

View file

@ -65,9 +65,9 @@
## Features ## Features
[standalone]: https://notashelf.github.io/nvf/index.xhtml#ch-standalone-installation [standalone]: https://nvf.notashelf.dev/#ch-standalone-installation
[NixOS module]: https://notashelf.github.io/nvf/index.xhtml#ch-standalone-nixos [NixOS module]: https://nvf.notashelf.dev/#ch-standalone-nixos
[Home-Manager module]: https://notashelf.github.io/nvf/index.xhtml#ch-standalone-hm [Home-Manager module]: https://nvf.notashelf.dev/#ch-standalone-hm
[release notes]: https://notashelf.github.io/nvf/release-notes.html [release notes]: https://notashelf.github.io/nvf/release-notes.html
[discussions tab]: https://github.com/notashelf/nvf/discussions [discussions tab]: https://github.com/notashelf/nvf/discussions
[FAQ section]: #frequently-asked-questions [FAQ section]: #frequently-asked-questions

View file

@ -31,6 +31,7 @@ isMaximal: {
lspSignature.enable = !isMaximal; # conflicts with blink in maximal lspSignature.enable = !isMaximal; # conflicts with blink in maximal
otter-nvim.enable = isMaximal; otter-nvim.enable = isMaximal;
nvim-docs-view.enable = isMaximal; nvim-docs-view.enable = isMaximal;
harper-ls.enable = isMaximal;
}; };
debugger = { debugger = {
@ -56,6 +57,7 @@ isMaximal: {
clang.enable = isMaximal; clang.enable = isMaximal;
css.enable = isMaximal; css.enable = isMaximal;
html.enable = isMaximal; html.enable = isMaximal;
json.enable = isMaximal;
sql.enable = isMaximal; sql.enable = isMaximal;
java.enable = isMaximal; java.enable = isMaximal;
kotlin.enable = isMaximal; kotlin.enable = isMaximal;
@ -67,8 +69,9 @@ isMaximal: {
typst.enable = isMaximal; typst.enable = isMaximal;
rust = { rust = {
enable = isMaximal; enable = isMaximal;
crates.enable = isMaximal; extensions.crates-nvim.enable = isMaximal;
}; };
toml.enable = isMaximal;
# Language modules that are not as common. # Language modules that are not as common.
assembly.enable = false; assembly.enable = false;
@ -84,8 +87,11 @@ isMaximal: {
ocaml.enable = false; ocaml.enable = false;
elixir.enable = false; elixir.enable = false;
haskell.enable = false; haskell.enable = false;
hcl.enable = false;
ruby.enable = false; ruby.enable = false;
fsharp.enable = false; fsharp.enable = false;
just.enable = false;
qml.enable = false;
tailwind.enable = false; tailwind.enable = false;
svelte.enable = false; svelte.enable = false;
@ -188,6 +194,7 @@ isMaximal: {
vim-wakatime.enable = false; vim-wakatime.enable = false;
diffview-nvim.enable = true; diffview-nvim.enable = true;
yanky-nvim.enable = false; yanky-nvim.enable = false;
qmk-nvim.enable = false; # requires hardware specific options
icon-picker.enable = isMaximal; icon-picker.enable = isMaximal;
surround.enable = isMaximal; surround.enable = isMaximal;
leetcode-nvim.enable = isMaximal; leetcode-nvim.enable = isMaximal;
@ -208,7 +215,6 @@ isMaximal: {
}; };
notes = { notes = {
obsidian.enable = false; # FIXME: neovim fails to build if obsidian is enabled
neorg.enable = false; neorg.enable = false;
orgmode.enable = false; orgmode.enable = false;
mind-nvim.enable = isMaximal; mind-nvim.enable = isMaximal;

View file

@ -92,7 +92,7 @@
# Generate the HTML manual pages # Generate the HTML manual pages
html = pkgs.callPackage ./manual.nix { html = pkgs.callPackage ./manual.nix {
inherit release; inherit inputs release;
inherit (nvimModuleDocs) optionsJSON; inherit (nvimModuleDocs) optionsJSON;
}; };
in { in {

View file

@ -1,114 +1,44 @@
{ {
lib, inputs,
stdenvNoCC,
fetchzip,
runCommandLocal,
# build inputs
nixos-render-docs,
documentation-highlighter,
dart-sass,
path, path,
# nrd configuration stdenvNoCC,
release, runCommandLocal,
optionsJSON, optionsJSON,
release,
} @ args: let } @ args: let
manual-release = args.release or "unstable"; manual-release = args.release or "unstable";
scss-reset = fetchzip {
url = "https://github.com/Frontend-Layers/scss-reset/archive/refs/tags/1.4.2.zip";
hash = "sha256-cif5Sx8Ca5vxdw/mNAgpulLH15TwmzyJFNM7JURpoaE=";
};
compileStylesheet = runCommandLocal "compile-nvf-stylesheet" {} ''
mkdir -p $out
tmpfile=$(mktemp -d)
trap "rm -r $tmpfile" EXIT
ln -s "${scss-reset}/build" "$tmpfile/scss-reset"
${dart-sass}/bin/sass --load-path "$tmpfile" \
${./static/style.scss} "$out/style.css"
echo "Generated styles"
'';
in in
stdenvNoCC.mkDerivation { runCommandLocal "nvf-docs-html" {
name = "nvf-manual"; nativeBuildInputs = [
src = builtins.path { (inputs.ndg.packages.${stdenvNoCC.system}.ndg.overrideAttrs
name = "nvf-manual-${manual-release}"; {
path = lib.sourceFilesBySuffices ./manual [".md" ".md.in"]; # FIXME: the tests take too long to build
}; doCheck = false;
})
];
} ''
mkdir -p $out/share/doc
strictDependencies = true; # Copy the markdown sources to be processed by ndg. This is not
nativeBuildInputs = [nixos-render-docs]; # strictly necessary, but allows us to modify the Markdown sources
# as we see fit.
cp -rvf ${./manual} ./manual
postPatch = '' # Replace variables following the @VARIABLE@ style in the manual
ln -s ${optionsJSON}/share/doc/nixos/options.json ./config-options.json # pages. This can be built into ndg at a later date.
''; substituteInPlace ./manual/index.md \
--subst-var-by NVF_VERSION ${manual-release}
buildPhase = '' # Generate the final manual from a set of parameters. This uses
dest="$out/share/doc/nvf" # feel-co/ndg to render the web manual.
mkdir -p "$(dirname "$dest")" ndg --config-file ${./ndg.toml} html \
mkdir -p $dest/{highlightjs,script} --jobs $NIX_BUILD_CORES --title "NVF" \
--module-options ${optionsJSON}/share/doc/nixos/options.json \
--manpage-urls ${path}/doc/manpage-urls.json \
--input-dir ./manual \
--output-dir "$out/share/doc"
# Copy highlight scripts to /highlights in document root. # Hydra support. Probably not necessary.
cp -vt $dest/highlightjs \ mkdir -p $out/nix-support/
${documentation-highlighter}/highlight.pack.js \ echo "doc manual $dest index.html" >> $out/nix-support/hydra-build-products
${documentation-highlighter}/LICENSE \ ''
${documentation-highlighter}/mono-blue.css \
${documentation-highlighter}/loader.js
# Copy anchor scripts to the script directory in document root.
cp -vt "$dest"/script \
${./static/script}/anchor-min.js \
${./static/script}/anchor-use.js \
${./static/script}/search.js
substituteInPlace ./options.md \
--subst-var-by OPTIONS_JSON ./config-options.json
substituteInPlace ./manual.md \
--subst-var-by NVF_VERSION ${manual-release}
substituteInPlace ./hacking/additional-plugins.md \
--subst-var-by NVF_REPO "https://github.com/notashelf/nvf/blob/${manual-release}"
# Move compiled stylesheet
cp -vt $dest \
${compileStylesheet}/style.css
# Move release notes
cp -vr ${./release-notes} release-notes
# Generate final manual from a set of parameters. Explanation of the CLI flags are
# as follows:
#
# 1. --manpage-urls will allow you to use manual pages as they are defined in
# the nixpkgs documentation.
# 2. --revision is the project revision as it is defined in 'release.json' in the
# repository root
# 3. --script will inject a given Javascript file into the resulting pages inside
# the <script> tag.
# 4. --toc-depth will determine the depth of the initial Table of Contents while
# --section-toc-depth will determine the depth of per-section Table of Contents
# sections.
nixos-render-docs manual html \
--manpage-urls ${path + "/doc/manpage-urls.json"} \
--revision ${lib.trivial.revisionWithDefault manual-release} \
--stylesheet style.css \
--script highlightjs/highlight.pack.js \
--script highlightjs/loader.js \
--script script/anchor-use.js \
--script script/anchor-min.js \
--script script/search.js \
--toc-depth 1 \
--section-toc-depth 1 \
manual.md \
"$dest/index.xhtml"
# Hydra support. Probably not necessary.
mkdir -p $out/nix-support/
echo "doc manual $dest index.html" >> $out/nix-support/hydra-build-products
'';
}

View file

@ -1,14 +1,16 @@
# Configuring nvf {#ch-configuring} # Configuring nvf {#ch-configuring}
[helpful tips section]: #ch-helpful-tips [helpful tips section]: ./tips.html#ch-helpful-tips
[options reference]: ./options.html
nvf allows for _very_ extensive configuration in Neovim through the Nix module **nvf** allows for _very_ extensive configuration in Neovim through the Nix
interface. The below chapters describe several of the options exposed in nvf for module interface. The below chapters describe several of the options exposed in
your convenience. You might also be interested in the [helpful tips section] for nvf for your convenience. You might also be interested in the
more advanced or unusual configuration options supported by nvf. [helpful tips section] for more advanced or unusual configuration options
supported by nvf.
Note that this section does not cover module _options_. For an overview of all Note that this section does not cover module _options_. For an overview of all
module options provided by nvf, please visit the [appendix](/nvf/options.html) module options provided by nvf, please visit the [options reference]
```{=include=} chapters ```{=include=} chapters
configuring/custom-package.md configuring/custom-package.md

View file

@ -1,22 +0,0 @@
# Custom Neovim Package {#ch-custom-package}
As of v0.5, you may now specify the Neovim package that will be wrapped with
your configuration. This is done with the [](#opt-vim.package) option.
```nix
{inputs, pkgs, ...}: {
# using the neovim-nightly overlay
vim.package = inputs.neovim-overlay.packages.${pkgs.stdenv.system}.neovim;
}
```
The neovim-nightly-overlay always exposes an unwrapped package. If using a
different source, you are highly recommended to get an "unwrapped" version of
the neovim package, similar to `neovim-unwrapped` in nixpkgs.
```nix
{ pkgs, ...}: {
# using the neovim-nightly overlay
vim.package = pkgs.neovim-unwrapped;
}
```

View file

@ -19,7 +19,7 @@ as a module.
:::{.info} :::{.info}
To add a plugin to your runtime, you will need to add it to To add a plugin to your runtime, you will need to add it to
[](#opt-vim.startPlugins) list in your configuration. This is akin to cloning a {option}`vim.startPlugins` list in your configuration. This is akin to cloning a
plugin to `~/.config/nvim`, but they are only ever placed in the Nix store and plugin to `~/.config/nvim`, but they are only ever placed in the Nix store and
never exposed to the outside world for purity and full isolation. never exposed to the outside world for purity and full isolation.

View file

@ -19,7 +19,7 @@ hooks should do what you need.
```nix ```nix
{ {
config.vim.lazy.plugins = { config.vim.lazy.plugins = {
aerial.nvim = { "aerial.nvim" = {
# ^^^^^^^^^ this name should match the package.pname or package.name # ^^^^^^^^^ this name should match the package.pname or package.name
package = aerial-nvim; package = aerial-nvim;

View file

@ -1,17 +1,17 @@
# Legacy Method {#sec-legacy-method} # Legacy Method {#sec-legacy-method}
Prior to version **0.5**, the method of adding new plugins was adding the plugin Prior to version **0.5**, the method of adding new plugins was adding the plugin
package to [](#opt-vim.startPlugins) and adding its configuration as a DAG under package to {option}`vim.startPlugins` and adding its configuration as a DAG
one of `vim.configRC` or [](#opt-vim.luaConfigRC). While `configRC` has been under one of `vim.configRC` or {option}`vim.luaConfigRC`. While `configRC` has
deprecated, users who have not yet updated to 0.5 or those who prefer a more been deprecated, users who have not yet updated to 0.5 or those who prefer a
hands-on approach may choose to use the old method where the load order of the more hands-on approach may choose to use the old method where the load order of
plugins is explicitly determined by DAGs without internal abstractions. the plugins is explicitly determined by DAGs without internal abstractions.
## Adding New Plugins {#sec-adding-new-plugins} ## Adding New Plugins {#sec-adding-new-plugins}
To add a plugin not available in **nvf** as a module to your configuration using To add a plugin not available in **nvf** as a module to your configuration using
the legacy method, you must add it to [](#opt-vim.startPlugins) in order to make the legacy method, you must add it to {option}`vim.startPlugins` in order to
it available to Neovim at runtime. make it available to Neovim at runtime.
```nix ```nix
{pkgs, ...}: { {pkgs, ...}: {

View file

@ -2,7 +2,7 @@
As of version **0.5**, we have a more extensive API for configuring plugins that As of version **0.5**, we have a more extensive API for configuring plugins that
should be preferred over the legacy method. This API is available as should be preferred over the legacy method. This API is available as
[](#opt-vim.extraPlugins). Instead of using DAGs exposed by the library {option}`vim.extraPlugins`. Instead of using DAGs exposed by the library
_directly_, you may use the extra plugin module as follows: _directly_, you may use the extra plugin module as follows:
```nix ```nix

View file

@ -1,25 +1,92 @@
# Language Support {#ch-languages} # Language Support {#ch-languages}
Language specific support means there is a combination of language specific Language specific support means there is a combination of language specific
plugins, `treesitter` support, `nvim-lspconfig` language servers, and `null-ls` plugins, `treesitter` support, `nvim-lspconfig` language servers, `conform-nvim`
integration. This gets you capabilities ranging from autocompletion to formatters, and `nvim-lint` linter integration. This gets you capabilities
formatting to diagnostics. The following languages have sections under the ranging from autocompletion to formatting to diagnostics. The following
`vim.languages` attribute. languages have sections under the `vim.languages` attribute.
- Rust: [vim.languages.rust.enable](#opt-vim.languages.rust.enable) - Rust:
- Nix: [vim.languages.nix.enable](#opt-vim.languages.nix.enable) [vim.languages.rust.enable](./options.html#option-vim-languages-rust-enable)
- SQL: [vim.languages.sql.enable](#opt-vim.languages.sql.enable) - Nix:
- C/C++: [vim.languages.clang.enable](#opt-vim.languages.clang.enable) [vim.languages.nix.enable](./options.html#option-vim-languages-nix-enable)
- Typescript/Javascript: [vim.languages.ts.enable](#opt-vim.languages.ts.enable) - SQL:
- Python: [vim.languages.python.enable](#opt-vim.languages.python.enable): [vim.languages.sql.enable](./options.html#option-vim-languages-sql-enable)
- Zig: [vim.languages.zig.enable](#opt-vim.languages.zig.enable) - C/C++:
- Markdown: [vim.languages.markdown.enable](#opt-vim.languages.markdown.enable) [vim.languages.clang.enable](./options.html#option-vim-languages-clang-enable)
- HTML: [vim.languages.html.enable](#opt-vim.languages.html.enable) - Typescript/Javascript:
- Dart: [vim.languages.dart.enable](#opt-vim.languages.dart.enable) [vim.languages.ts.enable](./options.html#option-vim-languages-ts-enable)
- Go: [vim.languages.go.enable](#opt-vim.languages.go.enable) - Python:
- Lua: [vim.languages.lua.enable](#opt-vim.languages.lua.enable) [vim.languages.python.enable](./options.html#option-vim-languages-python-enable):
- PHP: [vim.languages.php.enable](#opt-vim.languages.php.enable) - Zig:
- F#: [vim.languages.fsharp.enable](#opt-vim.languages.fsharp.enable) [vim.languages.zig.enable](./options.html#option-vim-languages-zig-enable)
- Markdown:
[vim.languages.markdown.enable](./options.html#option-vim-languages-markdown-enable)
- HTML:
[vim.languages.html.enable](./options.html#option-vim-languages-html-enable)
- Dart:
[vim.languages.dart.enable](./options.html#option-vim-languages-dart-enable)
- Go: [vim.languages.go.enable](./options.html#option-vim-languages-go-enable)
- Lua:
[vim.languages.lua.enable](./options.html#option-vim-languages-lua-enable)
- PHP:
[vim.languages.php.enable](./options.html#option-vim-languages-php-enable)
- F#:
[vim.languages.fsharp.enable](./options.html#option-vim-languages-fsharp-enable)
- Assembly:
[vim.languages.assembly.enable](./options.html#option-vim-languages-assembly-enable)
- Astro:
[vim.languages.astro.enable](./options.html#option-vim-languages-astro-enable)
- Bash:
[vim.languages.bash.enable](./options.html#option-vim-languages-bash-enable)
- Clang:
[vim.languages.clang.enable](./options.html#option-vim-languages-clang-enable)
- Clojure:
[vim.languages.clojure.enable](./options.html#option-vim-languages-clojure-enable)
- C#:
[vim.languages.csharp.enable](./options.html#option-vim-languages-csharp-enable)
- CSS:
[vim.languages.css.enable](./options.html#option-vim-languages-css-enable)
- CUE:
[vim.languages.cue.enable](./options.html#option-vim-languages-cue-enable)
- Elixir:
[vim.languages.elixir.enable](./options.html#option-vim-languages-elixir-enable)
- Gleam:
[vim.languages.gleam.enable](./options.html#option-vim-languages-gleam-enable)
- HCL:
[vim.languages.hcl.enable](./options.html#option-vim-languages-hcl-enable)
- Helm:
[vim.languages.helm.enable](./options.html#option-vim-languages-helm-enable)
- Julia:
[vim.languages.julia.enable](./options.html#option-vim-languages-julia-enable)
- Kotlin:
[vim.languages.kotlin.enable](./options.html#option-vim-languages-kotlin-enable)
- Nim:
[vim.languages.nim.enable](./options.html#option-vim-languages-nim-enable)
- Nu: [vim.languages.nu.enable](./options.html#option-vim-languages-nu-enable)
- OCaml:
[vim.languages.ocaml.enable](./options.html#option-vim-languages-ocaml-enable)
- Odin:
[vim.languages.odin.enable](./options.html#option-vim-languages-odin-enable)
- R: [vim.languages.r.enable](./options.html#option-vim-languages-r-enable)
- Ruby:
[vim.languages.ruby.enable](./options.html#option-vim-languages-ruby-enable)
- Scala:
[vim.languages.scala.enable](./options.html#option-vim-languages-scala-enable)
- Svelte:
[vim.languages.svelte.enable](./options.html#option-vim-languages-svelte-enable)
- Tailwind:
[vim.languages.tailwind.enable](./options.html#option-vim-languages-tailwind-enable)
- Terraform:
[vim.languages.terraform.enable](./options.html#option-vim-languages-terraform-enable)
- Typst:
[vim.languages.typst.enable](./options.html#option-vim-languages-typst-enable)
- Vala:
[vim.languages.vala.enable](./options.html#option-vim-languages-vala-enable)
- WGSL:
[vim.languages.wgsl.enable](./options.html#option-vim-languages-wgsl-enable)
- YAML:
[vim.languages.yaml.enable](./options.html#option-vim-languages-yaml-enable)
Adding support for more languages, and improving support for existing ones are Adding support for more languages, and improving support for existing ones are
great places where you can contribute with a PR. great places where you can contribute with a PR.

View file

@ -1,10 +1,10 @@
# Overriding plugins {#ch-overriding-plugins} # Overriding plugins {#ch-overriding-plugins}
The [additional plugins section](#sec-additional-plugins) details the addition The [additional plugins section](./hacking.html#sec-additional-plugins) details
of new plugins to nvf under regular circumstances, i.e. while making a pull the addition of new plugins to nvf under regular circumstances, i.e. while
request to the project. You may _override_ those plugins in your config to making a pull request to the project. You may _override_ those plugins in your
change source versions, e.g., to use newer versions of plugins that are not yet config to change source versions, e.g., to use newer versions of plugins that
updated in **nvf**. are not yet updated in **nvf**.
```nix ```nix
vim.pluginOverrides = { vim.pluginOverrides = {
@ -22,7 +22,7 @@ vim.pluginOverrides = {
}; };
``` ```
This will override the source for the `neodev.nvim` plugin that is used in nvf This will override the source for the `lazydev.nvim` plugin that is used in nvf
with your own plugin. with your own plugin.
::: {.warning} ::: {.warning}

View file

@ -3,12 +3,13 @@
[open issues]: https://github.com/notashelf/nvf/issues [open issues]: https://github.com/notashelf/nvf/issues
[new issue]: https://github.com/notashelf/nvf/issues/new [new issue]: https://github.com/notashelf/nvf/issues/new
nvf is designed for the developer as much as it is designed for the end-user. We **nvf** is designed for the developer as much as it is designed for the
would like for any contributor to be able to propagate their changes, or add new end-user. We would like for any contributor to be able to propagate their
features to the project with minimum possible friction. As such, below are the changes, or add new features to the project with minimum possible friction. As
guides and guidelines written to streamline the contribution process and to such, below are the guides and guidelines written to streamline the contribution
ensure that your valuable input integrates into nvf's development as seamlessly process and to ensure that your valuable input integrates into **nvf**'s
as possible without leaving any question marks in your head. development as seamlessly as possible without leaving any question marks in your
head.
This section is directed mainly towards those who wish to contribute code into This section is directed mainly towards those who wish to contribute code into
the project. If you instead wish to report a bug, or discuss a potential new the project. If you instead wish to report a bug, or discuss a potential new
@ -21,10 +22,803 @@ ideally also include relevant context in which an issue occurs or a feature
should be implemented. If you wish to make a contribution, but feel stuck - should be implemented. If you wish to make a contribution, but feel stuck -
please do not be afraid to submit a pull request, we will help you get it in. please do not be afraid to submit a pull request, we will help you get it in.
```{=include=} sections ## Getting Started {#sec-contrib-getting-started}
hacking/getting-started.md
hacking/guidelines.md [Fork a repo guide]: https://help.github.com/articles/fork-a-repo/
hacking/testing.md [Contributing Guidelines]: #sec-guidelines
hacking/keybinds.md [Create a Pull Request]: https://help.github.com/articles/creating-a-pull-request
hacking/additional-plugins.md
To contribute to **nvf**, you'll first want to fork the repository. If you are
new to Git and GitHub, do have a look at GitHub's [Fork a repo guide] for
instructions on how you can do this. Once your fork is created, you should
create a separate branch based on the most recent `main` branch. While you _can_
work on the main branch of your repository, it is generally preferable to use
feature branches. You should give your branch a reasonably descriptive name
(e.g. `feature/new-debugger` or `fix/pesky-bug`) and you are ready to work on
your changes!
Implement your changes and commit them to the newly created branch and when you
are happy with the result, and positive that it fulfills our
[Contributing Guidelines], push the branch to GitHub and [Create a Pull Request]
The default pull request template available on the **nvf** repository will guide
you through the rest of the process, and we'll gently nudge you in the correct
direction if there are any mistakes.
Before submitting your pull request, please ensure that:
- The code is formatted as described in the formatting section
- The commit message fits the contributing guidelines (**nvf** does not use
Conventional Commits!)
- You have updated the changelog entry and optionally updated the documentation
with important information
None of those are reasons for a Pull Request to be closed, but it will reduce
the number of "roundtrips", or rather, the back-and-forth required before we can
merge your Pull Request.
> [!IMPORTANT]
> If you do not agree with the idea of using Microsoft GitHub for contributions,
> that is perfectly understandable. Unless you refuse to have your code hosted
> on this platform, you may submit _patches_ through e-mail.
>
> You may send your patches to [@NotAShelf](https://github.com/notashelf) using
> the public e-mail located on the GitHub page. Though, please remember to
> adhere to the contributing guidelines strictly, as e-mail introduces a
> significant overhead to the communication process.
## Guidelines {#sec-guidelines}
[discussions tab]: https://github.com/NotAShelf/nvf/discussions
If your contribution tightly follows the guidelines, then there is a good chance
it will be merged without too much trouble. Some of the guidelines will be
strictly enforced, others will remain as gentle nudges towards the correct
direction. As we have no automated system enforcing those guidelines, please try
to double check your changes before making your pull request in order to avoid
"faulty" code slipping by.
If you are not quite certain how those rules affect the change you are planning
to make, then please start a friendly discussion in the [discussions tab] before
you begin developing. This is not a requirement, but it might answer some of
your burning questions and make the contribution process easier for all parties.
### Formatting {#sec-guidelines-formatting}
[code style section]: #sec-guidelines-code-style
There are various files within the **nvf** repository. To maintain a sense of
consistency and to avoid clashing opinions on how formatters should behave, we
are very opinionated on how those files should be formatted.
- Nix files **must** be formatted with the Alejandra formatter, following some
specific tips found in [Nix style section](#nix-sec-code-style-nix).
- Markdown files **must** be formatted with the `deno fmt` command, as described
in the [Markdown style section](#sec-code-style-markdown).
Make sure your code is formatted as described in [code style section] before
your changes are submitted.
### Formatting Commits {#sec-guidelines-commit-message-style}
Similar to [code style guidelines](#sec-guidelines-code-style) we encourage a
consistent commit message format as described in
[commit style guidelines](#sec-guidelines-commit-style).
### Commit Style {#sec-guidelines-commit-style}
The commits in your pull request should be reasonably self-contained. Which
means each and every commit in a pull request should make sense both on its own
and in general context. That is, a second commit should not resolve an issue
that is introduced in an earlier commit. In particular, you will be asked to
amend any commit that introduces syntax errors or similar problems even if they
are fixed in a later commit.
The commit messages should follow the
[seven rules](https://chris.beams.io/posts/git-commit/#seven-rule), except for
"Capitalize the subject line". We also ask you to include the affected code
component or module in the first line. A commit message ideally, but not
necessarily, follow the given template from home-manager's own documentation
```gitcommit
{component}: {description}
{long description}
``` ```
where `{component}` refers to the code component (or module) your change
affects, `{description}` is a very brief description of your change, and
`{long description}` is an optional clarifying description.
[example commit message]: #sec-guidelines-ex-commit-message
As a rare exception, if there is no clear component, or your change affects many
components, then the `{component}` part is optional. See
[example commit message] for a commit message that fulfills these requirements.
#### Example Commit {#sec-guidelines-ex-commit-message}
[sample commit from Home Manager]: https://github.com/nix-community/home-manager/commit/69f8e47e9e74c8d3d060ca22e18246b7f7d988ef
The [sample commit from Home Manager] contains the following commit message.
```gitcommit
starship: allow running in Emacs if vterm is used
The vterm buffer is backed by libvterm and can handle Starship prompts
without issues.
```
Similarly, if you are contributing to **nvf**, you would include the scope of
the commit followed by the description:
```gitcommit
languages/ruby: init module
Adds a language module for Ruby, adds appropriate formatters and Treesitter
grammars
```
Long description can be omitted if the change is too simple to warrant it. A
minor fix in spelling or a formatting change does not warrant long description,
however, a module addition or removal does as you would like to provide the
relevant context, i.e., the reasoning for your commit.
For new plugin additions, the following is a good starting point:
```gitcommit
plugin: init
```
You can, of course, still include a long description if you wish.
```gitcommit
neotree: init
This adds the neo-tree plugin.
```
In case of nested modules, e.g., `modules/languages/java.nix` you are
recommended to contain the parent as well -- for example
`languages/java: some major change` , or if it's a new language module,
`languages/java: init`
### Code Style {#sec-guidelines-code-style}
#### Treewide {#sec-code-style-treewide}
Across the tree, you're encouraged to follow kebab-case for file names, and keep
text files (such as Markdown) to 80 characters or less. This 80 character
recommendation also applies to option descriptions and string literals inside of
Nix files.
#### Markdown {#sec-code-style-markdown}
Various Markdown files are used for documentation in the **nvf** repository.
Besides the README, the manual is written almost entirely in Markdown. Since
**nvf** uses a special variant of CommonMark, dubbed "Nixpkgs-flavored
CommonMark" within this repository, you are encouraged to use the `deno fmt`
command (provided by `pkgs.deno`) to format your Markdown sources. To avoid
accidentally formatting HTML or CSS files, you might want to specify the file
extension as follows:
```bash
# Format all Markdown files within the repository
$ deno fmt --ext md **/*.md
```
You may also pass `--check` to the `deno fmt` command above to see if your
formatting complies with the project standards.
#### Nix {#sec-code-style-nix}
[alejandra]: https://github.com/kamadorueda/alejandra
**nvf** is formatted by the [alejandra] tool and the formatting is checked in
the pull request and push workflows. Run the `nix fmt` command inside the
project repository before submitting your pull request.
While Alejandra is mostly opinionated on how code looks after formatting,
certain changes are done at the user's discretion based on how the original code
was structured.
##### Attribute Sets
Please use one line code for attribute sets that contain only one subset. For
example:
<!-- markdownlint-disable MD013 -->
```nix
# Parent modules should always be unfolded.
# which means `module = { value = ... }` instead of `module.value = { ... }`.
module = {
value = mkEnableOption "some description" // { default = true; }; # merges can be done inline where possible
# same as parent modules, unfold submodules
subModule = {
# this is an option that contains more than one nested value
# Note: try to be careful about the ordering of `mkOption` arguments.
# General rule of thumb is to order from least to most likely to change.
# This is, for most cases, type < default < description.
# Example, if present, would be between default and description
someOtherValue = mkOption {
type = lib.types.bool;
default = true;
description = "Some other description";
};
};
}
```
<!-- markdownlint-enable MD013 -->
If you move a line down after the merge operator, Alejandra will automatically
unfold the whole merged attribute set for you, which we **do not** want.
```nix
module = {
# This is wrong!
key = mkEnableOption "some description" // {
default = true; # we want this to be inline
};
# ...
}
```
Though, if the right-hand side is more than a single line, it is okay to move to
a new line. For example:
```nix
module = {
# This is okay!
key = mkEnableOption "some description" // {
default = true;
example = false;
};
# ...
}
```
##### Lists
For lists, it is mostly up to your own discretion how you want to format them,
but please try to unfold lists if they contain multiple items and especially if
they are to include comments.
```nix
# This is ok
acceptableList = [
item1 # comment
item2
item3 # some other comment
item4
];
# This is *not* ok
listToBeAvoided = [item1 item2 /* comment */ item3 item4];
# This is ok
acceptableList = [item1 item2];
# This is also ok if the list is expected to contain more elements
acceptableList = [
item1
item2
# more items if needed...
];
```
## Testing Changes {#sec-testing-changes}
Once you have made your changes, you will need to test them thoroughly. To make
testing easier you may either use the `configuration.nix` located in the
repository root, or use the development package located in `flake/develop.nix`.
The development package allows you to quickly bootstrap a Neovim configuration
with only the required modules, instead of the packages that consume the
`configuration.nix`, so it is generally preferable. To use it navigate to the
`develop.nix` module, and update the `configuration` set with the Neovim
configuration that you would like to test with. For example:
```nix
{
# Let's assume you are adding a new module for the Nix language.
# You will need to enable it here
configuration = {
vim.languages.nix.enable = true;
# You can also enable other plugins that you wish to test with, for example
# none-ls:
vim.lsp.null-ls = {
enable = true;
setupOpts = { /* Your setup options here */ };
};
};
```
You may then run this package with `nix run .#develop` and check for build or
runtime errors. If Neovim builds and opens without any errors, then your changes
are good to go. Open your pull request, and it will be reviewed as soon as
possible.
If your changes are rather large, or if you would like to instead test with a
more complex configuration then you might use the `configuration.nix` for
testing. Make your changes, and then build either the default or `maximal`
package to test your changes.
> [!IMPORTANT]
> `configuration.nix` is a module used to bootstrap **demo** packages and should
> generally not be changed unless migrating old APIs or updating the set of
> default plugins. Similarly, the `develop.nix` file is for reference, and
> testing configurations **should not be committed**.
## Adding Documentation {#sec-guidelines-documentation}
[Nixpkgs Flavoured Markdown]: https://github.com/NixOS/nixpkgs/blob/master/doc/README.md#syntax
[in-house documentation generator]: https://github.com/feel-co/ndg
[library documentation]: https://github.com/feel-co/ndg/blob/main/ndg-commonmark/docs/SYNTAX.md
Almost all changes to **nvf**'s codebase warrant updates to the documentation.
At the very least, you must update the relevant changelog document to describe
your changes. The documentation files found within the repository use a superset
of [Nixpkgs Flavoured Markdown] thanks to our
[in-house documentation generator].
As a general rule of thumb:
- Everything in the CommonMark spec is supported
- Everything in Nixpkgs Flavoured Markdown is supported
- Github Flavored Markdown is supported for Tables and Admonitions
By feeding NDG, our documentation generator, Markdown sources we can generate a
HTML manual with various goodies, including a **search page** and an **options
page**. The latter, found under `options.html` contains module options, similar
to the official Nixpkgs search utility. The supported syntax for NDG can be
found over at the [library documentation].
### Building the Documentation
The HTML version of this documentation, dubbed the "nvf manual", can be
generated and opened by typing the following in a shell within a clone of the
**nvf** Git repository:
```sh
# Build the online manual
$ nix build .#docs-html
# Open it with a valid browser
$ xdg-open $PWD/result/share/doc/index.html
```
Additionally, if you are adding new links to the documentation it is **generally
recommended** that you run the package that identifies dead URLs in the
documentation:
```sh
# Build the link checker package
$ nix build .#docs-linkcheck
```
You must ensure that the **HTML Documentation** builds before submitting a pull
request. If the documentation builds, an automatic "preview" build will be
deployed automatically for your Pull Request. You may use this preview to view
your changes as your Pull Request is updated.
### Formatting Changelog Entries
For additions, removals or any general change that concerns the users you must
add a changelog entry. The changelog entries are later included in the rendered
manual for users hoping to learn what has changed.
To maintain consistency, you must follow the following format in the changelog:
```markdown
[username](https://github.com/username):
- Added ...
- Removed ...
- Changed ...
```
If this is your first contribution, you should add yourself to the changelog.
Linking your GitHub account is not a strict requirement; it can be any page that
people can use to discover you. Below the link to your profile, you should
include a brief description of your changes. Those descriptions must be in past
tense, unlike commit messages.
While adding a new section, please insert the section at an arbitrary location
under the `## Changelog` section rather than the end of the document. This helps
avoid merge conflicts.
### Breaking Changes
If you are introducing _breaking_ changes to the repository, then you must also
briefly mention what has changed in the breaking changes section of the
changelog document that you are editing. If this section does not yet exist, you
must create it.
```markdown
# Release 0.9 {#sec-release-0-9}
## Breaking changes
- We broke everything, please migrate!
```
This section is _critical_, as it is used to communicate to the users what has
changed in the codebase and what breakage they may expect upon an update. To be
comprehensive, you should include migration steps or how users may mitigate
breakage depending on the context of the change.
## Adding Plugins {#sec-additional-plugins}
**nvf** generally tries to avoid using Neovim plugins from Nixpkgs, and thus
uses one of the two alternative methods where applicable. npins is the faster
option that should be preferred if the plugin consists of pure Lua or Vimscript
code. In which case there is no building required, and we can easily handle the
copying of plugin files. Alternative method, which is required when plugins try
to build their own libraries (e.g., in Rust, C or even Assembly) that need to be
built with Nix to function correctly. In this case you must use a local overlay.
### With npins {#sec-npins-for-plugins}
npins is the standard, and as described above, the _faster_ method of adding new
plugins to **nvf**. You simply need the repository URL for the plugin, and you
can add it as a source to be built automatically with just one command. To add a
new Neovim plugin, use `npins`. For example:
```bash
nix-shell -p npins # or nix shell nixpkgs#npins if using flakes
```
Then run:
```bash
npins add --name <plugin name> github <owner> <repo> -b <branch>
```
> [!NOTE]
> Be sure to replace any non-alphanumeric characters with `-` for `--name`. For
> example
>
> ```bash
> npins add --name lazydev-nvim github folke lazydev.nvim -b main
> ```
Once the `npins` command is done, you can start referencing the plugin as a
**string**.
```nix
{
config.vim.startPlugins = ["lazydev-nvim"];
}
```
### Packaging Complex Plugins {#sec-pkgs-for-plugins}
[blink.cmp]: https://github.com/Saghen/blink.cmp
Some plugins require additional packages to be built and substituted to function
correctly. For example [blink.cmp] requires its own fuzzy matcher library, built
with Rust, to be installed or else defaults to a much slower Lua implementation.
In the Blink documentation, you are advised to build with `cargo` but that is
not ideal since we are leveraging the power of Nix. In this case the ideal
solution is to write a derivation for the plugin.
We use `buildRustPackage` to build the library from the repository root, and
copy everything in the `postInstall` phase.
```nix
{
# ...
postInstall = ''
cp -r {lua,plugin} "$out"
mkdir -p "$out/doc"
cp 'doc/'*'.txt' "$out/doc/"
mkdir -p "$out/target"
mv "$out/lib" "$out/target/release"
'';
# ...
}
```
In a similar fashion, you may utilize `stdenv.mkDerivation` and other Nixpkgs
builders to build your library from source, and copy the relevant files and Lua
plugin files in the `postInstall` phase. Do note, however, that you still need
to fetch the plugin sources somehow. npins is, once again, the recommended
option to fetch the plugin sources. Refer to the previous section on how to use
npins to add a new plugin.
Plugins built from source must go into the `flake/pkgs/by-name` overlay. It will
automatically create flake outputs for individual packages. Lastly, you must add
your package to the plugin builder (`pluginBuilders`) function manually in
`modules/wrapper/build/config.nix`. Once done, you may refer to your plugin as a
**string**.
```nix
{
config.vim.startPlugins = ["blink-cmp"];
}
```
### Modular Setup Options {#sec-modular-setup-options}
Most plugins is initialized with a call to `require('plugin').setup({...})`.
We use a special function that lets you easily add support for such setup
options in a modular way: `mkPluginSetupOption`.
Once you have added the source of the plugin as shown above, you can define the
setup options like this:
```nix
# in modules/.../your-plugin/your-plugin.nix
{lib, ...}:
let
inherit (lib.types) bool int;
inherit (lib.nvim.types) mkPluginSetupOption;
in {
options.vim.your-plugin = {
setupOpts = mkPluginSetupOption "plugin name" {
enable_feature_a = mkOption {
type = bool;
default = false;
# ...
};
number_option = mkOption {
type = int;
default = 3;
# ...
};
};
};
}
```
```nix
# in modules/.../your-plugin/config.nix
{lib, config, ...}:
let
cfg = config.vim.your-plugin;
in {
vim.luaConfigRC = lib.nvim.dag.entryAnywhere ''
require('plugin-name').setup(${lib.nvim.lua.toLuaObject cfg.setupOpts})
'';
}
```
This above config will result in this Lua script:
```lua
require('plugin-name').setup({
enable_feature_a = false,
number_option = 3,
})
```
Now users can set any of the pre-defined option field, and can also add their
own fields!
```nix
# in user's config
{
vim.your-plugin.setupOpts = {
enable_feature_a = true;
number_option = 4;
another_field = "hello";
size = { # nested fields work as well
top = 10;
};
};
}
```
### Details of `toLuaObject` {#sec-details-of-toluaobject}
As you've seen above, `toLuaObject` is used to convert our nix attrSet
`cfg.setupOpts`, into a lua table. Here are some rules of the conversion:
1. Nix `null` converts to lua `nil`
2. Number and strings convert to their lua counterparts
3. Nix attribute sets (`{}`) and lists (`[]`) convert into Lua dictionaries and
tables respectively. Here is an example of Nix -> Lua conversion.
- `{foo = "bar"}` -> `{["foo"] = "bar"}`
- `["foo" "bar"]` -> `{"foo", "bar"}`
4. You can write raw Lua code using `lib.generators.mkLuaInline`. This function
is part of nixpkgs, and is accessible without relying on **nvf**'s extended
library.
- `mkLuaInline "function add(a, b) return a + b end"` will yield the
following result:
```nix
{
_type = "lua-inline";
expr = "function add(a, b) return a + b end";
}
```
The above expression will be interpreted as a Lua expression in the final
config. Without the `mkLuaInline` function, you will only receive a string
literal. You can use it to feed plugin configuration tables Lua functions
that return specific values as expected by the plugins.
```nix
{
vim.your-plugin.setupOpts = {
on_init = lib.generators.mkLuaInline ''
function()
print('we can write lua!')
end
'';
};
}
```
### Lazy Loading Plugins {#sec-lazy-plugins}
If the plugin can be lazy-loaded, `vim.lazy.plugins` should be used to add it.
Lazy plugins are managed by `lz.n`.
```nix
# in modules/.../your-plugin/config.nix
{config, ...}: let
cfg = config.vim.your-plugin;
in {
vim.lazy.plugins.your-plugin = {
# Instead of vim.startPlugins, use this:
package = "your-plugin";
# ıf your plugin uses the `require('your-plugin').setup{...}` pattern
setupModule = "your-plugin";
inherit (cfg) setupOpts;
# Events that trigger this plugin to be loaded
event = ["DirChanged"];
cmd = ["YourPluginCommand"];
# Plugin Keymaps
keys = [
# We'll cover this in detail in the 'keybinds' section
{
key = "<leader>d";
mode = "n";
action = ":YourPluginCommand";
}
];
};
}
```
This results in the following lua code:
```lua
require('lz.n').load({
{
"name-of-your-plugin",
after = function()
require('your-plugin').setup({
--[[ your setupOpts ]]--
})
end,
event = {"DirChanged"},
cmd = {"YourPluginCommand"},
keys = {
{"<leader>d", ":YourPluginCommand", mode = {"n"}},
},
}
})
```
[`vim.lazy.plugins` spec]: ./options.html#option-vim-lazy-plugins
A full list of options can be found in the [`vim.lazy.plugins` spec] on the
rendered manual.
## Keybinds {#sec-keybinds}
[extended standard library]: https://github.com/NotAShelf/nvf/tree/main/lib
As of 0.4, there exists an API for writing your own keybinds and a couple of
useful utility functions are available in the [extended standard library]. The
following section contains a general overview to how you may utilize said
functions.
### Custom Key Mappings Support for a Plugin {#sec-custom-key-mappings}
To set a mapping, you should define it in `vim.keymaps`. As an example, a simple
keybinding can look like this:
```nix
{
vim.keymaps = [
{
key = "<leader>wq";
mode = ["n"];
action = ":wq<CR>";
silent = true;
desc = "Save file and quit";
}
];
}
```
[module option documentation]: options.html#option-vim-keymaps
There are many other settings available in the keymap module. Please refer to
the [module option documentation] for a full and up-to-date list of them.
To make adding new keymaps for your favorite plugins easier, **nvf** provides a
helper function. This is so that you do not have to write the mapping attribute
sets every time:
- `mkKeymap`, which mimics Neovim's `vim.keymap.set` function
You can read the source code of some modules to see them in action, but the
usage should look something like this:
```nix
# pluginDefinition.nix
{lib, ...}: let
inherit (lib.options) mkEnableOption;
inherit (lib.nvim.binds) mkMappingOption;
in {
options.vim.plugin = {
enable = mkEnableOption "Enable plugin";
# Mappings should always be inside an attrset called mappings
mappings = {
workspaceDiagnostics = mkMappingOption "Workspace diagnostics [trouble]" "<leader>lwd";
documentDiagnostics = mkMappingOption "Document diagnostics [trouble]" "<leader>ld";
lspReferences = mkMappingOption "LSP References [trouble]" "<leader>lr";
quickfix = mkMappingOption "QuickFix [trouble]" "<leader>xq";
locList = mkMappingOption "LOCList [trouble]" "<leader>xl";
symbols = mkMappingOption "Symbols [trouble]" "<leader>xs";
};
}
```
<!-- markdownlint-disable MD013 -->
```nix
# config.nix
{
config,
lib,
options,
...
}: let
inherit (lib.modules) mkIf;
inherit (lib.nvim.binds) mkKeymap;
cfg = config.vim.plugin;
keys = cfg.mappings;
inherit (options.vim.lsp.trouble) mappings;
in {
config = mkIf cfg.enable {
vim.keymaps = [
(mkKeymap "n" keys.workspaceDiagnostics "<cmd>Trouble toggle diagnostics<CR>" {desc = mappings.workspaceDiagnostics.description;})
(mkKeymap "n" keys.documentDiagnostics "<cmd>Trouble toggle diagnostics filter.buf=0<CR>" {desc = mappings.documentDiagnostics.description;})
(mkKeymap "n" keys.lspReferences "<cmd>Trouble toggle lsp_references<CR>" {desc = mappings.lspReferences.description;})
(mkKeymap "n" keys.quickfix "<cmd>Trouble toggle quickfix<CR>" {desc = mappings.quickfix.description;})
(mkKeymap "n" keys.locList "<cmd>Trouble toggle loclist<CR>" {desc = mappings.locList.description;})
(mkKeymap "n" keys.symbols "<cmd>Trouble toggle symbols<CR>" {desc = mappings.symbols.description;})
];
};
}
```
<!-- markdownlint-enable MD013 -->
> [!TIP]
> If you have come across a plugin that has an API that doesn't seem to easily
> allow custom keybindings, don't be scared to implement a draft PR. We'll help
> you get it done.

View file

@ -1,266 +0,0 @@
# Adding Plugins {#sec-additional-plugins}
There are two methods for adding new Neovim plugins to **nvf**. npins is the
faster option that should be preferred if the plugin consists of pure Lua or
Vimscript code. In which case there is no building required, and we can easily
handle the copying of plugin files. Alternative method, which is required when
plugins try to build their own libraries (e.g., in Rust or C) that need to be
built with Nix to function correctly.
## With npins {#sec-npins-for-plugins}
npins is the standard method of adding new plugins to **nvf**. You simply need
the repository URL for the plugin, and can add it as a source to be built
automatically with one command. To add a new Neovim plugin, use `npins`. For
example:
```bash
nix-shell -p npins # or nix shell nixpkgs#npins if using flakes
```
Then run:
```bash
npins add --name <plugin name> github <owner> <repo> -b <branch>
```
::: {.note}
Be sure to replace any non-alphanumeric characters with `-` for `--name`. For
example
```bash
npins add --name lazydev-nvim github folke lazydev.nvim -b main
```
:::
Once the `npins` command is done, you can start referencing the plugin as a
**string**.
```nix
{
config.vim.startPlugins = ["lazydev-nvim"];
}
```
## Packaging Complex Plugins {#sec-pkgs-for-plugins}
[blink.cmp]: https://github.com/Saghen/blink.cmp
Some plugins require additional packages to be built and substituted to function
correctly. For example [blink.cmp] requires its own fuzzy matcher library, built
with Rust, to be installed or else defaults to a much slower Lua implementation.
In the Blink documentation, you are advised to build with `cargo` but that is
not ideal since we are leveraging the power of Nix. In this case the ideal
solution is to write a derivation for the plugin.
We use `buildRustPackage` to build the library from the repository root, and
copy everything in the `postInstall` phase.
```nix
postInstall = ''
cp -r {lua,plugin} "$out"
mkdir -p "$out/doc"
cp 'doc/'*'.txt' "$out/doc/"
mkdir -p "$out/target"
mv "$out/lib" "$out/target/release"
'';
```
In a similar fashion, you may utilize `stdenv.mkDerivation` and other Nixpkgs
builders to build your library from source, and copy the relevant files and Lua
plugin files in the `postInstall` phase. Do note, however, that you still need
to fetch the plugin sources somehow. npins is, once again, the recommended
option to fetch the plugin sources. Refer to the previous section on how to use
npins to add a new plugin.
Plugins built from source must go into the `flake/pkgs/by-name` overlay. It will
automatically create flake outputs for individual packages. Lastly, you must add
your package to the plugin builder (`pluginBuilders`) function manually in
`modules/wrapper/build/config.nix`. Once done, you may refer to your plugin as a
**string**.
```nix
{
config.vim.startPlugins = ["blink-cmp"];
}
```
## Modular setup options {#sec-modular-setup-options}
Most plugins is initialized with a call to `require('plugin').setup({...})`.
We use a special function that lets you easily add support for such setup
options in a modular way: `mkPluginSetupOption`.
Once you have added the source of the plugin as shown above, you can define the
setup options like this:
```nix
# in modules/.../your-plugin/your-plugin.nix
{lib, ...}:
let
inherit (lib.types) bool int;
inherit (lib.nvim.types) mkPluginSetupOption;
in {
options.vim.your-plugin = {
setupOpts = mkPluginSetupOption "plugin name" {
enable_feature_a = mkOption {
type = bool;
default = false;
# ...
};
number_option = mkOption {
type = int;
default = 3;
# ...
};
};
};
}
```
```nix
# in modules/.../your-plugin/config.nix
{lib, config, ...}:
let
cfg = config.vim.your-plugin;
in {
vim.luaConfigRC = lib.nvim.dag.entryAnywhere ''
require('plugin-name').setup(${lib.nvim.lua.toLuaObject cfg.setupOpts})
'';
}
```
This above config will result in this Lua script:
```lua
require('plugin-name').setup({
enable_feature_a = false,
number_option = 3,
})
```
Now users can set any of the pre-defined option field, and can also add their
own fields!
```nix
# in user's config
{
vim.your-plugin.setupOpts = {
enable_feature_a = true;
number_option = 4;
another_field = "hello";
size = { # nested fields work as well
top = 10;
};
};
}
```
## Details of toLuaObject {#sec-details-of-toluaobject}
As you've seen above, `toLuaObject` is used to convert our nix attrSet
`cfg.setupOpts`, into a lua table. Here are some rules of the conversion:
1. Nix `null` converts to lua `nil`
2. Number and strings convert to their lua counterparts
3. Nix attribute sets (`{}`) and lists (`[]`) convert into Lua dictionaries and
tables respectively. Here is an example of Nix -> Lua conversion.
- `{foo = "bar"}` -> `{["foo"] = "bar"}`
- `["foo" "bar"]` -> `{"foo", "bar"}`
4. You can write raw Lua code using `lib.generators.mkLuaInline`. This function
is part of nixpkgs, and is accessible without relying on **nvf**'s extended
library.
- `mkLuaInline "function add(a, b) return a + b end"` will yield the
following result:
```nix
{
_type = "lua-inline";
expr = "function add(a, b) return a + b end";
}
```
The above expression will be interpreted as a Lua expression in the final
config. Without the `mkLuaInline` function, you will only receive a string
literal. You can use it to feed plugin configuration tables Lua functions
that return specific values as expected by the plugins.
```nix
{
vim.your-plugin.setupOpts = {
on_init = lib.generators.mkLuaInline ''
function()
print('we can write lua!')
end
'';
};
}
```
## Lazy plugins {#sec-lazy-plugins}
If the plugin can be lazy-loaded, `vim.lazy.plugins` should be used to add it.
Lazy plugins are managed by `lz.n`.
```nix
# in modules/.../your-plugin/config.nix
{config, ...}: let
cfg = config.vim.your-plugin;
in {
vim.lazy.plugins.your-plugin = {
# Instead of vim.startPlugins, use this:
package = "your-plugin";
# ıf your plugin uses the `require('your-plugin').setup{...}` pattern
setupModule = "your-plugin";
inherit (cfg) setupOpts;
# Events that trigger this plugin to be loaded
event = ["DirChanged"];
cmd = ["YourPluginCommand"];
# Plugin Keymaps
keys = [
# We'll cover this in detail in the 'keybinds' section
{
key = "<leader>d";
mode = "n";
action = ":YourPluginCommand";
}
];
};
}
```
This results in the following lua code:
```lua
require('lz.n').load({
{
"name-of-your-plugin",
after = function()
require('your-plugin').setup({
--[[ your setupOpts ]]--
})
end,
event = {"DirChanged"},
cmd = {"YourPluginCommand"},
keys = {
{"<leader>d", ":YourPluginCommand", mode = {"n"}},
},
}
})
```
[`vim.lazy.plugins` spec]: https://notashelf.github.io/nvf/options.html#opt-vim.lazy.plugins
A full list of options can be found in the [`vim.lazy.plugins` spec] on the
rendered manual.

View file

@ -1,17 +0,0 @@
# Getting Started {#sec-contrib-getting-started}
You, naturally, would like to start by forking the repository to get started. If
you are new to Git and GitHub, do have a look at GitHub's
[Fork a repo guide](https://help.github.com/articles/fork-a-repo/) for
instructions on how you can do this. Once you have a fork of **nvf**, you should
create a separate branch based on the most recent `main` branch. Give your
branch a reasonably descriptive name (e.g. `feature/debugger` or
`fix/pesky-bug`) and you are ready to work on your changes
Implement your changes and commit them to the newly created branch and when you
are happy with the result, and positive that it fulfills our
[Contributing Guidelines](#sec-guidelines), push the branch to GitHub and
[create a pull request](https://help.github.com/articles/creating-a-pull-request).
The default pull request template available on the **nvf** repository will guide
you through the rest of the process, and we'll gently nudge you in the correct
direction if there are any mistakes.

View file

@ -1,188 +0,0 @@
# Guidelines {#sec-guidelines}
If your contribution tightly follows the guidelines, then there is a good chance
it will be merged without too much trouble. Some of the guidelines will be
strictly enforced, others will remain as gentle nudges towards the correct
direction. As we have no automated system enforcing those guidelines, please try
to double check your changes before making your pull request in order to avoid
"faulty" code slipping by.
If you are uncertain how these rules affect the change you would like to make
then feel free to start a discussion in the
[discussions tab](https://github.com/NotAShelf/nvf/discussions) ideally (but not
necessarily) before you start developing.
## Adding Documentation {#sec-guidelines-documentation}
[Nixpkgs Flavoured Markdown]: https://github.com/NixOS/nixpkgs/blob/master/doc/README.md#syntax
Almost all changes warrant updates to the documentation: at the very least, you
must update the changelog. Both the manual and module options use
[Nixpkgs Flavoured Markdown].
The HTML version of this manual containing both the module option descriptions
and the documentation of **nvf** (such as this page) can be generated and opened
by typing the following in a shell within a clone of the **nvf** Git repository:
```console
$ nix build .#docs-html
$ xdg-open $PWD/result/share/doc/nvf/index.html
```
## Formatting Code {#sec-guidelines-formatting}
Make sure your code is formatted as described in
[code-style section](#sec-guidelines-code-style). To maintain consistency
throughout the project you are encouraged to browse through existing code and
adopt its style also in new code.
## Formatting Commits {#sec-guidelines-commit-message-style}
Similar to [code style guidelines](#sec-guidelines-code-style) we encourage a
consistent commit message format as described in
[commit style guidelines](#sec-guidelines-commit-style).
## Commit Style {#sec-guidelines-commit-style}
The commits in your pull request should be reasonably self-contained. Which
means each and every commit in a pull request should make sense both on its own
and in general context. That is, a second commit should not resolve an issue
that is introduced in an earlier commit. In particular, you will be asked to
amend any commit that introduces syntax errors or similar problems even if they
are fixed in a later commit.
The commit messages should follow the
[seven rules](https://chris.beams.io/posts/git-commit/#seven-rule), except for
"Capitalize the subject line". We also ask you to include the affected code
component or module in the first line. A commit message ideally, but not
necessarily, follow the given template from home-manager's own documentation
```
{component}: {description}
{long description}
```
where `{component}` refers to the code component (or module) your change
affects, `{description}` is a very brief description of your change, and
`{long description}` is an optional clarifying description. As a rare exception,
if there is no clear component, or your change affects many components, then the
`{component}` part is optional. See
[example commit message](#sec-guidelines-ex-commit-message) for a commit message
that fulfills these requirements.
## Example Commit {#sec-guidelines-ex-commit-message}
The commit
[69f8e47e9e74c8d3d060ca22e18246b7f7d988ef](https://github.com/nix-community/home-manager/commit/69f8e47e9e74c8d3d060ca22e18246b7f7d988ef)
in home-manager contains the following commit message.
```
starship: allow running in Emacs if vterm is used
The vterm buffer is backed by libvterm and can handle Starship prompts
without issues.
```
Similarly, if you are contributing to **nvf**, you would include the scope of
the commit followed by the description:
```
languages/ruby: init module
Adds a language module for Ruby, adds appropriate formatters and Treesitter grammars
```
Long description can be omitted if the change is too simple to warrant it. A
minor fix in spelling or a formatting change does not warrant long description,
however, a module addition or removal does as you would like to provide the
relevant context, i.e. the reasoning behind it, for your commit.
Finally, when adding a new module, say `modules/foo.nix`, we use the fixed
commit format `foo: add module`. You can, of course, still include a long
description if you wish.
In case of nested modules, i.e `modules/languages/java.nix` you are recommended
to contain the parent as well - for example `languages/java: some major change`.
## Code Style {#sec-guidelines-code-style}
### Treewide {#sec-code-style-treewide}
Keep lines at a reasonable width, ideally 80 characters or less. This also
applies to string literals and module descriptions and documentation.
### Nix {#sec-code-style-nix}
[alejandra]: https://github.com/kamadorueda/alejandra
**nvf** is formatted by the [alejandra] tool and the formatting is checked in
the pull request and push workflows. Run the `nix fmt` command inside the
project repository before submitting your pull request.
While Alejandra is mostly opinionated on how code looks after formatting,
certain changes are done at the user's discretion based on how the original code
was structured.
Please use one line code for attribute sets that contain only one subset. For
example:
```nix
# parent modules should always be unfolded
# which means module = { value = ... } instead of module.value = { ... }
module = {
value = mkEnableOption "some description" // { default = true; }; # merges can be done inline where possible
# same as parent modules, unfold submodules
subModule = {
# this is an option that contains more than one nested value
# Note: try to be careful about the ordering of `mkOption` arguments.
# General rule of thumb is to order from least to most likely to change.
# This is, for most cases, type < default < description.
# Example, if present, would be between default and description
someOtherValue = mkOption {
type = lib.types.bool;
default = true;
description = "Some other description";
};
};
}
```
If you move a line down after the merge operator, Alejandra will automatically
unfold the whole merged attrset for you, which we **do not** want.
```nix
module = {
key = mkEnableOption "some description" // {
default = true; # we want this to be inline
}; # ...
}
```
For lists, it is mostly up to your own discretion how you want to format them,
but please try to unfold lists if they contain multiple items and especially if
they are to include comments.
```nix
# this is ok
acceptableList = [
item1 # comment
item2
item3 # some other comment
item4
];
# this is not ok
listToBeAvoided = [item1 item2 /* comment */ item3 item4];
# this is ok
acceptableList = [item1 item2];
# this is also ok if the list is expected to contain more elements
acceptableList= [
item1
item2
# more items if needed...
];
```

View file

@ -1,97 +0,0 @@
# Keybinds {#sec-keybinds}
As of 0.4, there exists an API for writing your own keybinds and a couple of
useful utility functions are available in the
[extended standard library](https://github.com/NotAShelf/nvf/tree/main/lib). The
following section contains a general overview to how you may utilize said
functions.
## Custom Key Mappings Support for a Plugin {#sec-custom-key-mappings}
To set a mapping, you should define it in `vim.keymaps`.
An example, simple keybinding, can look like this:
```nix
{
vim.keymaps = [
{
key = "<leader>wq";
mode = ["n"];
action = ":wq<CR>";
silent = true;
desc = "Save file and quit";
}
];
}
```
There are many settings available in the options. Please refer to the
[documentation](https://notashelf.github.io/nvf/options.html#opt-vim.keymaps) to
see a list of them.
**nvf** provides a helper function, so that you don't have to write the mapping
attribute sets every time:
- `mkKeymap`, which mimics neovim's `vim.keymap.set` function
You can read the source code of some modules to see them in action, but the
usage should look something like this:
```nix
# plugindefinition.nix
{lib, ...}: let
inherit (lib.options) mkEnableOption;
inherit (lib.nvim.binds) mkMappingOption;
in {
options.vim.plugin = {
enable = mkEnableOption "Enable plugin";
# Mappings should always be inside an attrset called mappings
mappings = {
workspaceDiagnostics = mkMappingOption "Workspace diagnostics [trouble]" "<leader>lwd";
documentDiagnostics = mkMappingOption "Document diagnostics [trouble]" "<leader>ld";
lspReferences = mkMappingOption "LSP References [trouble]" "<leader>lr";
quickfix = mkMappingOption "QuickFix [trouble]" "<leader>xq";
locList = mkMappingOption "LOCList [trouble]" "<leader>xl";
symbols = mkMappingOption "Symbols [trouble]" "<leader>xs";
};
}
```
```nix
# config.nix
{
config,
lib,
options,
...
}: let
inherit (lib.modules) mkIf;
inherit (lib.nvim.binds) mkKeymap;
cfg = config.vim.plugin;
keys = cfg.mappings;
inherit (options.vim.lsp.trouble) mappings;
in {
config = mkIf cfg.enable {
vim.keymaps = [
(mkKeymap "n" keys.workspaceDiagnostics "<cmd>Trouble toggle diagnostics<CR>" {desc = mappings.workspaceDiagnostics.description;})
(mkKeymap "n" keys.documentDiagnostics "<cmd>Trouble toggle diagnostics filter.buf=0<CR>" {desc = mappings.documentDiagnostics.description;})
(mkKeymap "n" keys.lspReferences "<cmd>Trouble toggle lsp_references<CR>" {desc = mappings.lspReferences.description;})
(mkKeymap "n" keys.quickfix "<cmd>Trouble toggle quickfix<CR>" {desc = mappings.quickfix.description;})
(mkKeymap "n" keys.locList "<cmd>Trouble toggle loclist<CR>" {desc = mappings.locList.description;})
(mkKeymap "n" keys.symbols "<cmd>Trouble toggle symbols<CR>" {desc = mappings.symbols.description;})
];
};
}
```
::: {.note}
If you have come across a plugin that has an API that doesn't seem to easily
allow custom keybindings, don't be scared to implement a draft PR. We'll help
you get it done.
:::

View file

@ -1,15 +0,0 @@
# Testing Changes {#sec-testing-changes}
Once you have made your changes, you will need to test them thoroughly. If it is
a module, add your module option to `configuration.nix` (located in the root of
this project) inside `neovimConfiguration`. Enable it, and then run the maximal
configuration with `nix run .#maximal -Lv` to check for build errors. If neovim
opens in the current directory without any error messages (you can check the
output of `:messages` inside neovim to see if there are any errors), then your
changes are good to go. Open your pull request, and it will be reviewed as soon
as possible.
If it is not a new module, but a change to an existing one, then make sure the
module you have changed is enabled in the maximal configuration by editing
`configuration.nix`, and then run it with `nix run .#maximal -Lv`. Same
procedure as adding a new module will apply here.

115
docs/manual/index.md Normal file
View file

@ -0,0 +1,115 @@
# Introduction {#nvf-manual}
Generated for nvf @NVF_VERSION@
## Preface {#ch-preface}
### What is nvf {#sec-what-is-it}
[Nix]: https://nixos.org
**nvf** is a highly modular, configurable, extensible and _easy to use_ Neovim
configuration framework built for and designed to be used with [Nix]. Boasting
flexibility, robustness and ease of use (among other positive traits), this
project allows you to configure a fully featured Neovim instance with a few
lines of Nix while leaving all kinds of doors open for integrating Lua in your
configurations _whether you are a beginner or an advanced user_.
## Try it Out {#ch-try-it-out}
Thanks to the portability of Nix, you can try out **nvf** without actually
installing it to your machine. Below are the commands you may run to try out
different configurations provided by this flake. As of v0.5, two specialized
configurations are provided:
- **Nix** (`packages.nix`) - Nix language server + simple utility plugins
- **Maximal** (`packages.maximal`) - Variable language servers + utility and
decorative plugins
You may try out any of the provided configurations using the `nix run` command
on a system where Nix is installed.
```sh
# Add the nvf cache
$ cachix use nvf # Optional: it'll save you CPU resources and time
# Run the minimal configuration with the cache enabled
$ nix run github:notashelf/nvf#nix # Will run the default minimal configuration
```
Do keep in mind that this is **susceptible to garbage collection** meaning that
the built outputs will be removed from your Nix store once you garbage collect.
## Using Prebuilt Configurations {#sec-using-prebuilt-configs}
<!-- markdownlint-disable MD014 -->
```bash
$ nix run github:notashelf/nvf#nix
$ nix run github:notashelf/nvf#maximal
```
<!-- markdownlint-enable MD014 -->
### Available Configurations {#sec-available-configs}
> [!NOTE]
> The below configurations are provided for demonstration purposes, and are
> **not** designed to be installed as is. You may refer to the installation
> steps below and the helpful tips section for details on creating your own
> configurations.
#### Nix {#sec-configs-nix}
`Nix` configuration by default provides LSP/diagnostic support for Nix alongside
a set of visual and functional plugins. By running `nix run .#`, which is the
default package, you will build Neovim with this config.
```bash
$ nix run github:notashelf/nvf#nix test.nix
# => This will open a file called `test.nix` with Nix LSP and syntax highlighting
```
This command will start Neovim with some opinionated plugin configurations, and
is designed specifically for Nix. The `nix` configuration lets you see how a
fully configured Neovim setup _might_ look like without downloading too many
packages or shell utilities.
#### Maximal {#sec-configs-maximal}
`Maximal` is the ultimate configuration that will enable support for more
commonly used language as well as additional complementary plugins. Keep in
mind, however, that this will pull a lot of dependencies.
```bash
$ nix run github:notashelf/nvf#maximal -- test.nix
# => This will open a file called `test.nix` with a variety of plugins available
```
It uses the same configuration template with the [Nix](#sec-configs-nix)
configuration, but supports many more languages, and enables more utility,
companion or fun plugins.
> [!WARNING]
> Running the maximal config will download _a lot_ of packages as it is
> downloading language servers, formatters, and more. If CPU time and bandwidth
> are concerns, please use the default package instead.
## Installing nvf {#ch-installation}
<!-- markdownlint-disable MD051 -->
[module installation section]: #ch-module-installation
<!-- markdownlint-enable MD051 -->
There are multiple ways of installing **nvf** on your system. You may either
choose the standalone installation method, which does not depend on a module
system and may be done on any system that has the Nix package manager or the
appropriate modules for NixOS and Home Manager as described in the
[module installation section].
```{=include=}
installation/custom-configuration.md
installation/modules.md
```

View file

@ -1,14 +0,0 @@
# Installing nvf {#ch-installation}
[module installation section]: #ch-module-installation
There are multiple ways of installing nvf on your system. You may either choose
the standalone installation method, which does not depend on a module system and
may be done on any system that has the Nix package manager or the appropriate
modules for NixOS and home-manager as described in the
[module installation section].
```{=include=} chapters
installation/custom-configuration.md
installation/modules.md
```

View file

@ -1,7 +1,7 @@
### Prerequisites {#sec-flakes-prerequisites} #### Prerequisites {#sec-flakes-prerequisites}
To install nvf with flakes, you must make sure the following requirements are To install **nvf** with flakes, you must make sure the following requirements
met. are met.
1. Nix 2.4 or later must be installed. You may use `nix-shell` to get a later 1. Nix 2.4 or later must be installed. You may use `nix-shell` to get a later
version of Nix from nixpkgs. version of Nix from nixpkgs.
@ -29,5 +29,6 @@ met.
following additional flags to `nix` and `home-manager`: following additional flags to `nix` and `home-manager`:
```sh ```sh
# Temporarily enables "nix-command" and "flakes" experimental features.
$ nix --extra-experimental-features "nix-command flakes" <sub-commands> $ nix --extra-experimental-features "nix-command flakes" <sub-commands>
``` ```

View file

@ -1,7 +1,7 @@
# Home-Manager Module {#ch-hm-module} ## Home Manager Module {#ch-hm-module}
The home-manager module allows us to customize the different `vim` options from The Home Manager module allows us to customize the different `vim` options from
inside the home-manager configuration without having to call for the wrapper inside the Home Manager configuration without having to call for the wrapper
yourself. It is the recommended way to use **nvf** alongside the NixOS module yourself. It is the recommended way to use **nvf** alongside the NixOS module
depending on your needs. depending on your needs.
@ -19,20 +19,13 @@ To use **nvf** with flakes, we first need to add the input to our `flake.nix`.
# flake.nix # flake.nix
{ {
inputs = { inputs = {
# Optional, if you intend to follow nvf's obsidian-nvim input # nvf works best with and only directly supports flakes
# you must also add it as a flake input.
obsidian-nvim.url = "github:epwalsh/obsidian.nvim";
# Required, nvf works best and only directly supports flakes
nvf = { nvf = {
url = "github:NotAShelf/nvf"; url = "github:NotAShelf/nvf";
# You can override the input nixpkgs to follow your system's # You can override the input nixpkgs to follow your system's
# instance of nixpkgs. This is safe to do as nvf does not depend # instance of nixpkgs. This is safe to do as nvf does not depend
# on a binary cache. # on a binary cache.
inputs.nixpkgs.follows = "nixpkgs"; inputs.nixpkgs.follows = "nixpkgs";
# Optionally, you can also override individual plugins
# for example:
inputs.obsidian-nvim.follows = "obsidian-nvim"; # <- this will use the obsidian-nvim from your inputs
}; };
# ... # ...
@ -44,8 +37,8 @@ Followed by importing the home-manager module somewhere in your configuration.
```nix ```nix
{ {
# Assuming "nvf" is in your inputs and inputs is in the argument set. # Assuming nvf is in your inputs and inputs is in the argument set.
# See example installation below # See example installation below.
imports = [ inputs.nvf.homeManagerModules.default ]; imports = [ inputs.nvf.homeManagerModules.default ];
} }
``` ```

View file

@ -1,11 +1,11 @@
# NixOS Module {#ch-nixos-module} ## NixOS Module {#ch-nixos-module}
The NixOS module allows us to customize the different `vim` options from inside The NixOS module allows us to customize the different `vim` options from inside
the NixOS configuration without having to call for the wrapper yourself. It is the NixOS configuration without having to call for the wrapper yourself. It is
the recommended way to use **nvf** alongside the home-manager module depending the recommended way to use **nvf** alongside the home-manager module depending
on your needs. on your needs.
## With Flakes {#sec-nixos-flakes} ### With Flakes {#sec-nixos-flakes}
```{=include=} ```{=include=}
flakes.md flakes.md
@ -19,20 +19,13 @@ To use **nvf** with flakes, we first need to add the input to our `flake.nix`.
# flake.nix # flake.nix
{ {
inputs = { inputs = {
# Optional, if you intend to follow nvf's obsidian-nvim input # nvf works best with and only directly supports flakes
# you must also add it as a flake input.
obsidian-nvim.url = "github:epwalsh/obsidian.nvim";
# Required, nvf works best and only directly supports flakes
nvf = { nvf = {
url = "github:NotAShelf/nvf"; url = "github:NotAShelf/nvf";
# You can override the input nixpkgs to follow your system's # You can override the input nixpkgs to follow your system's
# instance of nixpkgs. This is safe to do as nvf does not depend # instance of nixpkgs. This is safe to do as nvf does not depend
# on a binary cache. # on a binary cache.
inputs.nixpkgs.follows = "nixpkgs"; inputs.nixpkgs.follows = "nixpkgs";
# Optionally, you can also override individual plugins
# for example:
inputs.obsidian-nvim.follows = "obsidian-nvim"; # <- this will use the obsidian-nvim from your inputs
}; };
# ... # ...
@ -44,8 +37,8 @@ Followed by importing the NixOS module somewhere in your configuration.
```nix ```nix
{ {
# assuming nvf is in your inputs and inputs is in the argset # Assuming nvf is in your inputs and inputs is in the argument set.
# see example below # See example below.
imports = [ inputs.nvf.nixosModules.default ]; imports = [ inputs.nvf.nixosModules.default ];
} }
``` ```
@ -79,7 +72,6 @@ configure **nvf**.
{ {
programs.nvf = { programs.nvf = {
enable = true; enable = true;
# Your settings need to go into the settings attribute set # Your settings need to go into the settings attribute set
# most settings are documented in the appendix # most settings are documented in the appendix
settings = { settings = {

View file

@ -1,4 +1,4 @@
# Standalone Installation on Home-Manager {#ch-standalone-hm} ## Standalone Installation on Home-Manager {#ch-standalone-hm}
Your built Neovim configuration can be exposed as a flake output to make it Your built Neovim configuration can be exposed as a flake output to make it
easier to share across machines, repositories and so on. Or it can be added to easier to share across machines, repositories and so on. Or it can be added to

View file

@ -1,4 +1,4 @@
# Standalone Installation on NixOS {#ch-standalone-nixos} ## Standalone Installation on NixOS {#ch-standalone-nixos}
Your built Neovim configuration can be exposed as a flake output to make it Your built Neovim configuration can be exposed as a flake output to make it
easier to share across machines, repositories and so on. Or it can be added to easier to share across machines, repositories and so on. Or it can be added to

View file

@ -1,30 +0,0 @@
# nvf manual {#nvf-manual}
## Version @NVF_VERSION@
```{=include=} preface
preface.md
try-it-out.md
```
```{=include=} parts
installation.md
configuring.md
tips.md
```
```{=include=} chapters
hacking.md
```
```{=include=} appendix html:into-file=//quirks.html
quirks.md
```
```{=include=} appendix html:into-file=//options.html
options.md
```
```{=include=} appendix html:into-file=//release-notes.html
release-notes/release-notes.md
```

View file

@ -1,21 +0,0 @@
# nvf Configuration Options {#ch-options}
Below are the module options provided by nvf, in no particular order. Most
options will include useful comments, warnings or setup tips on how a module
option is meant to be used as well as examples in complex cases.
An offline version of this page is bundled with nvf as a part of the manpages
which you can access with `man 5 nvf`. Please let us know if you believe any of
the options below are missing useful examples.
<!--
In the manual, individual options may be referenced in Hyperlinks as follows:
[](#opt-vim.*) If changing the prefix here, do keep in mind the #opt- suffix will have
to be changed everywhere.
-->
```{=include=} options
id-prefix: opt-
list-id: nvf-options
source: @OPTIONS_JSON@
```

View file

@ -1,20 +0,0 @@
# Preface {#ch-preface}
## What is nvf {#sec-what-is-it}
nvf is a highly modular, configurable, extensible and easy to use Neovim
configuration in Nix. Designed for flexibility and ease of use, nvf allows you
to easily configure your fully featured Neovim instance with a few lines of Nix.
## Bugs & Suggestions {#sec-bugs-suggestions}
[issue tracker]: https://github.com/notashelf/nvf/issues
[discussions tab]: https://github.com/notashelf/nvf/discussions
[pull requests tab]: https://github.com/notashelf/nvf/pulls
If you notice any issues with nvf, or this documentation, then please consider
reporting them over at the [issue tracker]. Issues tab, in addition to the
[discussions tab] is a good place as any to request new features.
You may also consider submitting bugfixes, feature additions and upstreamed
changes that you think are critical over at the [pull requests tab].

View file

@ -5,9 +5,20 @@ be it a result of generating Lua from Nix, or the state of packaging. This page,
in turn, will list any known modules or plugins that are known to misbehave, and in turn, will list any known modules or plugins that are known to misbehave, and
possible workarounds that you may apply. possible workarounds that you may apply.
<!-- If adding a new known quirk, please create a new page in quirks/ and include ```{=include=}
the name of the file here.-->
```{=include=} chapters
quirks/nodejs.md quirks/nodejs.md
``` ```
## Bugs & Suggestions {#ch-bugs-suggestions}
[issue tracker]: https://github.com/notashelf/nvf/issues
[discussions tab]: https://github.com/notashelf/nvf/discussions
[pull requests tab]: https://github.com/notashelf/nvf/pulls
Some quirks are not exactly quirks, but bugs in the module system. If you notice
any issues with **nvf**, or this documentation, then please consider reporting
them over at the [issue tracker]. Issues tab, in addition to the
[discussions tab] is a good place as any to request new features.
You may also consider submitting bug fixes, feature additions and upstreamed
changes that you think are critical over at the [pull requests tab].

View file

@ -1,24 +1,29 @@
# NodeJS {#ch-quirks-nodejs} ## NodeJS {#ch-quirks-nodejs}
## eslint-plugin-prettier {#sec-eslint-plugin-prettier} ### eslint-plugin-prettier {#sec-eslint-plugin-prettier}
When working with NodeJS, everything works as expected, but some projects have [eslint-plugin-prettier]: https://github.com/prettier/eslint-plugin-prettier
settings that can fool nvf. [not supposed to]: https://prettier.io/docs/en/comparison.html
If [this plugin](https://github.com/prettier/eslint-plugin-prettier) or similar When working with NodeJS, which is _obviously_ known for its meticulous
is included, you might get a situation where your eslint configuration diagnoses standards, most things are bound to work as expected but some projects, tools
your formatting according to its own config (usually `.eslintrc.js`). and settings may fool the default configurations of tools provided by **nvf**.
The issue there is your formatting is made via prettierd. If
This results in auto-formatting relying on your prettier config, while your If [eslint-plugin-prettier] or similar is included, you might get a situation
eslint config diagnoses formatting where your Eslint configuration diagnoses your formatting according to its own
[which it's not supposed to](https://prettier.io/docs/en/comparison.html)) config (usually `.eslintrc.js`). The issue there is your formatting is made via
prettierd.
In the end, you get discrepancies between what your editor does and what it This results in auto-formatting relying on your prettier configuration, while
wants. your Eslint configuration diagnoses formatting "issues" while it's
[not supposed to]. In the end, you get discrepancies between what your editor
does and what it wants.
Solutions are: Solutions are:
1. Don't add a formatting config to eslint, and separate prettier and eslint. 1. Don't add a formatting config to Eslint, instead separate Prettier and
2. PR this repo to add an ESLint formatter and configure nvf to use it. Eslint.
2. PR the repo in question to add an ESLint formatter, and configure **nvf** to
use it.

View file

@ -0,0 +1,16 @@
# Release Notes {#ch-release-notes}
This section lists the release notes for tagged version of **nvf** and the
current main current main branch
```{=include=} chapters
release-notes/rl-0.1.md
release-notes/rl-0.2.md
release-notes/rl-0.3.md
release-notes/rl-0.4.md
release-notes/rl-0.5.md
release-notes/rl-0.6.md
release-notes/rl-0.7.md
release-notes/rl-0.8.md
release-notes/rl-0.9.md
```

View file

@ -1,4 +1,4 @@
# Release 0.1 {#sec-release-0.1} # Release 0.1 {#sec-release-0-1}
This is the current master branch and information here is not final. These are This is the current master branch and information here is not final. These are
changes from the v0.1 tag. changes from the v0.1 tag.
@ -7,7 +7,7 @@ Special thanks to [home-manager](https://github.com/nix-community/home-manager/)
for this release. Docs/manual generation, the new module evaluation system, and for this release. Docs/manual generation, the new module evaluation system, and
DAG implementation are from them. DAG implementation are from them.
## Changelog {#sec-release-0.1-changelog} ## Changelog {#sec-release-0-1-changelog}
[jordanisaacs](https://github.com/jordanisaacs): [jordanisaacs](https://github.com/jordanisaacs):
@ -15,7 +15,7 @@ DAG implementation are from them.
longer defined. If you use hare and would like it added back, please file an longer defined. If you use hare and would like it added back, please file an
issue. issue.
- [](#opt-vim.startPlugins) & [](#opt-vim.optPlugins) are now an enum of - {option}`vim.startPlugins` & {option} `vim-optPlugins` are now an enum of
`string` for options sourced from the flake inputs. Users can still provide `string` for options sourced from the flake inputs. Users can still provide
vim plugin packages. vim plugin packages.
@ -28,13 +28,13 @@ DAG implementation are from them.
[relevant discourse post]: https://discourse.nixos.org/t/psa-if-you-are-on-unstable-try-out-nvim-treesitter-withallgrammars/23321?u=snowytrees [relevant discourse post]: https://discourse.nixos.org/t/psa-if-you-are-on-unstable-try-out-nvim-treesitter-withallgrammars/23321?u=snowytrees
- Treesitter grammars are now configurable with - Treesitter grammars are now configurable with
[](#opt-vim.treesitter.grammars). Utilizes the nixpkgs `nvim-treesitter` {option}`vim.treesitter.grammars`. Utilizes the nixpkgs `nvim-treesitter`
plugin rather than a custom input in order to take advantage of build support plugin rather than a custom input in order to take advantage of build support
of pinned versions. See the [relevant discourse post] for more information. of pinned versions. See the [relevant discourse post] for more information.
Packages can be found under the `vimPlugins.nvim-treesitter.builtGrammars` Packages can be found under the `vimPlugins.nvim-treesitter.builtGrammars`
namespace. namespace.
- `vim.configRC` and [](#opt-vim.luaConfigRC) are now of type DAG lines. This - `vim.configRC` and {option}`vim.luaConfigRC` are now of type DAG lines. This
allows for ordering of the config. Usage is the same is in home-manager's allows for ordering of the config. Usage is the same is in home-manager's
`home.activation` option. `home.activation` option.
@ -44,5 +44,6 @@ vim.luaConfigRC = lib.nvim.dag.entryAnywhere "config here"
[MoritzBoehme](https://github.com/MoritzBoehme): [MoritzBoehme](https://github.com/MoritzBoehme):
- `catppuccin` theme is now available as a neovim theme [](#opt-vim.theme.style) - `catppuccin` theme is now available as a neovim theme
and Lualine theme [](#opt-vim.statusline.lualine.theme). {option}`vim.theme.style` and Lualine theme
{option}`vim.statusline.lualine.theme`.

View file

@ -1,8 +1,8 @@
# Release 0.2 {#sec-release-0.2} # Release 0.2 {#sec-release-0-2}
Release notes for release 0.2 Release notes for release 0.2
## Changelog {#sec-release-0.2-changelog} ## Changelog {#sec-release-0-2-changelog}
[notashelf](https://github.com/notashelf): [notashelf](https://github.com/notashelf):
@ -10,55 +10,39 @@ Release notes for release 0.2
default, while `minimap.vim` is available with its code-minimap dependency. default, while `minimap.vim` is available with its code-minimap dependency.
- A complementary plugin, `obsidian.nvim` and the Neovim alternative for Emacs' - A complementary plugin, `obsidian.nvim` and the Neovim alternative for Emacs'
orgmode with `orgmode.nvim` have been added. Both will be disabled by default. orgmode with `orgmode.nvim` have been added. Both will be disabled by default.
- Smooth scrolling for ANY movement command is now available with - Smooth scrolling for ANY movement command is now available with
`cinnamon.nvim` `cinnamon.nvim`
- You will now notice a dashboard on startup. This is provided by the - You will now notice a dashboard on startup. This is provided by the
`alpha.nvim` plugin. You can use any of the three available dashboard plugins, `alpha.nvim` plugin. You can use any of the three available dashboard plugins,
or disable them entirely. or disable them entirely.
- There is now a scrollbar on active buffers, which can highlight errors by - There is now a scrollbar on active buffers, which can highlight errors by
hooking to your LSPs. This is on by default, but can be toggled off under hooking to your LSPs. This is on by default, but can be toggled off under
`vim.visuals` if seen necessary. `vim.visuals` if seen necessary.
- Discord Rich Presence has been added through `presence.nvim` for those who - Discord Rich Presence has been added through `presence.nvim` for those who
want to flex that they are using the _superior_ text editor. want to flex that they are using the _superior_ text editor.
- An icon picker is now available with telescope integration. You can use - An icon picker is now available with telescope integration. You can use
`:IconPickerInsert` or `:IconPickerYank` to add icons to your code. `:IconPickerInsert` or `:IconPickerYank` to add icons to your code.
- A general-purpose cheatsheet has been added through `cheatsheet.nvim`. Forget - A general-purpose cheatsheet has been added through `cheatsheet.nvim`. Forget
no longer! no longer!
- `ccc.nvim` has been added to the default plugins to allow picking colors with - `ccc.nvim` has been added to the default plugins to allow picking colors with
ease. ease.
- Most UI components of Neovim have been replaced through the help of - Most UI components of Neovim have been replaced through the help of
`noice.nvim`. There are also notifications and custom UI elements available `noice.nvim`. There are also notifications and custom UI elements available
for Neovim messages and prompts. for Neovim messages and prompts.
- A (floating by default) terminal has been added through `toggleterm.nvim`. - A (floating by default) terminal has been added through `toggleterm.nvim`.
- Harness the power of ethical (`tabnine.nvim`) and not-so-ethical - Harness the power of ethical (`tabnine.nvim`) and not-so-ethical
(`copilot.lua`) AI by those new assistant plugins. Both are off by default, (`copilot.lua`) AI by those new assistant plugins. Both are off by default,
TabNine needs to be wrapped before it's working. TabNine needs to be wrapped before it's working.
- Experimental mouse gestures have been added through `gesture.nvim`. See plugin - Experimental mouse gestures have been added through `gesture.nvim`. See plugin
page and the relevant module for more details on how to use. page and the relevant module for more details on how to use.
- Re-open last visited buffers via `nvim-session-manager`. Disabled by default - Re-open last visited buffers via `nvim-session-manager`. Disabled by default
as deleting buffers seems to be problematic at the moment. as deleting buffers seems to be problematic at the moment.
- Most of NvimTree's configuration options have been changed with some options - Most of NvimTree's configuration options have been changed with some options
being toggled to off by default. being toggled to off by default.
- Lualine had its configuration simplified and style toned down. Less color, - Lualine had its configuration simplified and style toned down. Less color,
more info. more info.
- Modules where multiple plugin configurations were in the same directory have - Modules where multiple plugin configurations were in the same directory have
been simplified. Each plugin inside a single module gets its directory to be been simplified. Each plugin inside a single module gets its directory to be
imported. imported.
- Separate config options with the same parent attribute have been merged into - Separate config options with the same parent attribute have been merged into
one for simplicity. one for simplicity.

View file

@ -1,4 +1,4 @@
# Release 0.3 {#sec-release-0.3} # Release 0.3 {#sec-release-0-3}
Release 0.3 had to come out before I wanted it to due to Neovim 0.9 dropping Release 0.3 had to come out before I wanted it to due to Neovim 0.9 dropping
into nixpkgs-unstable. The Treesitter changes have prompted a Treesitter rework, into nixpkgs-unstable. The Treesitter changes have prompted a Treesitter rework,
@ -7,7 +7,7 @@ those are downstreamed from the original repository. The feature requests that
was originally planned for 0.3 have been moved to 0.4, which should come out was originally planned for 0.3 have been moved to 0.4, which should come out
soon. soon.
## Changelog {#sec-release-0.3-changelog} ## Changelog {#sec-release-0-3-changelog}
- We have transitioned to flake-parts, from flake-utils to extend the - We have transitioned to flake-parts, from flake-utils to extend the
flexibility of this flake. This means the flake structure is different than flexibility of this flake. This means the flake structure is different than
@ -39,7 +39,7 @@ soon.
[discourse]: https://discourse.nixos.org/t/psa-if-you-are-on-unstable-try-out-nvim-treesitter-withallgrammars/23321?u=snowytrees [discourse]: https://discourse.nixos.org/t/psa-if-you-are-on-unstable-try-out-nvim-treesitter-withallgrammars/23321?u=snowytrees
- Treesitter grammars are now configurable with - Treesitter grammars are now configurable with
[](#opt-vim.treesitter.grammars). Utilizes the nixpkgs `nvim-treesitter` {option}`vim.treesitter.grammars`. Utilizes the nixpkgs `nvim-treesitter`
plugin rather than a custom input in order to take advantage of build support plugin rather than a custom input in order to take advantage of build support
of pinned versions. See [discourse] for more information. Packages can be of pinned versions. See [discourse] for more information. Packages can be
found under the `pkgs.vimPlugins.nvim-treesitter.builtGrammars` attribute. found under the `pkgs.vimPlugins.nvim-treesitter.builtGrammars` attribute.
@ -50,20 +50,20 @@ soon.
- A new section has been added for language support: `vim.languages.<language>`. - A new section has been added for language support: `vim.languages.<language>`.
- The options `enableLSP` [](#opt-vim.languages.enableTreesitter), etc. will - The options `enableLSP` {option}`vim.languages.enableTreesitter`, etc. will
enable the respective section for all languages that have been enabled. enable the respective section for all languages that have been enabled.
- All LSP languages have been moved here - All LSP languages have been moved here
- `plantuml` and `markdown` have been moved here - `plantuml` and `markdown` have been moved here
- A new section has been added for `html`. The old - A new section has been added for `html`. The old
`vim.treesitter.autotagHtml` can be found at `vim.treesitter.autotagHtml` can be found at
[](#opt-vim.languages.html.treesitter.autotagHtml). {option}`vim.languages.html.treesitter.autotagHtml`.
- `vim.git.gitsigns.codeActions` has been added, allowing you to turn on - `vim.git.gitsigns.codeActions` has been added, allowing you to turn on
Gitsigns' code actions. Gitsigns' code actions.
- Removed the plugins document in the docs. Was too unwieldy to keep updated. - Removed the plugins document in the docs. Was too unwieldy to keep updated.
- `vim.visual.lspkind` has been moved to [](#opt-vim.lsp.lspkind.enable) - `vim.visual.lspkind` has been moved to {option}`vim.lsp.lspkind.enable`
- Improved handling of completion formatting. When setting - Improved handling of completion formatting. When setting
`vim.autocomplete.sources`, can also include optional menu mapping. And can `vim.autocomplete.sources`, can also include optional menu mapping. And can
@ -74,7 +74,7 @@ soon.
by using `null` rather than `""` now. by using `null` rather than `""` now.
- Transparency has been made optional and has been disabled by default. - Transparency has been made optional and has been disabled by default.
[](#opt-vim.theme.transparent) option can be used to enable or disable {option}`vim.theme.transparent` option can be used to enable or disable
transparency for your configuration. transparency for your configuration.
- Fixed deprecated configuration method for Tokyonight, and added new style - Fixed deprecated configuration method for Tokyonight, and added new style

View file

@ -1,4 +1,4 @@
# Release 0.4 {#sec-release-0.4} # Release 0.4 {#sec-release-0-4}
Following the release of v0.3, I have decided to release v0.4 with a massive new Following the release of v0.3, I have decided to release v0.4 with a massive new
change: customizable keybinds. As of the 0.4 release, keybinds will no longer be change: customizable keybinds. As of the 0.4 release, keybinds will no longer be
@ -12,7 +12,7 @@ as `lazygit` integration and the new experimental Lua loader of Neovim 0.9
thanks to our awesome contributors who made this update possible during my thanks to our awesome contributors who made this update possible during my
absence. absence.
## Changelog {#sec-release-0.4-changelog} ## Changelog {#sec-release-0-4-changelog}
[n3oney](https://github.com/n3oney): [n3oney](https://github.com/n3oney):

View file

@ -1,8 +1,6 @@
# Release 0.5 {#sec-release-0.5} # Release 0.5 {#sec-release-0-5}
Release notes for release 0.5 ## Changelog {#sec-release-0-5-changelog}
## Changelog {#sec-release-0.5-changelog}
[vagahbond](https://github.com/vagahbond): [vagahbond](https://github.com/vagahbond):
@ -17,14 +15,14 @@ Release notes for release 0.5
- Fixed a bug where cmp's close and scrollDocs mappings wasn't working - Fixed a bug where cmp's close and scrollDocs mappings wasn't working
- Streamlined and simplified extra plugin API with the addition of - Streamlined and simplified extra plugin API with the addition of
[](#opt-vim.extraPlugins) {option}`vim.extraPlugins`
- Allow using command names in place of LSP packages to avoid automatic - Allow using command names in place of LSP packages to avoid automatic
installation installation
- Add lua LSP and Treesitter support, and neodev.nvim plugin support - Add lua LSP and Treesitter support, and neodev.nvim plugin support
- Add [](#opt-vim.lsp.mappings.toggleFormatOnSave) keybind - Add {option}`vim.lsp.mappings.toggleFormatOnSave` keybind
[amanse](https://github.com/amanse): [amanse](https://github.com/amanse):
@ -52,10 +50,10 @@ Release notes for release 0.5
- Added GitHub Copilot to nvim-cmp completion sources. - Added GitHub Copilot to nvim-cmp completion sources.
- Added [](#opt-vim.ui.borders.enable) for global and individual plugin border - Added {option}`vim.ui.borders.enable` for global and individual plugin border
configuration. configuration.
- LSP integrated breadcrumbs with [](#opt-vim.ui.breadcrumbs.enable) through - LSP integrated breadcrumbs with {option}`vim.ui.breadcrumbs.enable` through
nvim-navic nvim-navic
- LSP navigation helper with nvim-navbuddy, depends on nvim-navic (automatically - LSP navigation helper with nvim-navbuddy, depends on nvim-navic (automatically
@ -66,14 +64,14 @@ Release notes for release 0.5
- Fixed mismatching Zig language description - Fixed mismatching Zig language description
- Added support for `statix` and `deadnix` through - Added support for `statix` and `deadnix` through
[](#opt-vim.languages.nix.extraDiagnostics.types) {option}`vim.languages.nix.extraDiagnostics.types`
- Added `lsp_lines` plugin for showing diagnostic messages - Added `lsp_lines` plugin for showing diagnostic messages
- Added a configuration option for choosing the leader key - Added a configuration option for choosing the leader key
- The package used for neovim is now customizable by the user, using - The package used for neovim is now customizable by the user, using
[](#opt-vim.package). For best results, always use an unwrapped package {option}`vim.package`. For best results, always use an unwrapped package
- Added highlight-undo plugin for highlighting undo/redo targets - Added highlight-undo plugin for highlighting undo/redo targets

View file

@ -1,4 +1,4 @@
# Release 0.6 {#sec-release-0.6} # Release 0.6 {#sec-release-0-6}
Release notes for release 0.6 Release notes for release 0.6
@ -41,14 +41,14 @@ end
vim.api.nvim_set_keymap('n', '<leader>a', ':lua camelToSnake()<CR>', { noremap = true, silent = true }) vim.api.nvim_set_keymap('n', '<leader>a', ':lua camelToSnake()<CR>', { noremap = true, silent = true })
``` ```
## Changelog {#sec-release-0.6-changelog} ## Changelog {#sec-release-0-6-changelog}
[ksonj](https://github.com/ksonj): [ksonj](https://github.com/ksonj):
- Added Terraform language support. - Added Terraform language support.
- Added `ChatGPT.nvim`, which can be enabled with - Added `ChatGPT.nvim`, which can be enabled with
[](#opt-vim.assistant.chatgpt.enable). Do keep in mind that this option {option}`vim.assistant.chatgpt.enable`. Do keep in mind that this option
requires `OPENAI_API_KEY` environment variable to be set. requires `OPENAI_API_KEY` environment variable to be set.
[donnerinoern](https://github.com/donnerinoern): [donnerinoern](https://github.com/donnerinoern):
@ -95,7 +95,7 @@ vim.api.nvim_set_keymap('n', '<leader>a', ':lua camelToSnake()<CR>', { noremap =
and also has been removed. and also has been removed.
- `which-key.nvim` categories can now be customized through - `which-key.nvim` categories can now be customized through
[vim.binds.whichKey.register](#opt-vim.binds.whichKey.register) [vim.binds.whichKey.register](./options.html#option-vim-binds-whichKey-register)
- Added `magick` to `vim.luaPackages` for `image.nvim`. - Added `magick` to `vim.luaPackages` for `image.nvim`.
@ -125,10 +125,10 @@ vim.api.nvim_set_keymap('n', '<leader>a', ':lua camelToSnake()<CR>', { noremap =
- Lualine module now allows customizing `always_divide_middle`, `ignore_focus` - Lualine module now allows customizing `always_divide_middle`, `ignore_focus`
and `disabled_filetypes` through the new options: and `disabled_filetypes` through the new options:
[vim.statusline.lualine.alwaysDivideMiddle](#opt-vim.statusline.lualine.alwaysDivideMiddle), [vim.statusline.lualine.alwaysDivideMiddle](./options.html#option-vim-statusline-lualine-alwaysDivideMiddle),
[vim.statusline.lualine.ignoreFocus](#opt-vim.statusline.lualine.ignoreFocus) [vim.statusline.lualine.ignoreFocus](./options.html#option-vim-statusline-lualine-ignoreFocus)
and and
[vim.statusline.lualine.disabledFiletypes](#opt-vim.statusline.lualine.disabledFiletypes). [vim.statusline.lualine.disabledFiletypes](./options.html#option-vim-statusline-lualine-disabledFiletypes).
- Updated all plugin inputs to their latest versions (**21.04.2024**) - this - Updated all plugin inputs to their latest versions (**21.04.2024**) - this
brought minor color changes to the Catppuccin theme. brought minor color changes to the Catppuccin theme.
@ -159,10 +159,10 @@ vim.api.nvim_set_keymap('n', '<leader>a', ':lua camelToSnake()<CR>', { noremap =
arguments to take `luaBefore`, `luaConfig` and `luaAfter` as strings, which arguments to take `luaBefore`, `luaConfig` and `luaAfter` as strings, which
are then concatted inside a lua block. are then concatted inside a lua block.
- Added [](#opt-vim.luaConfigPre) and [](#opt-vim.luaConfigPost) for inserting - Added {option}`vim.luaConfigPre` and {option} `vim-luaConfigPost` for
verbatim Lua configuration before and after the resolved Lua DAG respectively. inserting verbatim Lua configuration before and after the resolved Lua DAG
Both of those options take strings as the type, so you may read the contents respectively. Both of those options take strings as the type, so you may read
of a Lua file from a given path. the contents of a Lua file from a given path.
- Added `vim.spellchecking.ignoredFiletypes` and - Added `vim.spellchecking.ignoredFiletypes` and
`vim.spellChecking.programmingWordlist.enable` for ignoring certain filetypes `vim.spellChecking.programmingWordlist.enable` for ignoring certain filetypes
@ -172,12 +172,12 @@ vim.api.nvim_set_keymap('n', '<leader>a', ':lua camelToSnake()<CR>', { noremap =
- Exposed `withRuby`, `withNodeJs`, `withPython3`, and `python3Packages` from - Exposed `withRuby`, `withNodeJs`, `withPython3`, and `python3Packages` from
the `makeNeovimConfig` function under their respective options. the `makeNeovimConfig` function under their respective options.
- Added [](#opt-vim.extraPackages) for appending additional packages to the - Added {option}`vim.extraPackages` for appending additional packages to the
wrapper PATH, making said packages available while inside the Neovim session. wrapper PATH, making said packages available while inside the Neovim session.
- Made Treesitter options configurable, and moved treesitter-context to - Made Treesitter options configurable, and moved treesitter-context to
`setupOpts` while it is enabled. `setupOpts` while it is enabled.
- Added [](#opt-vim.notify.nvim-notify.setupOpts.render) which takes either a - Added {option}`vim.notify.nvim-notify.setupOpts.render` which takes either a
string of enum, or a Lua function. The default is "compact", but you may string of enum, or a Lua function. The default is "compact", but you may
change it according to nvim-notify documentation. change it according to nvim-notify documentation.

View file

@ -1,4 +1,4 @@
# Release 0.7 {#sec-release-0.7} # Release 0.7 {#sec-release-0-7}
Release notes for release 0.7 Release notes for release 0.7
@ -98,7 +98,7 @@ options that were under `vim` as convenient shorthands for `vim.o.*` options.
::: {.warning} ::: {.warning}
As v0.7 features the addition of [](#opt-vim.options), those options are now As v0.7 features the addition of {option}`vim.options`, those options are now
considered as deprecated. You should migrate to the appropriate options in the considered as deprecated. You should migrate to the appropriate options in the
`vim.options` submodule. `vim.options` submodule.
@ -108,14 +108,14 @@ The changes are, in no particular order:
- `colourTerm`, `mouseSupport`, `cmdHeight`, `updateTime`, `mapTime`, - `colourTerm`, `mouseSupport`, `cmdHeight`, `updateTime`, `mapTime`,
`cursorlineOpt`, `splitBelow`, `splitRight`, `autoIndent` and `wordWrap` have `cursorlineOpt`, `splitBelow`, `splitRight`, `autoIndent` and `wordWrap` have
been mapped to their [](#opt-vim.options) equivalents. Please see the module been mapped to their {option}`vim.options` equivalents. Please see the module
definition for the updated options. definition for the updated options.
- `tabWidth` has been **removed** as it lead to confusing behaviour. You can - `tabWidth` has been **removed** as it lead to confusing behaviour. You can
replicate the same functionality by setting `shiftwidth`, `tabstop` and replicate the same functionality by setting `shiftwidth`, `tabstop` and
`softtabstop` under `vim.options` as you see fit. `softtabstop` under `vim.options` as you see fit.
## Changelog {#sec-release-0.7-changelog} ## Changelog {#sec-release-0-7-changelog}
[ItsSorae](https://github.com/ItsSorae): [ItsSorae](https://github.com/ItsSorae):
@ -125,7 +125,7 @@ The changes are, in no particular order:
[frothymarrow](https://github.com/frothymarrow): [frothymarrow](https://github.com/frothymarrow):
- Modified type for - Modified type for
[](#opt-vim.visuals.fidget-nvim.setupOpts.progress.display.overrides) from {option}`vim.visuals.fidget-nvim.setupOpts.progress.display.overrides` from
`anything` to a `submodule` for better type checking. `anything` to a `submodule` for better type checking.
- Fix null `vim.lsp.mappings` generating an error and not being filtered out. - Fix null `vim.lsp.mappings` generating an error and not being filtered out.
@ -134,7 +134,7 @@ The changes are, in no particular order:
group for `Normal`, `NormalFloat`, `LineNr`, `SignColumn` and optionally group for `Normal`, `NormalFloat`, `LineNr`, `SignColumn` and optionally
`NvimTreeNormal` to `none`. `NvimTreeNormal` to `none`.
- Fix [](#opt-vim.ui.smartcolumn.setupOpts.custom_colorcolumn) using the wrong - Fix {option}`vim.ui.smartcolumn.setupOpts.custom_colorcolumn` using the wrong
type `int` instead of the expected type `string`. type `int` instead of the expected type `string`.
[horriblename](https://github.com/horriblename): [horriblename](https://github.com/horriblename):
@ -170,7 +170,7 @@ The changes are, in no particular order:
- Add [ocaml-lsp] support - Add [ocaml-lsp] support
- Fix misspelled "Emacs" - Fix "Emac" typo
- Add [new-file-template.nvim] to automatically fill new file contents using - Add [new-file-template.nvim] to automatically fill new file contents using
templates templates
@ -216,18 +216,18 @@ The changes are, in no particular order:
- Remove `autopairs.type`, and rename `autopairs.enable` to - Remove `autopairs.type`, and rename `autopairs.enable` to
`autopairs.nvim-autopairs.enable`. The new `autopairs.nvim-autopairs.enable`. The new
[](#opt-vim.autopairs.nvim-autopairs.enable) supports `setupOpts` format by {option}`vim.autopairs.nvim-autopairs.enable` supports `setupOpts` format by
default. default.
- Refactor of `nvim-cmp` and completion related modules - Refactor of `nvim-cmp` and completion related modules
- Remove `autocomplete.type` in favor of per-plugin enable options such as - Remove `autocomplete.type` in favor of per-plugin enable options such as
[](#opt-vim.autocomplete.nvim-cmp.enable). {option}`vim.autocomplete.nvim-cmp.enable`.
- Deprecate legacy Vimsnip in favor of Luasnip, and integrate - Deprecate legacy Vimsnip in favor of Luasnip, and integrate
friendly-snippets for bundled snippets. [](#opt-vim.snippets.luasnip.enable) friendly-snippets for bundled snippets.
can be used to toggle Luasnip. {option}`vim.snippets.luasnip.enable` can be used to toggle Luasnip.
- Add sorting function options for completion sources under - Add sorting function options for completion sources under
[](#opt-vim.autocomplete.nvim-cmp.setupOpts.sorting.comparators) {option}`vim.autocomplete.nvim-cmp.setupOpts.sorting.comparators`
- Add C# support under `vim.languages.csharp`, with support for both - Add C# support under `vim.languages.csharp`, with support for both
omnisharp-roslyn and csharp-language-server. omnisharp-roslyn and csharp-language-server.
@ -297,12 +297,12 @@ The changes are, in no particular order:
Lualine. Only `vim.ui.breadcrumbs.lualine.winbar` is supported for the time Lualine. Only `vim.ui.breadcrumbs.lualine.winbar` is supported for the time
being. being.
- [](#opt-vim.ui.breadcrumbs.lualine.winbar.enable) has been added to allow - {option}`vim.ui.breadcrumbs.lualine.winbar.enable` has been added to allow
controlling the default behaviour of the `nvim-navic` component on Lualine, controlling the default behaviour of the `nvim-navic` component on Lualine,
which used to occupy `winbar.lualine_c` as long as breadcrumbs are enabled. which used to occupy `winbar.lualine_c` as long as breadcrumbs are enabled.
- `vim.ui.breadcrumbs.alwaysRender` has been renamed to - `vim.ui.breadcrumbs.alwaysRender` has been renamed to
[](#opt-vim.ui.breadcrumbs.lualine.winbar.alwaysRender) to be conform to the {option}`vim.ui.breadcrumbs.lualine.winbar.alwaysRender` to be conform to
new format. the new format.
- Add [basedpyright](https://github.com/detachhead/basedpyright) as a Python LSP - Add [basedpyright](https://github.com/detachhead/basedpyright) as a Python LSP
server and make it default. server and make it default.
@ -310,10 +310,10 @@ The changes are, in no particular order:
- Add [python-lsp-server](https://github.com/python-lsp/python-lsp-server) as an - Add [python-lsp-server](https://github.com/python-lsp/python-lsp-server) as an
additional Python LSP server. additional Python LSP server.
- Add [](#opt-vim.options) to set `vim.o` values in in your nvf configuration - Add {option}`vim.options` to set `vim.o` values in in your nvf configuration
without using additional Lua. See option documentation for more details. without using additional Lua. See option documentation for more details.
- Add [](#opt-vim.dashboard.dashboard-nvim.setupOpts) to allow user - Add {option}`vim.dashboard.dashboard-nvim.setupOpts` to allow user
configuration for [dashboard.nvim](https://github.com/nvimdev/dashboard-nvim) configuration for [dashboard.nvim](https://github.com/nvimdev/dashboard-nvim)
- Update `lualine.nvim` input and add missing themes: - Update `lualine.nvim` input and add missing themes:
@ -321,7 +321,7 @@ The changes are, in no particular order:
- Adds `ayu`, `gruvbox_dark`, `iceberg`, `moonfly`, `onedark`, - Adds `ayu`, `gruvbox_dark`, `iceberg`, `moonfly`, `onedark`,
`powerline_dark` and `solarized_light` themes. `powerline_dark` and `solarized_light` themes.
- Add [](#opt-vim.spellcheck.extraSpellWords) to allow adding arbitrary - Add {option}`vim.spellcheck.extraSpellWords` to allow adding arbitrary
spellfiles to Neovim's runtime with ease. spellfiles to Neovim's runtime with ease.
- Add combined nvf configuration (`config.vim`) into the final package's - Add combined nvf configuration (`config.vim`) into the final package's
@ -375,9 +375,9 @@ The changes are, in no particular order:
[nezia1](https://github.com/nezia1): [nezia1](https://github.com/nezia1):
- Add [biome](https://github.com/biomejs/biome) support for Typescript, CSS and - Add [biome](https://github.com/biomejs/biome) support for Typescript, CSS and
Svelte. Enable them via [](#opt-vim.languages.ts.format.type), Svelte. Enable them via {option}`vim.languages.ts.format.type`,
[](#opt-vim.languages.css.format.type) and {option}`vim.languages.css.format.type` and
[](#opt-vim.languages.svelte.format.type) respectively. {option}`vim.languages.svelte.format.type` respectively.
- Replace [nixpkgs-fmt](https://github.com/nix-community/nixpkgs-fmt) with - Replace [nixpkgs-fmt](https://github.com/nix-community/nixpkgs-fmt) with
[nixfmt](https://github.com/NixOS/nixfmt) (nixfmt-rfc-style). [nixfmt](https://github.com/NixOS/nixfmt) (nixfmt-rfc-style).

View file

@ -1,4 +1,4 @@
# Release 0.8 {#sec-release-0.8} # Release 0.8 {#sec-release-0-8}
## Breaking changes ## Breaking changes
@ -21,13 +21,19 @@
- `vim.useSystemClipboard` has been deprecated as a part of removing most - `vim.useSystemClipboard` has been deprecated as a part of removing most
top-level convenience options, and should instead be configured in the new top-level convenience options, and should instead be configured in the new
module interface. You may set [](#opt-vim.clipboard.registers) appropriately module interface. You may set {option}`vim.clipboard.registers` appropriately
to configure Neovim to use the system clipboard. to configure Neovim to use the system clipboard.
- Changed which-key group used for gitsigns from `<leader>g` to `<leader>h` to - Changed which-key group used for gitsigns from `<leader>g` to `<leader>h` to
align with the "hunks" themed mapping and avoid conflict with the new [neogit] align with the "hunks" themed mapping and avoid conflict with the new [neogit]
group. group.
- LSP keybinds and related plugin integrations are now attached in an LspAttach
autocmd event. If you were calling `default_on_attach()` in your LSP setup you
can remove them now.
## Changelog {#sec-release-0-8-changelog}
[NotAShelf](https://github.com/notashelf): [NotAShelf](https://github.com/notashelf):
[typst-preview.nvim]: https://github.com/chomosuke/typst-preview.nvim [typst-preview.nvim]: https://github.com/chomosuke/typst-preview.nvim
@ -48,16 +54,16 @@
- Add [render-markdown.nvim] under - Add [render-markdown.nvim] under
`languages.markdown.extensions.render-markdown-nvim`. `languages.markdown.extensions.render-markdown-nvim`.
- Implement [](#opt-vim.git.gitsigns.setupOpts) for user-specified setup table - Implement {option}`vim.git.gitsigns.setupOpts` for user-specified setup table
in gitsigns configuration. in gitsigns configuration.
- [](#opt-vim.options.mouse) no longer compares values to an enum of available - {option}`vim.options.mouse` no longer compares values to an enum of available
mouse modes. This means you can provide any string without the module system mouse modes. This means you can provide any string without the module system
warning you that it is invalid. Do keep in mind that this value is no longer warning you that it is invalid. Do keep in mind that this value is no longer
checked, so you will be responsible for ensuring its validity. checked, so you will be responsible for ensuring its validity.
- Deprecate `vim.enableEditorconfig` in favor of - Deprecate `vim.enableEditorconfig` in favor of
[](#opt-vim.globals.editorconfig). {option}`vim.globals.editorconfig`.
- Deprecate rnix-lsp as it has been abandoned and archived upstream. - Deprecate rnix-lsp as it has been abandoned and archived upstream.
@ -66,10 +72,9 @@
your Editorconfig configuration, or use an autocommand to set indentation your Editorconfig configuration, or use an autocommand to set indentation
values for buffers with the Nix filetype. values for buffers with the Nix filetype.
- Add [](#opt-vim.lsp.lightbulb.autocmd.enable) for manually managing the - Add {option}`vim.lsp.lightbulb.autocmd.enable` for manually managing the
previously managed lightbulb autocommand. previously managed lightbulb autocommand.
- A warning will occur if {option} vim-lsp-lightbulb-autocmd-enable) and
- A warning will occur if [](#opt-vim.lsp.lightbulb.autocmd.enable) and
`vim.lsp.lightbulb.setupOpts.autocmd.enabled` are both set at the same time. `vim.lsp.lightbulb.setupOpts.autocmd.enabled` are both set at the same time.
Pick only one. Pick only one.
@ -80,7 +85,7 @@
- Add [yazi.nvim] as a companion plugin for Yazi, the terminal file manager. - Add [yazi.nvim] as a companion plugin for Yazi, the terminal file manager.
- Add [](#opt-vim.autocmds) and [](#opt-vim.augroups) to allow declaring - Add {option}`vim.autocmds` and {option}`vim-augroups` to allow declaring
autocommands via Nix. autocommands via Nix.
- Fix plugin `setupOpts` for yanky.nvim and assert if shada is configured as a - Fix plugin `setupOpts` for yanky.nvim and assert if shada is configured as a
@ -102,7 +107,7 @@
`vim.utility.oil-nvim`. `vim.utility.oil-nvim`.
- Add `vim.diagnostics` to interact with Neovim's diagnostics module. Available - Add `vim.diagnostics` to interact with Neovim's diagnostics module. Available
options for `vim.diagnostic.config()` can now be customized through the options for `vim.diagnostic.config()` can now be customized through the
[](#opt-vim.diagnostics.config) in nvf. {option}`vim.diagnostics.config` in nvf.
- Add `vim.clipboard` module for easily managing Neovim clipboard providers and - Add `vim.clipboard` module for easily managing Neovim clipboard providers and
relevant packages in a simple UI. relevant packages in a simple UI.
@ -111,6 +116,14 @@
- Add [hunk.nvim], Neovim plugin & tool for splitting diffs in Neovim. Available - Add [hunk.nvim], Neovim plugin & tool for splitting diffs in Neovim. Available
as `vim.git.hunk-nvim` as `vim.git.hunk-nvim`
- Move `crates.nvim` into `languages.rust.extensions and support` `setupOpts`
for the plugin. Deprecates the top level "crates" option in `languages.rust`.
[sjcobb2022](https://github.com/sjcobb2022):
- Migrate all current lsp configurations to `vim.lsp.server` and remove internal
dependency on `nvim-lspconfig`
[amadaluzia](https://github.com/amadaluzia): [amadaluzia](https://github.com/amadaluzia):
[haskell-tools.nvim]: https://github.com/MrcJkb/haskell-tools.nvim [haskell-tools.nvim]: https://github.com/MrcJkb/haskell-tools.nvim
@ -130,6 +143,11 @@
- Moved code setting `additionalRuntimePaths` and `enableLuaLoader` out of - Moved code setting `additionalRuntimePaths` and `enableLuaLoader` out of
`luaConfigPre`'s default to prevent being overridden `luaConfigPre`'s default to prevent being overridden
- Use conform over custom autocmds for LSP format on save - Use conform over custom autocmds for LSP format on save
- Move LSP keybinds and other related plugin integrations into an LspAttach
event.
- Allow multiple formatters in language modules.
- Fixed `prettier` in astro and svelte, and removed `prettierd` due to high
complexity that would be needed to support it.
[diniamo](https://github.com/diniamo): [diniamo](https://github.com/diniamo):
@ -191,7 +209,7 @@
- Add [fzf-lua](https://github.com/ibhagwan/fzf-lua) in `vim.fzf-lua` - Add [fzf-lua](https://github.com/ibhagwan/fzf-lua) in `vim.fzf-lua`
- Add [rainbow-delimiters](https://github.com/HiPhish/rainbow-delimiters.nvim) - Add [rainbow-delimiters](https://github.com/HiPhish/rainbow-delimiters.nvim)
in `vim.visuals.rainbow-delimiters` in `vim.visuals.rainbow-delimiters`
- Add options to define highlights under [](#opt-vim.highlight) - Add options to define highlights under {option}`vim.highlight`
[kaktu5](https://github.com/kaktu5): [kaktu5](https://github.com/kaktu5):
@ -207,8 +225,8 @@
[thamenato](https://github.com/thamenato): [thamenato](https://github.com/thamenato):
[ruff]: (https://github.com/astral-sh/ruff) [ruff]: https://github.com/astral-sh/ruff
[cue]: (https://cuelang.org/) [cue]: https://cuelang.org/
- Add [ruff] as a formatter option in `vim.languages.python.format.type`. - Add [ruff] as a formatter option in `vim.languages.python.format.type`.
- Add [cue] support under `vim.languages.cue`. - Add [cue] support under `vim.languages.cue`.
@ -284,6 +302,13 @@
- Fix [blink.cmp] breaking when built-in sources were modified. - Fix [blink.cmp] breaking when built-in sources were modified.
- Fix [conform.nvim] not allowing disabling formatting on and after save. Use - Fix [conform.nvim] not allowing disabling formatting on and after save. Use
`null` value to disable them if conform is enabled. `null` value to disable them if conform is enabled.
- Add [markdown-oxide](https://github.com/Feel-ix-343/markdown-oxide) option to
markdown language module.
- Fix Helm-YAML language module integration. YAML diagnostics will now remain in
`helmfile`s when both are enabled.
- Fix YAML language module not activating LSP keybinds if the Helm language
module was also enabled.
- Fix `json` language module (default) language server not activating.
[TheColorman](https://github.com/TheColorman): [TheColorman](https://github.com/TheColorman):
@ -319,6 +344,7 @@
- Add global function `nvf_lint` under - Add global function `nvf_lint` under
`vim.diagnostics.nvim-lint.lint_function`. `vim.diagnostics.nvim-lint.lint_function`.
- Deprecate `vim.scrollOffset` in favor of `vim.options.scrolloff`. - Deprecate `vim.scrollOffset` in favor of `vim.options.scrolloff`.
- Fix `svelte-language-server` not reloading .js/.ts files on change.
[Sc3l3t0n](https://github.com/Sc3l3t0n): [Sc3l3t0n](https://github.com/Sc3l3t0n):
@ -381,7 +407,7 @@
[aionoid](https://github.com/aionoid): [aionoid](https://github.com/aionoid):
[avante-nvim]: https://github.com/yetone/avante.nvim [avante.nvim]: https://github.com/yetone/avante.nvim
- Fix [render-markdown.nvim] file_types option type to list, to accept merging. - Fix [render-markdown.nvim] file_types option type to list, to accept merging.
- Add [avante.nvim] plugin under `vim.assistant.avante-nvim`. - Add [avante.nvim] plugin under `vim.assistant.avante-nvim`.
@ -389,9 +415,12 @@
[poz](https://poz.pet): [poz](https://poz.pet):
[everforest]: https://github.com/sainnhe/everforest [everforest]: https://github.com/sainnhe/everforest
[oil]: https://github.com/stevearc/oil.nvim
[oil-git-status]: https://github.com/refractalize/oil-git-status.nvim
- Fix gitsigns null-ls issue. - Fix gitsigns null-ls issue.
- Add [everforest] theme support. - Add [everforest] theme support.
- Add [oil-git-status] support to [oil] module.
[Haskex](https://github.com/haskex): [Haskex](https://github.com/haskex):
@ -479,13 +508,8 @@
- fix broken `neorg` grammars - fix broken `neorg` grammars
- remove obsolete warning in the `otter` module - remove obsolete warning in the `otter` module
- add mainProgram attribute to vala language server wrapper
[Cool-Game-Dev](https://github.com/Cool-Game-Dev): - fix `crates-nvim`'s completions by using the in-program lsp
[nvim-biscuits]: https://github.com/code-biscuits/nvim-biscuits
- Add [nvim-biscuits] to show block context. Available at
`vim.utility.nvim-biscuits`.
[JManch](https://github.com/JManch): [JManch](https://github.com/JManch):
@ -493,6 +517,56 @@
`autocomplete.nvim-cmp.enable` was disabled and `autocomplete.nvim-cmp.enable` was disabled and
`autocomplete.nvim-cmp.sources` had not been modified. `autocomplete.nvim-cmp.sources` had not been modified.
[Poseidon](https://github.com/poseidon-rises):
[nvim-biscuits]: https://github.com/code-biscuits/nvim-biscuits
[just-lsp]: https://github.com/terror/just-lsp
[roslyn-ls]: https://github.com/dotnet/vscode-csharp
[jsonls]: https://github.com/microsoft/vscode/tree/1.101.2/extensions/json-language-features/server
[jsonfmt]: https://github.com/caarlos0/jsonfmt
[superhtml]: https://github.com/kristoff-it/superhtml
[htmlHINT]: https://github.com/htmlhint/HTMLHint
[qmk-nvim]: https://github.com/codethread/qmk.nvim
[qmlls]: https://doc.qt.io/qt-6/qtqml-tooling-qmlls.html
[qmlformat]: https://doc.qt.io/qt-6/qtqml-tooling-qmlformat.html
- Add [nvim-biscuits] support under `vim.utility.nvim-biscuits`.
- Add just support under `vim.languages.just` using [just-lsp].
- Add [roslyn-ls] to the `vim.languages.csharp` module.
- Add JSON support under `vim.languages.json` using [jsonls] and [jsonfmt].
- Add advanced HTML support under `vim.languages.html` using [superhtml] and
[htmlHINT].
- Add QMK support under `vim.utility.qmk-nvim` via [qmk-nvim].
- Add QML support under `vim.languages.qml` using [qmlls] and [qmlformat].
[Morsicus](https://github.com/Morsicus):
- Add [EEx Treesitter Grammar](https://github.com/connorlay/tree-sitter-eex) for
Elixir
- Add
[HEEx Treesitter Grammar](https://github.com/phoenixframework/tree-sitter-heex)
for Elixir
[diced](https://github.com/diced):
- Fixed `typescript` treesitter grammar not being included by default.
[valterschutz](https://github.com/valterschutz):
[ruff]: https://github.com/astral-sh/ruff
- Add [ruff-fix] as a formatter option in `vim.languages.python.format.type`.
[gmvar](https://github.com/gmvar):
[harper-ls]: https://github.com/Automattic/harper
- Add [harper-ls] to the `vim.lsp` module.
[derethil](https://github.com/derethil):
- Fix `vim.lazy.plugins.<name>.enabled` Lua evaluation.
[Jules](https://github.com/jules-sommer): [Jules](https://github.com/jules-sommer):
[nvim-highlight-colors]: https://github.com/brenoprata10/nvim-highlight-colors [nvim-highlight-colors]: https://github.com/brenoprata10/nvim-highlight-colors
@ -511,6 +585,32 @@
- Add inline typst concealing support under `vim.languages.typst` using - Add inline typst concealing support under `vim.languages.typst` using
[typst-concealer]. [typst-concealer].
[KrappRamiro](https://github.com/KrappRamiro):
[phaazon/hop.nvim]: https://github.com/hadronized/hop.nvim
[smoka7/hop.nvim]: https://github.com/smoka7/hop.nvim
- Migrate [phaazon/hop.nvim] to [smoka7/hop.nvim]
[simon-wg](https://github.com/simon-wg):
- Update `python` language module to use correct lsp binary.
- Fix `python` pyright and basedpyright language servers not using default on
attach behavior.
[critical](https://github.com/critical):
[mellow.nvim]: https://github.com/mellow-theme/mellow.nvim
- Add [mellow.nvim] plugin for vim and lualine theme support
[valyntyler](https://github.com/valyntyler):
[emmet-ls]: https://github.com/aca/emmet-ls
- Enable `languages.ts.format` for `.js` files
- Add [emmet-ls] to `html.lsp.servers`
[axelbdt](https://github.com/axelbdt): [axelbdt](https://github.com/axelbdt):
[neocodeium]: https://github.com/monkoose/neocodeium [neocodeium]: https://github.com/monkoose/neocodeium

View file

@ -0,0 +1,154 @@
# Release 0.9 {#sec-release-0-9}
## Breaking changes
- Nixpkgs has merged a fully incompatible rewrite of
`vimPlugins.nvim-treesitter`. Namely, it changes from the frozen `master`
branch to the new main branch. This change removes incremental selections, so
it is no longer available.
- [obsidian.nvim] now uses a maintained fork which has removed the `dir`
setting. Use `workspaces` instead:
```nix
{
workspaces = [
{
name = "any-string";
path = "~/old/dir/path/value";
}
];
}
```
Some other settings and commands are now deprecated but are still supported.
- The `setupOpts.mappings` options were also removed. Use the built-in Neovim
settings (nvf's {option}`vim.keymaps`)
## Changelog {#sec-release-0-9-changelog}
[taylrfnt](https://github.com/taylrfnt)
- Introduce a `darwinModule` option for Darwin users. The ergonomics of
importing a `nixosModule` into a Darwin flake were less than ideal, and when
users fork and update npins, they are prone to encountering errors like the
following:
```shell
(class: "nixos") cannot be imported into a module
evaluation that expects class "darwin".
```
[suimong](https://github.com/suimong):
- Fix `vim.tabline.nvimBufferline` where `setupOpts.options.hover` requires
`vim.opt.mousemoveevent` to be set.
[thamenato](https://github.com/thamenato):
- Attempt to adapt nvim-treesitter to (breaking) Nixpkgs changes. Some
treesitter grammars were changed to prefer `grammarPlugins` over
`builtGrammars`.
[jfeo](https://github.com/jfeo):
[ccc.nvim]: https://github.com/uga-rosa/ccc.nvim
- Added [ccc.nvim] option {option}`vim.utility.ccc.setupOpts` with the existing
hard-coded options as default values.
[Ring-A-Ding-Ding-Baby](https://github.com/Ring-A-Ding-Ding-Baby):
- Aligned `codelldb` adapter setup with [rustaceanvim]s built-in logic.
- Added `languages.rust.dap.backend` option to choose between `codelldb` and
`lldb-dap` adapters.
[Libadoxon](https://github.com/Libadoxon):
- `toggleterm` open map now also works when in terminal mode
[jtliang24](https://github.com/jtliang24):
- Updated nix language plugin to use pkgs.nixfmt instead of
pkgs.nixfmt-rfc-style
[alfarel](https://github.com/alfarelcynthesis):
[obsidian.nvim]: https://github.com/obsidian-nvim/obsidian.nvim
[blink.cmp]: https://cmp.saghen.dev/
[snacks.nvim]: https://github.com/folke/snacks.nvim
[mini.nvim]: https://nvim-mini.org/mini.nvim/
[telescope.nvim]: https://github.com/nvim-telescope/telescope.nvim
[fzf-lua]: https://github.com/ibhagwan/fzf-lua
[render-markdown.nvim]: https://github.com/MeanderingProgrammer/render-markdown.nvim
[markview.nvim]: https://github.com/OXY2DEV/markview.nvim
[which-key.nvim]: https://github.com/folke/which-key.nvim
- Upgrade [obsidian.nvim] to use a maintained fork, instead of the unmaintained
upstream.
- Various upstream improvements:
- Support [blink.cmp] and completion plugin autodetection.
- Support various pickers for prompts, including [snacks.nvim]'s
`snacks.picker`, [mini.nvim]'s `mini.pick`, [telescope.nvim], and
[fzf-lua].
- Merge commands like `ObsidianBacklinks` into `Obisidian backlinks`. The
old format is still supported by default.
- Some `setupOpts` options have changed:
- `disable_frontmatter` -> `frontmatter.enabled` (and inverted), still
supported.
- `note_frontmatter_func` -> `frontmatter.func`, still supported.
- `statusline` module is now deprecated in favour of `footer`, still
supported.
- `dir` is no longer supported, use `workspaces`:
```nix
{
workspaces = [
{
name = "any-string";
path = "~/old/dir/path/value";
}
];
}
```
- `use_advanced_uri` -> `open.use_advanced_uri`.
- Mappings are now expected to be set using the built-in Neovim APIs,
managed by `vim.keymaps` in nvf, instead of `mappings` options.
- Some option defaults have changed.
- And more.
- Automatically configure an enabled picker in the order mentioned above, if
any are enabled.
- Add integration with `snacks.image` for rendering workspace/vault assets.
- Detect if [render-markdown.nvim] or [markview.nvim] are enabled and disable
the `ui` module if so. It should work without this, but `render-markdown`'s
{command}`:healthcheck` doesn't know that.
- Remove [which-key.nvim] `<leader>o` `+Notes` description which did not
actually correspond to any keybinds.
[pyrox0](https://github.com/pyrox0):
- Added [rumdl](https://github.com/rvben/rumdl) support to `languages.markdown`
- Added [sqruff](https://github.com/quarylabs/sqruff) support to `languages.sql`
- Added [Pyrefly](https://pyrefly.org/) and [zuban](https://zubanls.com/)
support to `languages.python`
- Added TOML support via {option}`languages.toml` and the
[Tombi](https://tombi-toml.github.io/tombi/) language server, linter, and
formatter.
- Added [hlargs.nvim](https://github.com/m-demare/hlargs.nvim) support as
`visuals.hlargs-nvim`.
[Machshev](https://github.com/machshev):
- Added `ruff` and `ty` LSP support for Python under `programs.python`.
[Snoweuph](https://github.com/snoweuph)
- Added [Selenen](https://github.com/kampfkarren/selene) for more diagnostics in
`languages.lua`.
<!-- vim: set textwidth=80: -->

View file

@ -6,7 +6,7 @@ documentation, configuring **nvf** with pure Lua and using custom plugin sources
in **nvf** in this section. For general configuration tips, please see previous in **nvf** in this section. For general configuration tips, please see previous
chapters. chapters.
```{=include=} chapters ```{=include=}
tips/debugging-nvf.md tips/debugging-nvf.md
tips/offline-docs.md tips/offline-docs.md
tips/pure-lua-config.md tips/pure-lua-config.md

View file

@ -26,7 +26,7 @@ startup.
} }
``` ```
[`vim.extraPlugins`]: https://notashelf.github.io/nvf/options.html#opt-vim.extraPlugins [`vim.extraPlugins`]: ./options.html#option-vim-extraPlugins
This will fetch aerial.nvim from nixpkgs, and add it to Neovim's runtime path to This will fetch aerial.nvim from nixpkgs, and add it to Neovim's runtime path to
be loaded manually. Although for plugins that require manual setup, you are be loaded manually. Although for plugins that require manual setup, you are
@ -43,7 +43,7 @@ encouraged to use [`vim.extraPlugins`].
} }
``` ```
[custom plugins section]: https://notashelf.github.io/nvf/index.xhtml#ch-custom-plugins [custom plugins section]: ./configuring.html#ch-custom-plugins
More details on the extraPlugins API is documented in the More details on the extraPlugins API is documented in the
[custom plugins section]. [custom plugins section].

View file

@ -36,7 +36,7 @@ manner.
This will add the `nvim` directory, or rather, the _store path_ that will be This will add the `nvim` directory, or rather, the _store path_ that will be
realised after your flake gets copied to the Nix store, to Neovim's runtime realised after your flake gets copied to the Nix store, to Neovim's runtime
directory. You may now create a `lua/myconfig` directory within this nvim directory. You may now create a `lua/myconfig` directory within this nvim
directory, and call it with [](#opt-vim.luaConfigRC). directory, and call it with {option}`vim.luaConfigRC`.
```nix ```nix
{pkgs, ...}: { {pkgs, ...}: {
@ -90,7 +90,7 @@ vim.keymap.set("n", " ", "<Nop>", { silent = true, remap = false })
vim.g.mapleader = " " vim.g.mapleader = " "
``` ```
The following Nix configuration via [](#opt-vim.luaConfigRC) will allow loading The following Nix configuration via {option}`vim.luaConfigRC` will allow loading
this this
```nix ```nix
@ -105,7 +105,7 @@ this
} }
``` ```
[DAG system]: https://notashelf.github.io/nvf/index.xhtml#ch-using-dags [DAG system]: ./configuring.html#ch-using-dags
After you load your custom configuration, you may use an `init.lua` located in After you load your custom configuration, you may use an `init.lua` located in
your custom configuration directory to configure Neovim exactly as you would your custom configuration directory to configure Neovim exactly as you would

View file

@ -1,72 +0,0 @@
# Try it out {#ch-try-it-out}
Thanks to the portability of Nix, you can try out nvf without actually
installing it to your machine. Below are the commands you may run to try out
different configurations provided by this flake. As of v0.5, two specialized
configurations are provided:
- **Nix** (`packages.nix`) - Nix language server + simple utility plugins
- **Maximal** (`packages.maximal`) - Variable language servers + utility and
decorative plugins
You may try out any of the provided configurations using the `nix run` command
on a system where Nix is installed.
```sh
$ cachix use nvf # Optional: it'll save you CPU resources and time
$ nix run github:notashelf/nvf#nix # Will run the default minimal configuration
```
Do keep in mind that this is **susceptible to garbage collection** meaning that
the built outputs will be removed from your Nix store once you garbage collect.
## Using Prebuilt Configs {#sec-using-prebuilt-configs}
```bash
$ nix run github:notashelf/nvf#nix
$ nix run github:notashelf/nvf#maximal
```
### Available Configurations {#sec-available-configs}
::: {.info}
The below configurations are provided for demonstration purposes, and are
**not** designed to be installed as is. You may
#### Nix {#sec-configs-nix}
`Nix` configuration by default provides LSP/diagnostic support for Nix alongside
a set of visual and functional plugins. By running `nix run .#`, which is the
default package, you will build Neovim with this config.
```bash
$ nix run github:notashelf/nvf#nix test.nix
```
This command will start Neovim with some opinionated plugin configurations, and
is designed specifically for Nix. the `nix` configuration lets you see how a
fully configured Neovim setup _might_ look like without downloading too many
packages or shell utilities.
#### Maximal {#sec-configs-maximal}
`Maximal` is the ultimate configuration that will enable support for more
commonly used language as well as additional complementary plugins. Keep in
mind, however, that this will pull a lot of dependencies.
```bash
$ nix run github:notashelf/nvf#maximal -- test.nix
```
It uses the same configuration template with the [Nix](#sec-configs-nix)
configuration, but supports many more languages, and enables more utility,
companion or fun plugins.
::: {.warning}
Running the maximal config will download _a lot_ of packages as it is
downloading language servers, formatters, and more. If CPU time and bandwidth
are concerns, please use the default package instead.
:::

28
docs/ndg.toml Normal file
View file

@ -0,0 +1,28 @@
# NDG Configuration File
# Input directory containing markdown files
input_dir = "docs"
# Output directory for generated documentation
output_dir = "build"
# Title for the documentation
title = "NVF"
# Footer text for the documentation
footer_text = "Generated with ndg"
generate_anchors = true
# Search configuration
[search]
enable = true
highlight_code = true
tab_style = "none"
revision = "main"
# Maximum heading level to index
max_heading_level = 3
# Depth of parent categories in options TOC
options_toc_depth = 2

View file

@ -1,14 +0,0 @@
# Release Notes {#ch-release-notes}
This section lists the release notes for tagged version of **nvf** and the
current main current main branch
```{=include=} chapters
rl-0.1.md
rl-0.2.md
rl-0.3.md
rl-0.4.md
rl-0.5.md
rl-0.6.md
rl-0.7.md
```

40
flake.lock generated
View file

@ -23,11 +23,11 @@
] ]
}, },
"locked": { "locked": {
"lastModified": 1760948891, "lastModified": 1768135262,
"narHash": "sha256-TmWcdiUUaWk8J4lpjzu4gCGxWY6/Ok7mOK4fIFfBuU4=", "narHash": "sha256-PVvu7OqHBGWN16zSi6tEmPwwHQ4rLPU9Plvs8/1TUBY=",
"owner": "hercules-ci", "owner": "hercules-ci",
"repo": "flake-parts", "repo": "flake-parts",
"rev": "864599284fc7c0ba6357ed89ed5e2cd5040f0c04", "rev": "80daad04eddbbf5a4d883996a73f3f542fa437ac",
"type": "github" "type": "github"
}, },
"original": { "original": {
@ -38,11 +38,11 @@
}, },
"mnw": { "mnw": {
"locked": { "locked": {
"lastModified": 1758834834, "lastModified": 1768701608,
"narHash": "sha256-Y7IvY4F8vajZyp3WGf+KaiIVwondEkMFkt92Cr9NZmg=", "narHash": "sha256-kSvWF3Xt2HW9hmV5V7i8PqeWJIBUKmuKoHhOgj3Znzs=",
"owner": "Gerg-L", "owner": "Gerg-L",
"repo": "mnw", "repo": "mnw",
"rev": "cfbc7d1cc832e318d0863a5fc91d940a96034001", "rev": "20d63a8a1ae400557c770052a46a9840e768926b",
"type": "github" "type": "github"
}, },
"original": { "original": {
@ -51,13 +51,34 @@
"type": "github" "type": "github"
} }
}, },
"ndg": {
"inputs": {
"nixpkgs": [
"nixpkgs"
]
},
"locked": {
"lastModified": 1768214250,
"narHash": "sha256-hnBZDQWUxJV3KbtvyGW5BKLO/fAwydrxm5WHCWMQTbw=",
"owner": "feel-co",
"repo": "ndg",
"rev": "a6bd3c1ce2668d096e4fdaaa03ad7f03ba1fbca8",
"type": "github"
},
"original": {
"owner": "feel-co",
"ref": "refs/tags/v2.6.0",
"repo": "ndg",
"type": "github"
}
},
"nixpkgs": { "nixpkgs": {
"locked": { "locked": {
"lastModified": 1761880412, "lastModified": 1768875095,
"narHash": "sha256-QoJjGd4NstnyOG4mm4KXF+weBzA2AH/7gn1Pmpfcb0A=", "narHash": "sha256-dYP3DjiL7oIiiq3H65tGIXXIT1Waiadmv93JS0sS+8A=",
"owner": "nixos", "owner": "nixos",
"repo": "nixpkgs", "repo": "nixpkgs",
"rev": "a7fc11be66bdfb5cdde611ee5ce381c183da8386", "rev": "ed142ab1b3a092c4d149245d0c4126a5d7ea00b0",
"type": "github" "type": "github"
}, },
"original": { "original": {
@ -72,6 +93,7 @@
"flake-compat": "flake-compat", "flake-compat": "flake-compat",
"flake-parts": "flake-parts", "flake-parts": "flake-parts",
"mnw": "mnw", "mnw": "mnw",
"ndg": "ndg",
"nixpkgs": "nixpkgs", "nixpkgs": "nixpkgs",
"systems": "systems" "systems": "systems"
} }

View file

@ -53,11 +53,16 @@
'' ''
self.nixosModules.nvf; self.nixosModules.nvf;
}; };
darwinModules = {
nvf = import ./flake/modules/nixos.nix {inherit lib inputs;};
default = self.darwinModules.nvf;
};
}; };
perSystem = {pkgs, ...}: { perSystem = {pkgs, ...}: {
# Provides the default formatter for 'nix fmt', which will format the # Provides the default formatter for 'nix fmt', which will format the
# entire tree with Alejandra. The wrapper script is necessary due to # entire Nix source with Alejandra. The wrapper script is necessary due to
# changes to the behaviour of Nix, which now encourages wrappers for # changes to the behaviour of Nix, which now encourages wrappers for
# tree-wide formatting. # tree-wide formatting.
formatter = pkgs.writeShellApplication { formatter = pkgs.writeShellApplication {
@ -66,11 +71,17 @@
runtimeInputs = [ runtimeInputs = [
pkgs.alejandra pkgs.alejandra
pkgs.fd pkgs.fd
pkgs.deno
]; ];
text = '' text = ''
# Find Nix files in the tree and format them with Alejandra # Find Nix files in the tree and format them with Alejandra
echo "Formatting Nix files"
fd "$@" -t f -e nix -x alejandra -q '{}' fd "$@" -t f -e nix -x alejandra -q '{}'
# Same for Markdown files, but with deno
echo "Formatting Markdown files"
fd "$@" -t f -e md -x deno fmt -q '{}'
''; '';
}; };
@ -80,9 +91,29 @@
# Check if codebase is properly formatted. # Check if codebase is properly formatted.
# This can be initiated with `nix build .#checks.<system>.nix-fmt` # This can be initiated with `nix build .#checks.<system>.nix-fmt`
# or with `nix flake check` # or with `nix flake check`
nix-fmt = pkgs.runCommand "nix-fmt-check" {nativeBuildInputs = [pkgs.alejandra];} '' nix-fmt =
alejandra --check ${self} < /dev/null | tee $out pkgs.runCommand "nix-fmt-check"
''; {
src = self;
nativeBuildInputs = [pkgs.alejandra pkgs.fd];
} ''
cd "$src"
fd -t f -e nix -x alejandra --check '{}'
touch $out
'';
# Check if Markdown sources are properly formatted
# This can be initiated with `nix build .#checks.<system>.md-fmt`
# or with `nix flake check`
md-fmt =
pkgs.runCommand "md-fmt-check" {
src = self;
nativeBuildInputs = [pkgs.deno pkgs.fd];
} ''
cd "$src"
fd -t f -e md -x deno fmt --check '{}'
touch $out
'';
}; };
}; };
}; };
@ -105,5 +136,11 @@
# Alternate neovim-wrapper # Alternate neovim-wrapper
mnw.url = "github:Gerg-L/mnw"; mnw.url = "github:Gerg-L/mnw";
# Alternative documentation generator
ndg = {
url = "github:feel-co/ndg?ref=refs/tags/v2.6.0";
inputs.nixpkgs.follows = "nixpkgs";
};
}; };
} }

View file

@ -1,16 +1,23 @@
{lib, ...}: { {lib, ...}: {
perSystem = { perSystem = {pkgs, ...}: {
pkgs, # The default dev shell provides packages required to interact with
config, # the codebase as described by the contributing guidelines. It includes the
self', # formatters required, and a few additional goodies for linting work.
inputs',
...
}: {
devShells = { devShells = {
default = self'.devShells.lsp; default = pkgs.mkShellNoCC {
nvim-nix = pkgs.mkShellNoCC {packages = [config.packages.nix];}; packages = with pkgs; [
lsp = pkgs.mkShellNoCC { # Nix tooling
packages = with pkgs; [nil statix deadnix alejandra npins]; nil # LSP
statix # static checker
deadnix # dead code finder
# So that we can interact with plugin sources
npins
# Formatters
alejandra
deno
];
}; };
}; };
@ -19,7 +26,11 @@
# testing, but make sure to discard the changes before creating a pull # testing, but make sure to discard the changes before creating a pull
# request. # request.
packages.dev = let packages.dev = let
configuration = {}; configuration = {
# This is essentially the configuration that will be passed to the
# builder function. For example:
# vim.languages.nix.enable = true;
};
customNeovim = lib.nvim.neovimConfiguration { customNeovim = lib.nvim.neovimConfiguration {
inherit pkgs; inherit pkgs;

View file

@ -1,4 +1,5 @@
{ {
lib,
pins, pins,
openssl, openssl,
pkg-config, pkg-config,
@ -11,6 +12,8 @@
}: let }: let
# From npins # From npins
pin = pins.avante-nvim; pin = pins.avante-nvim;
pname = "avante-nvim-lib";
version = pin.branch; version = pin.branch;
src = pkgs.fetchFromGitHub { src = pkgs.fetchFromGitHub {
inherit (pin.repository) owner repo; inherit (pin.repository) owner repo;
@ -19,8 +22,7 @@
}; };
avante-nvim-lib = rustPlatform.buildRustPackage { avante-nvim-lib = rustPlatform.buildRustPackage {
pname = "avante-nvim-lib"; inherit pname version src;
inherit version src;
cargoHash = "sha256-pTWCT2s820mjnfTscFnoSKC37RE7DAPKxP71QuM+JXQ="; cargoHash = "sha256-pTWCT2s820mjnfTscFnoSKC37RE7DAPKxP71QuM+JXQ=";
@ -43,6 +45,8 @@
"--skip=test_roundtrip" "--skip=test_roundtrip"
"--skip=test_fetch_md" "--skip=test_fetch_md"
]; ];
env.RUSTFLAGS = lib.optionalString stdenv.hostPlatform.isDarwin "-C link-arg=-undefined -C link-arg=dynamic_lookup";
}; };
in in
vimUtils.buildVimPlugin { vimUtils.buildVimPlugin {
@ -64,7 +68,15 @@ in
# Requires setup with corresponding provider # Requires setup with corresponding provider
"avante.providers.azure" "avante.providers.azure"
"avante.providers.copilot" "avante.providers.copilot"
"avante.providers.vertex_claude" "avante.providers.gemini"
"avante.providers.ollama" "avante.providers.ollama"
"avante.providers.vertex"
"avante.providers.vertex_claude"
]; ];
meta = {
description = "Neovim plugin designed to emulate the behaviour of the Cursor AI IDE";
homepage = "https://github.com/yetone/avante.nvim";
license = lib.licenses.asl20;
};
} }

View file

@ -1,17 +1,19 @@
{ {
lib,
stdenv,
rustPlatform, rustPlatform,
fetchFromGitHub, fetchFromGitHub,
writeShellScriptBin, writeShellScriptBin,
}: }:
rustPlatform.buildRustPackage (finalAttrs: { rustPlatform.buildRustPackage (finalAttrs: {
pname = "blink-cmp"; pname = "blink-cmp";
version = "1.6.0"; version = "1.8.0";
src = fetchFromGitHub { src = fetchFromGitHub {
owner = "Saghen"; owner = "Saghen";
repo = "blink.cmp"; repo = "blink.cmp";
tag = "v${finalAttrs.version}"; tag = "v${finalAttrs.version}";
hash = "sha256-IHRYgKcYP+JDGu8Vtawgzlhq25vpROFqb8KmpfVMwCk="; hash = "sha256-JjlcPj7v9J+v1SDBYIub6jFEslLhZGHmsipV1atUAFo=";
}; };
forceShare = [ forceShare = [
@ -29,11 +31,24 @@ rustPlatform.buildRustPackage (finalAttrs: {
mv "$out/lib" "$out/target/release" mv "$out/lib" "$out/target/release"
''; '';
cargoHash = "sha256-QsVCugYWRri4qu64wHnbJQZBhy4tQrr+gCYbXtRBlqE="; cargoHash = "sha256-Qdt8O7IGj2HySb1jxsv3m33ZxJg96Ckw26oTEEyQjfs=";
nativeBuildInputs = [ nativeBuildInputs = [
(writeShellScriptBin "git" "exit 1") (writeShellScriptBin "git" "exit 1")
]; ];
env.RUSTC_BOOTSTRAP = true; env = {
RUSTC_BOOTSTRAP = true;
# Those are the Linker args used by upstream. Without those, the build fails.
# See:
# <https://github.com/saghen/blink.cmp/blob/main/.cargo/config.toml#L1C1-L11C2>
RUSTFLAGS = lib.optionalString stdenv.hostPlatform.isDarwin "-C link-arg=-undefined -C link-arg=dynamic_lookup";
};
meta = {
description = "Performant, batteries-included completion plugin for Neovim";
homepage = "https://github.com/saghen/blink.cmp";
changelog = "https://github.com/Saghen/blink.cmp/blob/v${finalAttrs.version}/CHANGELOG.md";
};
}) })

View file

@ -0,0 +1,48 @@
{
stdenv,
fetchFromGitHub,
nodejs,
pnpm_9,
pins,
}: let
pin = pins.prettier-plugin-astro;
in
stdenv.mkDerivation (finalAttrs: {
pname = "prettier-plugin-astro";
version = pin.version or pin.revision;
src = fetchFromGitHub {
inherit (pin.repository) owner repo;
rev = finalAttrs.version;
sha256 = pin.hash;
};
pnpmDeps = pnpm_9.fetchDeps {
inherit (finalAttrs) pname src;
fetcherVersion = 2;
hash = "sha256-K7pIWLkIIbUKDIcysfEtcf/eVMX9ZgyFHdqcuycHCNE=";
};
nativeBuildInputs = [
nodejs
pnpm_9.configHook
];
buildPhase = ''
runHook preBuild
pnpm run build
runHook postBuild
'';
installPhase = ''
runHook preInstall
# mkdir -p $out/dist
cp -r dist/ $out
cp -r node_modules $out
runHook postInstall
'';
})

View file

@ -0,0 +1,19 @@
{
buildNpmPackage,
fetchFromGitHub,
pins,
}: let
pin = pins.prettier-plugin-svelte;
in
buildNpmPackage (finalAttrs: {
pname = "prettier-plugin-svelte";
version = pin.version or pin.revision;
src = fetchFromGitHub {
inherit (pin.repository) owner repo;
rev = finalAttrs.version;
sha256 = pin.hash;
};
npmDepsHash = "sha256-D+gDdKiIG38jV+M/BqTKf0yYj1KXpbIodtQFdzocpn8=";
})

View file

@ -8,7 +8,7 @@
# - the addition of the function `entryBefore` indicating a "wanted # - the addition of the function `entryBefore` indicating a "wanted
# by" relationship. # by" relationship.
{lib}: let {lib}: let
inherit (builtins) isAttrs attrValues attrNames elem all head tail length toJSON isString; inherit (builtins) isAttrs attrValues attrNames elem all head tail length toJSON isString removeAttrs;
inherit (lib.attrsets) filterAttrs mapAttrs; inherit (lib.attrsets) filterAttrs mapAttrs;
inherit (lib.lists) toposort; inherit (lib.lists) toposort;
inherit (lib.nvim.dag) empty isEntry entryBetween entryAfter entriesBetween entryAnywhere topoSort; inherit (lib.nvim.dag) empty isEntry entryBetween entryAfter entriesBetween entryAnywhere topoSort;
@ -169,10 +169,11 @@ in {
else value) else value)
dag; dag;
sortedDag = topoSort finalDag; sortedDag = topoSort finalDag;
loopDetail = map (loops: removeAttrs loops ["data"]) sortedDag.loops;
result = result =
if sortedDag ? result if sortedDag ? result
then mapResult sortedDag.result then mapResult sortedDag.result
else abort ("Dependency cycle in ${name}: " + toJSON sortedDag); else abort ("Dependency cycle in ${name}: " + toJSON loopDetail);
in in
result; result;
} }

View file

@ -1,7 +1,7 @@
{lib}: let {lib}: let
inherit (builtins) isString getAttr; inherit (builtins) isString getAttr;
inherit (lib.options) mkOption; inherit (lib.options) mkOption;
inherit (lib.types) listOf bool str submodule attrsOf anything either nullOr; inherit (lib.types) listOf bool str submodule attrsOf anything either nullOr uniq;
inherit (lib.nvim.attrsets) mapListToAttrs; inherit (lib.nvim.attrsets) mapListToAttrs;
inherit (lib.nvim.types) luaInline; inherit (lib.nvim.types) luaInline;
in { in {
@ -46,7 +46,7 @@ in {
capabilities = mkOption { capabilities = mkOption {
type = nullOr (either luaInline (attrsOf anything)); type = nullOr (either luaInline (attrsOf anything));
default = null; default = null;
description = "LSP capabilitiess to pass to lspconfig"; description = "LSP capabilities to pass to LSP server configuration";
}; };
on_attach = mkOption { on_attach = mkOption {
@ -58,11 +58,11 @@ in {
filetypes = mkOption { filetypes = mkOption {
type = nullOr (listOf str); type = nullOr (listOf str);
default = null; default = null;
description = "Filetypes to auto-attach LSP in"; description = "Filetypes to auto-attach LSP server in";
}; };
cmd = mkOption { cmd = mkOption {
type = nullOr (listOf str); type = nullOr (either luaInline (uniq (listOf str)));
default = null; default = null;
description = "Command used to start the LSP server"; description = "Command used to start the LSP server";
}; };

View file

@ -1,92 +1,52 @@
# Helpers for converting values to lua # Helpers for converting values to lua
{lib}: let {lib}: let
inherit (builtins) hasAttr head throw typeOf isList isAttrs isBool isInt isString isPath isFloat toJSON;
inherit (lib.attrsets) mapAttrsToList filterAttrs;
inherit (lib.strings) concatStringsSep concatMapStringsSep stringToCharacters;
inherit (lib.trivial) boolToString warn;
in rec {
# Convert a null value to lua's nil
nullString = value:
if value == null
then "nil"
else "'${value}'";
# convert an expression to lua
expToLua = exp:
if isList exp
then listToLuaTable exp # if list, convert to lua table
else if isAttrs exp
then attrsetToLuaTable exp # if attrs, convert to table
else if isBool exp
then boolToString exp # if bool, convert to string
else if isInt exp
then toString exp # if int, convert to string
else if exp == null
then "nil"
else (toJSON exp); # otherwise jsonify the value and print as is
# convert list to a lua table
listToLuaTable = list:
"{ " + (concatStringsSep ", " (map expToLua list)) + " }";
# convert attrset to a lua table
attrsetToLuaTable = attrset:
"{ "
+ (
concatStringsSep ", "
(
mapAttrsToList (
name: value:
name
+ " = "
+ (expToLua value)
)
attrset
)
)
+ " }";
# Convert a list of lua expressions to a lua table. The difference to listToLuaTable is that the elements here are expected to be lua expressions already, whereas listToLuaTable converts from nix types to lua first
luaTable = items: ''{${concatStringsSep "," items}}'';
isLuaInline = object: (object._type or null) == "lua-inline"; isLuaInline = object: (object._type or null) == "lua-inline";
toLuaObject = args: toLuaObject = args:
if isAttrs args {
then int = toString args;
if isLuaInline args float = toString args;
then args.expr
else if hasAttr "__empty" args # escapes \ and quotes
then string = builtins.toJSON args;
warn '' path = builtins.toJSON args;
Using `__empty` to define an empty lua table is deprecated. Use an empty attrset instead.
'' "{ }" bool = lib.boolToString args;
else null = "nil";
"{"
+ (concatStringsSep "," list = "{${lib.concatMapStringsSep ",\n" toLuaObject args}}";
(mapAttrsToList
(n: v: set =
if head (stringToCharacters n) == "@" if lib.isDerivation args
then toLuaObject v then ''"${args}"''
else "[${toLuaObject n}] = " + (toLuaObject v)) else if isLuaInline args
(filterAttrs then args.expr
(_: v: v != null) else "{${
args))) lib.pipe args [
+ "}" (lib.filterAttrs (_: v: v != null))
else if isList args (builtins.mapAttrs (
then "{" + concatMapStringsSep "," toLuaObject args + "}" n: v:
else if isString args if lib.hasPrefix "@" n
then then toLuaObject v
# This should be enough! else "[${toLuaObject n}] = ${toLuaObject v}"
toJSON args ))
else if isPath args builtins.attrValues
then toJSON (toString args) (lib.concatStringsSep ",\n")
else if isBool args ]
then "${boolToString args}" }}";
else if isFloat args }
then "${toString args}" .${
else if isInt args builtins.typeOf args
then "${toString args}" }
else if (args == null) or (builtins.throw "Could not convert object of type `${builtins.typeOf args}` to lua object");
then "nil" in
else throw "could not convert object of type `${typeOf args}` to lua object"; {
} inherit isLuaInline toLuaObject;
luaTable = x: (toLuaObject (map lib.mkLuaInline x));
}
// lib.genAttrs [
"nullString"
"expToLua"
"listToLuaTable"
"attrsetToLuaTable"
] (name: lib.warn "${name} is deprecated use toLuaObject instead" toLuaObject)

View file

@ -1,7 +1,10 @@
{lib}: let {lib}: let
inherit (builtins) toJSON;
inherit (lib.options) mergeEqualOption; inherit (lib.options) mergeEqualOption;
inherit (lib.lists) singleton;
inherit (lib.strings) isString stringLength match; inherit (lib.strings) isString stringLength match;
inherit (lib.types) listOf mkOptionType; inherit (lib.types) listOf mkOptionType coercedTo;
inherit (lib.trivial) warn;
in { in {
mergelessListOf = elemType: mergelessListOf = elemType:
mkOptionType { mkOptionType {
@ -25,4 +28,15 @@ in {
description = "RGB color in hex format"; description = "RGB color in hex format";
check = v: isString v && (match "#?[0-9a-fA-F]{6}" v) != null; check = v: isString v && (match "#?[0-9a-fA-F]{6}" v) != null;
}; };
# no compound types please
deprecatedSingleOrListOf = option: t:
coercedTo
t
(x:
warn ''
${option} no longer accepts non-list values, use [${toJSON x}] instead
''
(singleton x))
(listOf t);
} }

View file

@ -10,5 +10,5 @@ in {
inherit (typesDag) dagOf; inherit (typesDag) dagOf;
inherit (typesPlugin) pluginsOpt extraPluginType mkPluginSetupOption luaInline pluginType borderType; inherit (typesPlugin) pluginsOpt extraPluginType mkPluginSetupOption luaInline pluginType borderType;
inherit (typesLanguage) diagnostics mkGrammarOption; inherit (typesLanguage) diagnostics mkGrammarOption;
inherit (customTypes) char hexColor mergelessListOf; inherit (customTypes) char hexColor mergelessListOf deprecatedSingleOrListOf;
} }

View file

@ -30,7 +30,7 @@
mkGrammarOption = pkgs: grammar: mkGrammarOption = pkgs: grammar:
mkPackageOption pkgs ["${grammar} treesitter"] { mkPackageOption pkgs ["${grammar} treesitter"] {
default = ["vimPlugins" "nvim-treesitter" "builtGrammars" grammar]; default = ["vimPlugins" "nvim-treesitter" "grammarPlugins" grammar];
}; };
in { in {
inherit diagnostics diagnosticSubmodule mkGrammarOption; inherit diagnostics diagnosticSubmodule mkGrammarOption;

View file

@ -1,7 +1,9 @@
{lib, ...}: let {lib, ...}: let
inherit (lib.modules) mkRemovedOptionModule mkRenamedOptionModule; inherit (builtins) head;
inherit (lib.modules) mkRemovedOptionModule mkRenamedOptionModule doRename;
inherit (lib.lists) concatLists; inherit (lib.lists) concatLists;
inherit (lib.nvim.config) batchRenameOptions; inherit (lib.nvim.config) batchRenameOptions;
inherit (lib.trivial) warn;
renamedVimOpts = batchRenameOptions ["vim"] ["vim" "options"] { renamedVimOpts = batchRenameOptions ["vim"] ["vim" "options"] {
# 2024-12-01 # 2024-12-01
@ -20,6 +22,31 @@
# 2025-02-07 # 2025-02-07
scrollOffset = "scrolloff"; scrollOffset = "scrolloff";
}; };
mkRemovedLspOpt = lang: (mkRemovedOptionModule ["vim" "languages" lang "lsp" "opts"] ''
`vim.languages.${lang}.lsp.opts` is now moved to `vim.lsp.servers.<server_name>.init_options`
'');
mkRemovedLspPackage = lang: (mkRemovedOptionModule ["vim" "languages" lang "lsp" "package"] ''
`vim.languages.${lang}.lsp.package` is now moved to `vim.lsp.servers.<server_name>.cmd`
'');
mkRenamedLspServer = lang:
doRename
{
from = ["vim" "languages" lang "lsp" "server"];
to = ["vim" "languages" lang "lsp" "servers"];
visible = false;
warn = true;
use = x:
warn
"Obsolete option `vim.languages.${lang}.lsp.server` used, use `vim.languages.${lang}.lsp.servers` instead."
(head x);
};
mkRemovedFormatPackage = lang: (mkRemovedOptionModule ["vim" "languages" lang "format" "package"] ''
`vim.languages.${lang}.format.package` is removed, please use `vim.formatter.conform-nvim.formatters.<formatter_name>.command` instead.
'');
in { in {
imports = concatLists [ imports = concatLists [
[ [
@ -120,9 +147,200 @@ in {
in 'vim.clipboard.registers'. Please see the documentation for the new module for more in 'vim.clipboard.registers'. Please see the documentation for the new module for more
details, or open an issue if you are confused. details, or open an issue if you are confused.
'') '')
# 2025-07-12
(mkRenamedLspServer "assembly")
(mkRenamedLspServer "astro")
(mkRemovedLspPackage "astro")
(mkRenamedLspServer "bash")
(mkRemovedLspPackage "bash")
(mkRemovedLspOpt "clang")
(mkRemovedLspPackage "clang")
(mkRenamedLspServer "clang")
(mkRemovedLspPackage "clojure")
(mkRenamedLspServer "csharp")
(mkRemovedLspPackage "csharp")
(mkRenamedLspServer "css")
(mkRemovedLspPackage "css")
(mkRemovedLspPackage "cue")
(mkRenamedLspServer "dart")
(mkRemovedLspPackage "dart")
(mkRemovedLspOpt "dart")
(mkRenamedLspServer "elixir")
(mkRemovedLspPackage "elixir")
(mkRenamedLspServer "fsharp")
(mkRemovedLspPackage "fsharp")
(mkRenamedLspServer "gleam")
(mkRemovedLspPackage "gleam")
(mkRenamedLspServer "go")
(mkRemovedLspPackage "go")
(mkRemovedLspPackage "haskell")
(mkRemovedLspPackage "hcl")
(mkRenamedLspServer "helm")
(mkRemovedLspPackage "helm")
(mkRemovedLspPackage "java")
(mkRenamedLspServer "julia")
(mkRemovedLspPackage "julia")
(mkRemovedLspPackage "kotlin")
(mkRemovedLspPackage "lua")
(mkRenamedLspServer "markdown")
(mkRemovedLspPackage "markdown")
(mkRenamedLspServer "nim")
(mkRemovedLspPackage "nim")
(mkRenamedLspServer "nix")
(mkRemovedLspPackage "nix")
(mkRemovedOptionModule ["vim" "languages" "nix" "lsp" "options"] ''
`vim.languages.nix.lsp.options` has been moved to `vim.lsp.servers.<server_name>.init_options`.
'')
(mkRenamedLspServer "nu")
(mkRemovedLspPackage "nu")
(mkRenamedLspServer "ocaml")
(mkRemovedLspPackage "ocaml")
(mkRenamedLspServer "odin")
(mkRemovedLspPackage "odin")
(mkRenamedLspServer "php")
(mkRemovedLspPackage "php")
(mkRenamedLspServer "python")
(mkRemovedLspPackage "python")
(mkRenamedLspServer "r")
(mkRemovedLspPackage "r")
(mkRenamedLspServer "ruby")
(mkRemovedLspPackage "ruby")
(mkRenamedLspServer "sql")
(mkRemovedLspPackage "sql")
(mkRenamedLspServer "svelte")
(mkRemovedLspPackage "svelte")
(mkRenamedLspServer "tailwind")
(mkRemovedLspPackage "tailwind")
(mkRemovedLspPackage "terraform")
(mkRenamedLspServer "ts")
(mkRemovedLspPackage "ts")
(mkRenamedLspServer "typst")
(mkRemovedLspPackage "typst")
(mkRenamedLspServer "vala")
(mkRemovedLspPackage "vala")
(mkRenamedLspServer "wgsl")
(mkRemovedLspPackage "wgsl")
(mkRenamedLspServer "yaml")
(mkRemovedLspPackage "yaml")
(mkRenamedLspServer "zig")
(mkRemovedLspPackage "zig")
# 2025-10-22
(mkRenamedOptionModule ["vim" "languages" "rust" "crates" "enable"] ["vim" "languages" "rust" "extensions" "crates-nvim" "enable"])
(mkRemovedOptionModule ["vim" "languages" "rust" "crates" "codeActions"] ''
'vim.languages.rust.crates' option has been moved to 'vim.languages.rust.extensions.crates-nvim' in full and the
codeActions option has been removed. To set up code actions again, you may use the the new 'setupOpts' option
located under 'vim.languages.rust.extensions.crates-nvim'. Refer to crates.nvim documentation for setup steps:
<https://github.com/Saecki/crates.nvim/wiki/Documentation-v0.7.1#in-process-language-server>
'')
(mkRemovedOptionModule ["vim" "language" "astro" "format"] ''
This option has been removed due to being broken for a long time.
'')
(mkRemovedOptionModule ["vim" "language" "svelte" "format"] ''
This option has been removed due to being broken for a long time.
'')
] ]
(map mkRemovedFormatPackage [
"bash"
"css"
"elixir"
"fsharp"
"go"
"hcl"
"html"
"json"
"lua"
"markdown"
"nim"
"nix"
"ocaml"
"python"
"qml"
"r"
"ruby"
"rust"
"sql"
"ts"
"typst"
])
# Migrated via batchRenameOptions. Further batch renames must be below this line. # Migrated via batchRenameOptions. Further batch renames must be below this line.
renamedVimOpts renamedVimOpts
# 2026-01-06
[
(mkRemovedOptionModule ["vim" "treesitter" "highlight" "disable"] ''
Treesitter highlighting is now handled by Neovim natively, and it does not have a disable option.
'')
(mkRemovedOptionModule ["vim" "treesitter" "highlight" "additionalVimRegexHighlighting"] ''
Treesitter highlighting is now handled by Neovim natively, and it does not have a additionalVimRegexHighlighting option.
'')
(mkRemovedOptionModule ["vim" "treesitter" "indent" "disable"] ''
Treesitter indentation is now handled differently, and it does not have a disable option.
'')
(mkRemovedOptionModule ["vim" "treesitter" "incrementalSelection" "enable"] ''
Incremental selection configuration has been removed from nvim-treesitter.
'')
(mkRemovedOptionModule ["vim" "treesitter" "incrementalSelection" "disable"] ''
Incremental selection configuration has been removed from nvim-treesitter.
'')
(mkRemovedOptionModule ["vim" "treesitter" "mappings" "incrementalSelection" "init"] ''
Incremental selection configuration has been removed from nvim-treesitter.
'')
(mkRemovedOptionModule ["vim" "treesitter" "mappings" "incrementalSelection" "incrementByNode"] ''
Incremental selection configuration has been removed from nvim-treesitter.
'')
(
mkRemovedOptionModule ["vim" "treesitter" "mappings" "incrementalSelection" "incrementByScope"]
''
Incremental selection configuration has been removed from nvim-treesitter.
''
)
(mkRemovedOptionModule ["vim" "treesitter" "mappings" "incrementalSelection" "decrementByNode"] ''
Incremental selection configuration has been removed from nvim-treesitter.
'')
]
]; ];
} }

View file

@ -9,7 +9,7 @@
inherit (lib.types) nullOr submodule listOf str bool; inherit (lib.types) nullOr submodule listOf str bool;
inherit (lib.nvim.types) luaInline; inherit (lib.nvim.types) luaInline;
inherit (lib.nvim.lua) toLuaObject; inherit (lib.nvim.lua) toLuaObject;
inherit (lib.nvim.dag) entryAfter; inherit (lib.nvim.dag) entryAfter entryBetween;
autocommandType = submodule { autocommandType = submodule {
options = { options = {
@ -144,7 +144,7 @@ in {
enabledAutogroups = filter (au: au.enable) cfg.augroups; enabledAutogroups = filter (au: au.enable) cfg.augroups;
in { in {
luaConfigRC = { luaConfigRC = {
augroups = entryAfter ["pluginConfigs"] (optionalString (enabledAutogroups != []) '' augroups = entryBetween ["autocmds"] ["pluginConfigs"] (optionalString (enabledAutogroups != []) ''
local nvf_autogroups = {} local nvf_autogroups = {}
for _, group in ipairs(${toLuaObject enabledAutogroups}) do for _, group in ipairs(${toLuaObject enabledAutogroups}) do
if group.name then if group.name then

View file

@ -15,7 +15,7 @@ in {
clipboard = { clipboard = {
enable = mkEnableOption '' enable = mkEnableOption ''
clipboard management for Neovim. Users may still choose to manage their clipboard management for Neovim. Users may still choose to manage their
clipboard through [](#opt-vim.options) should they wish to avoid using clipboard through {option}`vim.options` should they wish to avoid using
this module. this module.
''; '';

View file

@ -8,5 +8,6 @@
./highlight.nix ./highlight.nix
./lsp.nix ./lsp.nix
./spellcheck.nix ./spellcheck.nix
./util.nix
]; ];
} }

View file

@ -16,6 +16,7 @@
cfg = config.vim.lsp; cfg = config.vim.lsp;
# TODO: lspConfigurations filter on enabledServers instead of cfg.servers?
lspConfigurations = lspConfigurations =
mapAttrsToList ( mapAttrsToList (
name: value: '' name: value: ''
@ -76,7 +77,6 @@ in {
{ {
vim.lsp.servers."*" = { vim.lsp.servers."*" = {
capabilities = mkDefault (mkLuaInline "capabilities"); capabilities = mkDefault (mkLuaInline "capabilities");
on_attach = mkDefault (mkLuaInline "default_on_attach");
}; };
} }

View file

@ -9,7 +9,7 @@
inherit (lib.strings) concatLines concatStringsSep optionalString; inherit (lib.strings) concatLines concatStringsSep optionalString;
inherit (lib.attrsets) mapAttrsToList; inherit (lib.attrsets) mapAttrsToList;
inherit (lib.types) listOf str attrsOf; inherit (lib.types) listOf str attrsOf;
inherit (lib.nvim.lua) listToLuaTable; inherit (lib.nvim.lua) toLuaObject;
inherit (lib.nvim.dag) entryAfter; inherit (lib.nvim.dag) entryAfter;
cfg = config.vim.spellcheck; cfg = config.vim.spellcheck;
@ -29,7 +29,7 @@ in {
To add your own language files, you may place your `spell` directory in either To add your own language files, you may place your `spell` directory in either
{file}`$XDG_CONFIG_HOME/nvf` or in a path that is included in the {file}`$XDG_CONFIG_HOME/nvf` or in a path that is included in the
[additionalRuntimePaths](#opt-vim.additionalRuntimePaths) list provided by nvf. [additionalRuntimePaths](./options.html#option-vim-additionalRuntimePaths) list provided by nvf.
''; '';
}; };
@ -152,7 +152,7 @@ in {
vim.api.nvim_create_augroup("nvf_autocmds", {clear = false}) vim.api.nvim_create_augroup("nvf_autocmds", {clear = false})
vim.api.nvim_create_autocmd({ "FileType" }, { vim.api.nvim_create_autocmd({ "FileType" }, {
group = "nvf_autocmds", group = "nvf_autocmds",
pattern = ${listToLuaTable cfg.ignoredFiletypes}, pattern = ${toLuaObject cfg.ignoredFiletypes},
callback = function() callback = function()
vim.opt_local.spell = false vim.opt_local.spell = false
end, end,

View file

@ -0,0 +1,177 @@
{
config,
lib,
...
}: let
inherit (lib.modules) mkIf mkMerge;
inherit (lib.nvim.dag) entryBefore;
cfg = config.vim.lsp;
in {
config = mkMerge [
(mkIf (cfg.servers != {}) {
vim.luaConfigRC.lsp-util =
entryBefore ["lsp-servers"]
/*
lua
*/
''
-- Port of nvim-lspconfig util
local util = { path = {} }
util.default_config = {
log_level = vim.lsp.protocol.MessageType.Warning,
message_level = vim.lsp.protocol.MessageType.Warning,
settings = vim.empty_dict(),
init_options = vim.empty_dict(),
handlers = {},
autostart = true,
capabilities = vim.lsp.protocol.make_client_capabilities(),
}
-- global on_setup hook
util.on_setup = nil
do
local validate = vim.validate
local api = vim.api
local lsp = vim.lsp
local nvim_eleven = vim.fn.has 'nvim-0.11' == 1
local iswin = vim.uv.os_uname().version:match 'Windows'
local function escape_wildcards(path)
return path:gsub('([%[%]%?%*])', '\\%1')
end
local function is_fs_root(path)
if iswin then
return path:match '^%a:$'
else
return path == '/'
end
end
local function traverse_parents(path, cb)
path = vim.uv.fs_realpath(path)
local dir = path
-- Just in case our algo is buggy, don't infinite loop.
for _ = 1, 100 do
dir = vim.fs.dirname(dir)
if not dir then
return
end
-- If we can't ascend further, then stop looking.
if cb(dir, path) then
return dir, path
end
if is_fs_root(dir) then
break
end
end
end
util.root_pattern = function(...)
local patterns = util.tbl_flatten { ... }
return function(startpath)
startpath = util.strip_archive_subpath(startpath)
for _, pattern in ipairs(patterns) do
local match = util.search_ancestors(startpath, function(path)
for _, p in ipairs(vim.fn.glob(table.concat({ escape_wildcards(path), pattern }, '/'), true, true)) do
if vim.uv.fs_stat(p) then
return path
end
end
end)
if match ~= nil then
return match
end
end
end
end
util.root_markers_with_field = function(root_files, new_names, field, fname)
local path = vim.fn.fnamemodify(fname, ':h')
local found = vim.fs.find(new_names, { path = path, upward = true })
for _, f in ipairs(found or {}) do
-- Match the given `field`.
for line in io.lines(f) do
if line:find(field) then
root_files[#root_files + 1] = vim.fs.basename(f)
break
end
end
end
return root_files
end
util.insert_package_json = function(root_files, field, fname)
return util.root_markers_with_field(root_files, { 'package.json', 'package.json5' }, field, fname)
end
util.strip_archive_subpath = function(path)
-- Matches regex from zip.vim / tar.vim
path = vim.fn.substitute(path, 'zipfile://\\(.\\{-}\\)::[^\\\\].*$', '\\1', ''')
path = vim.fn.substitute(path, 'tarfile:\\(.\\{-}\\)::.*$', '\\1', ''')
return path
end
util.get_typescript_server_path = function(root_dir)
local project_roots = vim.fs.find('node_modules', { path = root_dir, upward = true, limit = math.huge })
for _, project_root in ipairs(project_roots) do
local typescript_path = project_root .. '/typescript'
local stat = vim.loop.fs_stat(typescript_path)
if stat and stat.type == 'directory' then
return typescript_path .. '/lib'
end
end
return '''
end
util.search_ancestors = function(startpath, func)
if nvim_eleven then
validate('func', func, 'function')
end
if func(startpath) then
return startpath
end
local guard = 100
for path in vim.fs.parents(startpath) do
-- Prevent infinite recursion if our algorithm breaks
guard = guard - 1
if guard == 0 then
return
end
if func(path) then
return path
end
end
end
util.path.is_descendant = function(root, path)
if not path then
return false
end
local function cb(dir, _)
return dir == root
end
local dir, _ = traverse_parents(path, cb)
return dir == root
end
util.tbl_flatten = function(t)
--- @diagnostic disable-next-line:deprecated
return nvim_eleven and vim.iter(t):flatten(math.huge):totable() or vim.tbl_flatten(t)
end
end
'';
})
];
}

View file

@ -4,25 +4,16 @@
... ...
}: let }: let
inherit (lib.modules) mkIf; inherit (lib.modules) mkIf;
inherit (lib.lists) optionals;
cfg = config.vim.assistant.avante-nvim; cfg = config.vim.assistant.avante-nvim;
in { in {
config = mkIf cfg.enable { config = mkIf cfg.enable {
vim = { vim = {
startPlugins = startPlugins = [
[ "plenary-nvim"
"nvim-treesitter" "dressing-nvim"
"plenary-nvim" "nui-nvim"
"dressing-nvim" ];
"nui-nvim"
]
++ (optionals config.vim.mini.pick.enable ["mini-pick"])
++ (optionals config.vim.telescope.enable ["telescope"])
++ (optionals config.vim.autocomplete.nvim-cmp.enable ["nvim-cmp"])
++ (optionals config.vim.fzf-lua.enable ["fzf-lua"])
++ (optionals config.vim.visuals.nvim-web-devicons.enable ["nvim-web-devicons"])
++ (optionals config.vim.utility.images.img-clip.enable ["img-clip"]);
lazy.plugins = { lazy.plugins = {
avante-nvim = { avante-nvim = {

View file

@ -1,6 +1,7 @@
{ {
config, config,
lib, lib,
options,
... ...
}: let }: let
inherit (lib.modules) mkIf mkMerge; inherit (lib.modules) mkIf mkMerge;
@ -10,8 +11,7 @@
cfg = config.vim.assistant.chatgpt; cfg = config.vim.assistant.chatgpt;
self = import ./chatgpt.nix {inherit lib;}; mappingDefinitions = options.vim.assistant.chatgpt.mappings;
mappingDefinitions = self.options.vim.assistant.chatgpt.mappings;
mappings = addDescriptionsToMappings cfg.mappings mappingDefinitions; mappings = addDescriptionsToMappings cfg.mappings mappingDefinitions;
maps = mkMerge [ maps = mkMerge [
(mkSetBinding mappings.editWithInstructions "<cmd>ChatGPTEditWithInstruction<CR>") (mkSetBinding mappings.editWithInstructions "<cmd>ChatGPTEditWithInstruction<CR>")

View file

@ -1,13 +1,58 @@
{lib, ...}: let {lib, ...}: let
inherit (lib.generators) mkLuaInline; inherit (lib.generators) mkLuaInline;
inherit (lib.options) mkOption mkEnableOption literalMD; inherit (lib.options) mkOption mkEnableOption literalMD;
inherit (lib.types) attrs either nullOr; inherit (lib.types) attrs either nullOr listOf submodule str;
inherit (lib.nvim.lua) toLuaObject; inherit (lib.nvim.lua) toLuaObject;
inherit (lib.nvim.types) luaInline mkPluginSetupOption; inherit (lib.nvim.types) luaInline mkPluginSetupOption;
formattersType = submodule {
freeformType = attrs;
options = {
command = mkOption {
type = nullOr (either str luaInline);
default = null;
description = "The command to run.";
};
args = mkOption {
type = nullOr (either (listOf str) luaInline);
default = null;
description = ''
A list of strings, or a lua function that returns a list of strings.
Return a single string instead of a list to run the command in a
shell.
'';
};
prepend_args = mkOption {
type = nullOr (either (listOf str) luaInline);
default = null;
description = ''
When inherit = true, add additional arguments to the beginning of
args. Can also be a function, like args.
'';
};
append_args = mkOption {
type = nullOr (either (listOf str) luaInline);
default = null;
description = ''
When inherit = true, add additional arguments to the end of args.
Can also be a function, like args.
'';
};
};
};
in { in {
options.vim.formatter.conform-nvim = { options.vim.formatter.conform-nvim = {
enable = mkEnableOption "lightweight yet powerful formatter plugin for Neovim [conform-nvim]"; enable = mkEnableOption "lightweight yet powerful formatter plugin for Neovim [conform-nvim]";
setupOpts = mkPluginSetupOption "conform.nvim" { setupOpts = mkPluginSetupOption "conform.nvim" {
formatters = mkOption {
type = formattersType;
default = {};
description = "Custom formatters and overrides for built-in formatters.";
};
formatters_by_ft = mkOption { formatters_by_ft = mkOption {
type = attrs; type = attrs;
default = {}; default = {};

View file

@ -1,6 +1,7 @@
{ {
config, config,
lib, lib,
options,
... ...
}: let }: let
inherit (lib.modules) mkIf mkMerge; inherit (lib.modules) mkIf mkMerge;
@ -10,8 +11,7 @@
cfg = config.vim.git.git-conflict; cfg = config.vim.git.git-conflict;
self = import ./git-conflict.nix {inherit lib config;}; gcMappingDefinitions = options.vim.git.git-conflict.mappings;
gcMappingDefinitions = self.options.vim.git.git-conflict.mappings;
gcMappings = addDescriptionsToMappings cfg.mappings gcMappingDefinitions; gcMappings = addDescriptionsToMappings cfg.mappings gcMappingDefinitions;
in { in {

View file

@ -1,6 +1,7 @@
{ {
config, config,
lib, lib,
options,
... ...
}: let }: let
inherit (builtins) toJSON; inherit (builtins) toJSON;
@ -12,8 +13,7 @@
cfg = config.vim.git.gitsigns; cfg = config.vim.git.gitsigns;
self = import ./gitsigns.nix {inherit lib config;}; gsMappingDefinitions = options.vim.git.gitsigns.mappings;
gsMappingDefinitions = self.options.vim.git.gitsigns.mappings;
gsMappings = addDescriptionsToMappings cfg.mappings gsMappingDefinitions; gsMappings = addDescriptionsToMappings cfg.mappings gsMappingDefinitions;
in { in {

View file

@ -4,12 +4,24 @@
lib, lib,
... ...
}: let }: let
inherit (builtins) attrNames;
inherit (lib.options) mkEnableOption mkOption; inherit (lib.options) mkEnableOption mkOption;
inherit (lib.modules) mkIf mkMerge; inherit (lib.modules) mkIf mkMerge;
inherit (lib.types) package; inherit (lib.types) enum;
inherit (lib.nvim.types) mkGrammarOption; inherit (lib.nvim.types) mkGrammarOption deprecatedSingleOrListOf;
inherit (lib.meta) getExe;
inherit (lib.nvim.attrsets) mapListToAttrs;
cfg = config.vim.languages.assembly; cfg = config.vim.languages.assembly;
defaultServers = ["asm-lsp"];
servers = {
asm-lsp = {
enable = true;
cmd = [(getExe pkgs.asm-lsp)];
filetypes = ["asm" "vmasm"];
root_markers = [".asm-lsp.toml" ".git"];
};
};
in { in {
options.vim.languages.assembly = { options.vim.languages.assembly = {
enable = mkEnableOption "Assembly support"; enable = mkEnableOption "Assembly support";
@ -20,12 +32,11 @@ in {
}; };
lsp = { lsp = {
enable = mkEnableOption "Assembly LSP support (asm-lsp)" // {default = config.vim.lsp.enable;}; enable = mkEnableOption "Assembly LSP support" // {default = config.vim.lsp.enable;};
servers = mkOption {
package = mkOption { type = deprecatedSingleOrListOf "vim.language.asm.lsp.servers" (enum (attrNames servers));
type = package; default = defaultServers;
default = pkgs.asm-lsp; description = "Assembly LSP server to use";
description = "asm-lsp package";
}; };
}; };
}; };
@ -36,14 +47,12 @@ in {
}) })
(mkIf cfg.lsp.enable { (mkIf cfg.lsp.enable {
vim.lsp.lspconfig.enable = true; vim.lsp.servers =
vim.lsp.lspconfig.sources.asm-lsp = '' mapListToAttrs (n: {
lspconfig.asm_lsp.setup { name = n;
capabilities = capabilities, value = servers.${n};
on_attach = default_on_attach, })
cmd = {"${cfg.lsp.package}/bin/asm-lsp"}, cfg.lsp.servers;
}
'';
}) })
]); ]);
} }

View file

@ -1,4 +1,5 @@
{ {
inputs,
config, config,
pkgs, pkgs,
lib, lib,
@ -7,49 +8,54 @@
inherit (builtins) attrNames; inherit (builtins) attrNames;
inherit (lib.options) mkEnableOption mkOption; inherit (lib.options) mkEnableOption mkOption;
inherit (lib.modules) mkIf mkMerge; inherit (lib.modules) mkIf mkMerge;
inherit (lib.lists) isList;
inherit (lib.meta) getExe; inherit (lib.meta) getExe;
inherit (lib.types) enum either listOf package str; inherit (lib.types) enum coercedTo;
inherit (lib.nvim.lua) expToLua; inherit (lib.nvim.attrsets) mapListToAttrs;
inherit (lib.nvim.types) mkGrammarOption diagnostics; inherit (lib.nvim.types) mkGrammarOption diagnostics deprecatedSingleOrListOf;
inherit (lib.generators) mkLuaInline;
cfg = config.vim.languages.astro; cfg = config.vim.languages.astro;
defaultServer = "astro"; defaultServers = ["astro"];
servers = { servers = {
astro = { astro = {
package = pkgs.astro-language-server; enable = true;
lspConfig = '' cmd = [(getExe pkgs.astro-language-server) "--stdio"];
lspconfig.astro.setup { filetypes = ["astro"];
capabilities = capabilities, root_markers = ["package.json" "tsconfig.json" "jsconfig.json" ".git"];
on_attach = attach_keymaps, init_options = {
cmd = ${ typescript = {};
if isList cfg.lsp.package };
then expToLua cfg.lsp.package before_init =
else ''{"${cfg.lsp.package}/bin/astro-ls", "--stdio"}'' mkLuaInline
} /*
} lua
''; */
''
function(_, config)
if config.init_options and config.init_options.typescript and not config.init_options.typescript.tsdk then
config.init_options.typescript.tsdk = util.get_typescript_server_path(config.root_dir)
end
end
'';
}; };
}; };
# TODO: specify packages defaultFormat = ["prettier"];
defaultFormat = "prettier"; formats = let
formats = { parser = "${inputs.self.packages.${pkgs.stdenv.hostPlatform.system}.prettier-plugin-astro}/index.js";
in {
prettier = { prettier = {
package = pkgs.prettier; command = getExe pkgs.prettier;
}; options.ft_parsers.astro = "astro";
prepend_args = ["--plugin=${parser}"];
prettierd = {
package = pkgs.prettierd;
}; };
biome = { biome = {
package = pkgs.biome; command = getExe pkgs.biome;
}; };
}; };
# TODO: specify packages
defaultDiagnosticsProvider = ["eslint_d"]; defaultDiagnosticsProvider = ["eslint_d"];
diagnosticsProviders = { diagnosticsProviders = {
eslint_d = let eslint_d = let
@ -69,6 +75,15 @@
}; };
}; };
}; };
formatType =
deprecatedSingleOrListOf
"vim.languages.astro.format.type"
(coercedTo (enum ["prettierd"]) (_:
lib.warn
"vim.languages.astro.format.type: prettierd is deprecated, use prettier instead"
"prettier")
(enum (attrNames formats)));
in { in {
options.vim.languages.astro = { options.vim.languages.astro = {
enable = mkEnableOption "Astro language support"; enable = mkEnableOption "Astro language support";
@ -81,34 +96,20 @@ in {
lsp = { lsp = {
enable = mkEnableOption "Astro LSP support" // {default = config.vim.lsp.enable;}; enable = mkEnableOption "Astro LSP support" // {default = config.vim.lsp.enable;};
servers = mkOption {
server = mkOption { type = deprecatedSingleOrListOf "vim.language.astro.lsp.servers" (enum (attrNames servers));
type = enum (attrNames servers); default = defaultServers;
default = defaultServer;
description = "Astro LSP server to use"; description = "Astro LSP server to use";
}; };
package = mkOption {
type = either package (listOf str);
default = servers.${cfg.lsp.server}.package;
example = ''[lib.getExe pkgs.astro-language-server "--minify" "--stdio"]'';
description = "Astro LSP server package, or the command to run as a list of strings";
};
}; };
format = { format = {
enable = mkEnableOption "Astro formatting" // {default = config.vim.languages.enableFormat;}; enable = mkEnableOption "Astro formatting" // {default = config.vim.languages.enableFormat;};
type = mkOption { type = mkOption {
description = "Astro formatter to use"; type = formatType;
type = enum (attrNames formats);
default = defaultFormat; default = defaultFormat;
}; description = "Astro formatter to use";
package = mkOption {
description = "Astro formatter package";
type = package;
default = formats.${cfg.format.type}.package;
}; };
}; };
@ -130,16 +131,25 @@ in {
}) })
(mkIf cfg.lsp.enable { (mkIf cfg.lsp.enable {
vim.lsp.lspconfig.enable = true; vim.lsp.servers =
vim.lsp.lspconfig.sources.astro-lsp = servers.${cfg.lsp.server}.lspConfig; mapListToAttrs (n: {
name = n;
value = servers.${n};
})
cfg.lsp.servers;
}) })
(mkIf cfg.format.enable { (mkIf cfg.format.enable {
vim.formatter.conform-nvim = { vim.formatter.conform-nvim = {
enable = true; enable = true;
setupOpts.formatters_by_ft.astro = [cfg.format.type]; setupOpts = {
setupOpts.formatters.${cfg.format.type} = { formatters_by_ft.astro = cfg.format.type;
command = getExe cfg.format.package; formatters =
mapListToAttrs (name: {
inherit name;
value = formats.${name};
})
cfg.format.type;
}; };
}; };
}) })

View file

@ -5,38 +5,35 @@
... ...
}: let }: let
inherit (builtins) attrNames; inherit (builtins) attrNames;
inherit (lib.options) mkOption mkEnableOption literalExpression; inherit (lib.options) mkOption mkEnableOption;
inherit (lib.meta) getExe; inherit (lib.meta) getExe;
inherit (lib.modules) mkIf mkMerge; inherit (lib.modules) mkIf mkMerge;
inherit (lib.lists) isList; inherit (lib.types) enum bool;
inherit (lib.types) enum either package listOf str bool; inherit (lib.generators) mkLuaInline;
inherit (lib.nvim.types) diagnostics mkGrammarOption; inherit (lib.nvim.types) diagnostics mkGrammarOption deprecatedSingleOrListOf;
inherit (lib.nvim.lua) expToLua; inherit (lib.nvim.attrsets) mapListToAttrs;
cfg = config.vim.languages.bash; cfg = config.vim.languages.bash;
defaultServer = "bash-ls"; defaultServers = ["bash-ls"];
servers = { servers = {
bash-ls = { bash-ls = {
package = pkgs.bash-language-server; enable = true;
lspConfig = '' cmd = [(getExe pkgs.bash-language-server) "start"];
lspconfig.bashls.setup{ filetypes = ["bash" "sh"];
capabilities = capabilities; root_markers = [".git"];
on_attach = default_on_attach; settings = {
cmd = ${ basheIde = {
if isList cfg.lsp.package globPattern = mkLuaInline "vim.env.GLOB_PATTERN or '*@(.sh|.inc|.bash|.command)'";
then expToLua cfg.lsp.package
else ''{"${cfg.lsp.package}/bin/bash-language-server", "start"}''
}; };
} };
'';
}; };
}; };
defaultFormat = "shfmt"; defaultFormat = ["shfmt"];
formats = { formats = {
shfmt = { shfmt = {
package = pkgs.shfmt; command = getExe pkgs.shfmt;
}; };
}; };
@ -56,38 +53,24 @@ in {
}; };
lsp = { lsp = {
enable = mkEnableOption "Enable Bash LSP support" // {default = config.vim.lsp.enable;}; enable = mkEnableOption "Bash LSP support" // {default = config.vim.lsp.enable;};
servers = mkOption {
server = mkOption { type = deprecatedSingleOrListOf "vim.language.bash.lsp.servers" (enum (attrNames servers));
default = defaultServers;
description = "Bash LSP server to use"; description = "Bash LSP server to use";
type = enum (attrNames servers);
default = defaultServer;
};
package = mkOption {
description = "bash-language-server package, or the command to run as a list of strings";
example = literalExpression ''[lib.getExe pkgs.bash-language-server "start"]'';
type = either package (listOf str);
default = pkgs.bash-language-server;
}; };
}; };
format = { format = {
enable = mkOption { enable = mkOption {
description = "Enable Bash formatting";
type = bool; type = bool;
default = config.vim.languages.enableFormat; default = config.vim.languages.enableFormat;
description = "Enable Bash formatting";
}; };
type = mkOption { type = mkOption {
description = "Bash formatter to use"; type = deprecatedSingleOrListOf "vim.language.bash.format.type" (enum (attrNames formats));
type = enum (attrNames formats);
default = defaultFormat; default = defaultFormat;
}; description = "Bash formatter to use";
package = mkOption {
description = "Bash formatter package";
type = package;
default = formats.${cfg.format.type}.package;
}; };
}; };
@ -108,16 +91,25 @@ in {
}) })
(mkIf cfg.lsp.enable { (mkIf cfg.lsp.enable {
vim.lsp.lspconfig.enable = true; vim.lsp.servers =
vim.lsp.lspconfig.sources.bash-lsp = servers.${cfg.lsp.server}.lspConfig; mapListToAttrs (n: {
name = n;
value = servers.${n};
})
cfg.lsp.servers;
}) })
(mkIf cfg.format.enable { (mkIf cfg.format.enable {
vim.formatter.conform-nvim = { vim.formatter.conform-nvim = {
enable = true; enable = true;
setupOpts.formatters_by_ft.sh = [cfg.format.type]; setupOpts = {
setupOpts.formatters.${cfg.format.type} = { formatters_by_ft.sh = cfg.format.type;
command = getExe cfg.format.package; formatters =
mapListToAttrs (name: {
inherit name;
value = formats.${name};
})
cfg.format.type;
}; };
}; };
}) })

View file

@ -5,47 +5,139 @@
... ...
}: let }: let
inherit (builtins) attrNames; inherit (builtins) attrNames;
inherit (lib.lists) isList;
inherit (lib.strings) optionalString;
inherit (lib.options) mkEnableOption mkOption; inherit (lib.options) mkEnableOption mkOption;
inherit (lib.types) bool enum package either listOf str nullOr; inherit (lib.types) bool enum package;
inherit (lib.meta) getExe;
inherit (lib.modules) mkIf mkMerge; inherit (lib.modules) mkIf mkMerge;
inherit (lib.nvim.lua) expToLua; inherit (lib.generators) mkLuaInline;
inherit (lib.nvim.types) mkGrammarOption; inherit (lib.nvim.types) mkGrammarOption deprecatedSingleOrListOf;
inherit (lib.nvim.attrsets) mapListToAttrs;
inherit (lib.nvim.dag) entryAfter; inherit (lib.nvim.dag) entryAfter;
packageToCmd = package: defaultCmd:
if isList cfg.lsp.package
then expToLua cfg.lsp.package
else ''{ "${cfg.lsp.package}/bin/${defaultCmd}" }'';
cfg = config.vim.languages.clang; cfg = config.vim.languages.clang;
defaultServer = "clangd"; defaultServers = ["clangd"];
servers = { servers = {
ccls = { ccls = {
package = pkgs.ccls; cmd = [(getExe pkgs.ccls)];
lspConfig = '' filetypes = ["c" "cpp" "objc" "objcpp" "cuda"];
lspconfig.ccls.setup{ offset_encoding = "utf-32";
capabilities = capabilities; root_markers = ["compile_commands.json" ".ccls" ".git"];
on_attach=default_on_attach; workspace_required = true;
cmd = ${packageToCmd cfg.lsp.package "ccls"}; on_attach = mkLuaInline ''
${optionalString (cfg.lsp.opts != null) "init_options = ${cfg.lsp.opts}"} function(client, bufnr)
} local function switch_source_header(bufnr)
local method_name = "textDocument/switchSourceHeader"
local params = vim.lsp.util.make_text_document_params(bufnr)
client:request(method_name, params, function(err, result)
if err then
error(tostring(err))
end
if not result then
vim.notify('corresponding file cannot be determined')
return
end
vim.cmd.edit(vim.uri_to_fname(result))
end, bufnr)
end
vim.api.nvim_buf_create_user_command(
bufnr,
"LspCclsSwitchSourceHeader",
function(arg)
switch_source_header(client, 0)
end,
{desc = "Switch between source/header"}
)
end
''; '';
}; };
clangd = { clangd = {
package = pkgs.clang-tools; cmd = ["${pkgs.clang-tools}/bin/clangd"];
lspConfig = '' filetypes = ["c" "cpp" "objc" "objcpp" "cuda" "proto"];
local clangd_cap = capabilities root_markers = [
-- use same offsetEncoding as null-ls ".clangd"
clangd_cap.offsetEncoding = {"utf-16"} ".clang-tidy"
lspconfig.clangd.setup{ ".clang-format"
capabilities = clangd_cap; "compile_commands.json"
on_attach=default_on_attach; "compile_flags.txt"
cmd = ${packageToCmd cfg.lsp.package "clangd"}; "configure.ac"
${optionalString (cfg.lsp.opts != null) "init_options = ${cfg.lsp.opts}"} ".git"
} ];
capabilities = {
textDocument = {
completion = {
editsNearCursor = true;
};
};
offsetEncoding = ["utf-8" "utf-16"];
};
on_attach = mkLuaInline ''
function(client, bufnr)
local function switch_source_header(bufnr)
local method_name = "textDocument/switchSourceHeader"
local client = vim.lsp.get_clients({ bufnr = bufnr, name = "clangd", })[1]
if not client then
return vim.notify(('method %s is not supported by any servers active on the current buffer'):format(method_name))
end
local params = vim.lsp.util.make_text_document_params(bufnr)
client.request(method_name, params, function(err, result)
if err then
error(tostring(err))
end
if not result then
vim.notify('corresponding file cannot be determined')
return
end
vim.cmd.edit(vim.uri_to_fname(result))
end, bufnr)
end
local function symbol_info()
local bufnr = vim.api.nvim_get_current_buf()
local clangd_client = vim.lsp.get_clients({ bufnr = bufnr, name = "clangd" })[1]
if not clangd_client or not clangd_client.supports_method 'textDocument/symbolInfo' then
return vim.notify('Clangd client not found', vim.log.levels.ERROR)
end
local win = vim.api.nvim_get_current_win()
local params = vim.lsp.util.make_position_params(win, clangd_client.offset_encoding)
clangd_client:request('textDocument/symbolInfo', params, function(err, res)
if err or #res == 0 then
-- Clangd always returns an error, there is not reason to parse it
return
end
local container = string.format('container: %s', res[1].containerName) ---@type string
local name = string.format('name: %s', res[1].name) ---@type string
vim.lsp.util.open_floating_preview({ name, container }, "", {
height = 2,
width = math.max(string.len(name), string.len(container)),
focusable = false,
focus = false,
border = 'single',
title = 'Symbol Info',
})
end, bufnr)
end
vim.api.nvim_buf_create_user_command(
bufnr,
"ClangdSwitchSourceHeader",
function(arg)
switch_source_header(0)
end,
{desc = "Switch between source/header"}
)
vim.api.nvim_buf_create_user_command(
bufnr,
"ClangdShowSymbolInfo",
function(arg)
symbol_info()
end,
{desc = "Show symbol info"}
)
end
''; '';
}; };
}; };
@ -100,23 +192,10 @@ in {
lsp = { lsp = {
enable = mkEnableOption "clang LSP support" // {default = config.vim.lsp.enable;}; enable = mkEnableOption "clang LSP support" // {default = config.vim.lsp.enable;};
server = mkOption { servers = mkOption {
description = "The clang LSP server to use"; description = "The clang LSP server to use";
type = enum (attrNames servers); type = deprecatedSingleOrListOf "vim.language.clang.lsp.servers" (enum (attrNames servers));
default = defaultServer; default = defaultServers;
};
package = mkOption {
description = "clang LSP server package, or the command to run as a list of strings";
example = ''[lib.getExe pkgs.jdt-language-server " - data " " ~/.cache/jdtls/workspace "]'';
type = either package (listOf str);
default = servers.${cfg.lsp.server}.package;
};
opts = mkOption {
description = "Options to pass to clang LSP server";
type = nullOr str;
default = null;
}; };
}; };
@ -150,9 +229,12 @@ in {
}) })
(mkIf cfg.lsp.enable { (mkIf cfg.lsp.enable {
vim.lsp.lspconfig.enable = true; vim.lsp.servers =
mapListToAttrs (name: {
vim.lsp.lspconfig.sources.clang-lsp = servers.${cfg.lsp.server}.lspConfig; inherit name;
value = servers.${name};
})
cfg.lsp.servers;
}) })
(mkIf cfg.dap.enable { (mkIf cfg.dap.enable {

View file

@ -4,15 +4,25 @@
lib, lib,
... ...
}: let }: let
inherit (builtins) attrNames;
inherit (lib.options) mkEnableOption mkOption; inherit (lib.options) mkEnableOption mkOption;
inherit (lib.modules) mkIf mkMerge; inherit (lib.modules) mkIf mkMerge;
inherit (lib.meta) getExe; inherit (lib.meta) getExe;
inherit (lib.lists) isList; inherit (lib.types) enum listOf;
inherit (lib.types) either listOf package str;
inherit (lib.nvim.types) mkGrammarOption; inherit (lib.nvim.types) mkGrammarOption;
inherit (lib.nvim.lua) expToLua; inherit (lib.nvim.attrsets) mapListToAttrs;
cfg = config.vim.languages.clojure; cfg = config.vim.languages.clojure;
defaultServers = ["clojure-lsp"];
servers = {
clojure-lsp = {
enable = true;
cmd = [(getExe pkgs.clojure-lsp)];
filetypes = ["clojure" "edn"];
root_markers = ["project.clj" "deps.edn" "build.boot" "shadow-cljs.edn" ".git" "bb.edn"];
};
};
in { in {
options.vim.languages.clojure = { options.vim.languages.clojure = {
enable = mkEnableOption "Clojure language support"; enable = mkEnableOption "Clojure language support";
@ -24,28 +34,22 @@ in {
lsp = { lsp = {
enable = mkEnableOption "Clojure LSP support" // {default = config.vim.lsp.enable;}; enable = mkEnableOption "Clojure LSP support" // {default = config.vim.lsp.enable;};
package = mkOption { servers = mkOption {
type = either package (listOf str); type = listOf (enum (attrNames servers));
default = pkgs.clojure-lsp; default = defaultServers;
description = "Clojure LSP"; description = "Clojure LSP server to use";
}; };
}; };
}; };
config = mkIf cfg.enable (mkMerge [ config = mkIf cfg.enable (mkMerge [
(mkIf cfg.lsp.enable { (mkIf cfg.lsp.enable {
vim.lsp.lspconfig.enable = true; vim.lsp.servers =
vim.lsp.lspconfig.sources.clojure-lsp = '' mapListToAttrs (n: {
lspconfig.clojure_lsp.setup { name = n;
capabilities = capabilities; value = servers.${n};
on_attach = default_on_attach; })
cmd = ${ cfg.lsp.servers;
if isList cfg.lsp.package
then expToLua cfg.lsp.package
else ''{"${getExe cfg.lsp.package}"}''
};
}
'';
}) })
(mkIf cfg.treesitter.enable { (mkIf cfg.treesitter.enable {

View file

@ -5,14 +5,16 @@
options, options,
... ...
}: let }: let
inherit (builtins) attrNames; inherit (builtins) attrNames concatMap;
inherit (lib.options) mkEnableOption mkOption; inherit (lib.options) mkEnableOption mkOption;
inherit (lib.types) either listOf package str enum; inherit (lib.types) enum;
inherit (lib.modules) mkIf mkMerge; inherit (lib.modules) mkIf mkMerge;
inherit (lib.lists) isList; inherit (lib.meta) getExe;
inherit (lib.generators) mkLuaInline;
inherit (lib.strings) optionalString; inherit (lib.strings) optionalString;
inherit (lib.nvim.types) mkGrammarOption; inherit (lib.nvim.types) mkGrammarOption deprecatedSingleOrListOf;
inherit (lib.nvim.lua) expToLua; inherit (lib.nvim.lua) toLuaObject;
inherit (lib.nvim.attrsets) mapListToAttrs;
lspKeyConfig = config.vim.lsp.mappings; lspKeyConfig = config.vim.lsp.mappings;
lspKeyOptions = options.vim.lsp.mappings; lspKeyOptions = options.vim.lsp.mappings;
@ -25,58 +27,147 @@
# Omnisharp doesn't have colors in popup docs for some reason, and I've also # Omnisharp doesn't have colors in popup docs for some reason, and I've also
# seen mentions of it being way slower, so until someone finds missing # seen mentions of it being way slower, so until someone finds missing
# functionality, this will be the default. # functionality, this will be the default.
defaultServer = "csharp_ls"; defaultServers = ["csharp_ls"];
servers = { servers = {
omnisharp = { omnisharp = {
package = pkgs.omnisharp-roslyn; cmd = mkLuaInline ''
internalFormatter = true; {
lspConfig = '' ${toLuaObject (getExe pkgs.omnisharp-roslyn)},
lspconfig.omnisharp.setup { '-z', -- https://github.com/OmniSharp/omnisharp-vscode/pull/4300
capabilities = capabilities, '--hostPID',
on_attach = function(client, bufnr) tostring(vim.fn.getpid()),
default_on_attach(client, bufnr) 'DotNet:enablePackageRestore=false',
'--encoding',
local oe = require("omnisharp_extended") 'utf-8',
${mkLspBinding "goToDefinition" "oe.lsp_definition"} '--languageserver',
${mkLspBinding "goToType" "oe.lsp_type_definition"}
${mkLspBinding "listReferences" "oe.lsp_references"}
${mkLspBinding "listImplementations" "oe.lsp_implementation"}
end,
cmd = ${
if isList cfg.lsp.package
then expToLua cfg.lsp.package
else "{'${cfg.lsp.package}/bin/OmniSharp'}"
}
} }
''; '';
filetypes = ["cs" "vb"];
root_dir = mkLuaInline ''
function(bufnr, on_dir)
local function find_root_pattern(fname, lua_pattern)
return vim.fs.root(0, function(name, path)
return name:match(lua_pattern)
end)
end
local fname = vim.api.nvim_buf_get_name(bufnr)
on_dir(find_root_pattern(fname, "%.sln$") or find_root_pattern(fname, "%.csproj$"))
end
'';
init_options = {};
capabilities = {
workspace = {
workspaceFolders = false; # https://github.com/OmniSharp/omnisharp-roslyn/issues/909
};
};
on_attach = mkLuaInline ''
function(client, bufnr)
local oe = require("omnisharp_extended")
${mkLspBinding "goToDefinition" "oe.lsp_definition"}
${mkLspBinding "goToType" "oe.lsp_type_definition"}
${mkLspBinding "listReferences" "oe.lsp_references"}
${mkLspBinding "listImplementations" "oe.lsp_implementation"}
end
'';
settings = {
FormattingOptions = {
# Enables support for reading code style, naming convention and analyzer
# settings from .editorconfig.
EnableEditorConfigSupport = true;
# Specifies whether 'using' directives should be grouped and sorted during
# document formatting.
OrganizeImports = null;
};
MsBuild = {
# If true, MSBuild project system will only load projects for files that
# were opened in the editor. This setting is useful for big C# codebases
# and allows for faster initialization of code navigation features only
# for projects that are relevant to code that is being edited. With this
# setting enabled OmniSharp may load fewer projects and may thus display
# incomplete reference lists for symbols.
LoadProjectsOnDemand = null;
};
RoslynExtensionsOptions = {
# Enables support for roslyn analyzers, code fixes and rulesets.
EnableAnalyzersSupport = null;
# Enables support for showing unimported types and unimported extension
# methods in completion lists. When committed, the appropriate using
# directive will be added at the top of the current file. This option can
# have a negative impact on initial completion responsiveness;
# particularly for the first few completion sessions after opening a
# solution.
EnableImportCompletion = null;
# Only run analyzers against open files when 'enableRoslynAnalyzers' is
# true
AnalyzeOpenDocumentsOnly = null;
# Enables the possibility to see the code in external nuget dependencies
EnableDecompilationSupport = null;
};
RenameOptions = {
RenameInComments = null;
RenameOverloads = null;
RenameInStrings = null;
};
Sdk = {
# Specifies whether to include preview versions of the .NET SDK when
# determining which version to use for project loading.
IncludePrereleases = true;
};
};
}; };
csharp_ls = { csharp_ls = {
package = pkgs.csharp-ls; cmd = [(lib.getExe pkgs.csharp-ls)];
internalFormatter = true; filetypes = ["cs"];
lspConfig = '' root_dir = mkLuaInline ''
local extended_handler = require("csharpls_extended").handler function(bufnr, on_dir)
local function find_root_pattern(fname, lua_pattern)
return vim.fs.root(0, function(name, path)
return name:match(lua_pattern)
end)
end
lspconfig.csharp_ls.setup { local fname = vim.api.nvim_buf_get_name(bufnr)
capabilities = capabilities, on_dir(find_root_pattern(fname, "%.sln$") or find_root_pattern(fname, "%.csproj$"))
on_attach = default_on_attach, end
handlers = { '';
["textDocument/definition"] = extended_handler, init_options = {
["textDocument/typeDefinition"] = extended_handler AutomaticWorkspaceInit = true;
}, };
cmd = ${ };
if isList cfg.lsp.package
then expToLua cfg.lsp.package roslyn_ls = {
else "{'${cfg.lsp.package}/bin/csharp-ls'}" cmd = mkLuaInline ''
} {
${toLuaObject (getExe pkgs.roslyn-ls)},
'--logLevel=Warning',
'--extensionLogDirectory=' .. vim.fs.dirname(vim.lsp.get_log_path()),
'--stdio',
} }
''; '';
filetypes = ["cs"];
root_dir = mkLuaInline ''
function(bufnr, on_dir)
local function find_root_pattern(fname, lua_pattern)
return vim.fs.root(0, function(name, path)
return name:match(lua_pattern)
end)
end
local fname = vim.api.nvim_buf_get_name(bufnr)
on_dir(find_root_pattern(fname, "%.sln$") or find_root_pattern(fname, "%.csproj$"))
end
'';
init_options = {};
}; };
}; };
extraServerPlugins = { extraServerPlugins = {
omnisharp = ["omnisharp-extended-lsp-nvim"]; omnisharp = ["omnisharp-extended-lsp-nvim"];
csharp_ls = ["csharpls-extended-lsp-nvim"]; csharp_ls = ["csharpls-extended-lsp-nvim"];
roslyn_ls = [];
}; };
cfg = config.vim.languages.csharp; cfg = config.vim.languages.csharp;
@ -87,21 +178,15 @@ in {
treesitter = { treesitter = {
enable = mkEnableOption "C# treesitter" // {default = config.vim.languages.enableTreesitter;}; enable = mkEnableOption "C# treesitter" // {default = config.vim.languages.enableTreesitter;};
package = mkGrammarOption pkgs "c-sharp"; package = mkGrammarOption pkgs "c_sharp";
}; };
lsp = { lsp = {
enable = mkEnableOption "C# LSP support" // {default = config.vim.lsp.enable;}; enable = mkEnableOption "C# LSP support" // {default = config.vim.lsp.enable;};
server = mkOption { servers = mkOption {
description = "C# LSP server to use"; description = "C# LSP server to use";
type = enum (attrNames servers); type = deprecatedSingleOrListOf "vim.language.csharp.lsp.servers" (enum (attrNames servers));
default = defaultServer; default = defaultServers;
};
package = mkOption {
description = "C# LSP server package, or the command to run as a list of strings";
type = either package (listOf str);
default = servers.${cfg.lsp.server}.package;
}; };
}; };
}; };
@ -114,9 +199,13 @@ in {
}) })
(mkIf cfg.lsp.enable { (mkIf cfg.lsp.enable {
vim.startPlugins = extraServerPlugins.${cfg.lsp.server} or []; vim.startPlugins = concatMap (server: extraServerPlugins.${server}) cfg.lsp.servers;
vim.lsp.lspconfig.enable = true; vim.lsp.servers =
vim.lsp.lspconfig.sources.csharp-lsp = servers.${cfg.lsp.server}.lspConfig; mapListToAttrs (name: {
inherit name;
value = servers.${name};
})
cfg.lsp.servers;
}) })
]); ]);
} }

View file

@ -8,65 +8,40 @@
inherit (lib.options) mkEnableOption mkOption; inherit (lib.options) mkEnableOption mkOption;
inherit (lib.meta) getExe; inherit (lib.meta) getExe;
inherit (lib.modules) mkIf mkMerge; inherit (lib.modules) mkIf mkMerge;
inherit (lib.lists) isList; inherit (lib.types) enum;
inherit (lib.types) enum either listOf package str; inherit (lib.nvim.types) mkGrammarOption deprecatedSingleOrListOf;
inherit (lib.nvim.types) mkGrammarOption; inherit (lib.nvim.attrsets) mapListToAttrs;
inherit (lib.nvim.lua) expToLua;
cfg = config.vim.languages.css; cfg = config.vim.languages.css;
defaultServer = "vscode-langservers-extracted"; defaultServer = ["cssls"];
servers = { servers = {
vscode-langservers-extracted = { cssls = {
package = pkgs.vscode-langservers-extracted; cmd = ["${pkgs.vscode-langservers-extracted}/bin/vscode-css-language-server" "--stdio"];
lspConfig = '' filetypes = ["css" "scss" "less"];
-- enable (broadcasting) snippet capability for completion # needed to enable formatting
-- see <https://github.com/neovim/nvim-lspconfig/blob/master/doc/server_configurations.md#cssls> init_options = {provideFormatter = true;};
local css_capabilities = vim.lsp.protocol.make_client_capabilities() root_markers = [".git" "package.json"];
css_capabilities.textDocument.completion.completionItem.snippetSupport = true settings = {
css.validate = true;
-- cssls setup scss.validate = true;
lspconfig.cssls.setup { less.validate = true;
capabilities = css_capabilities; };
on_attach = default_on_attach;
cmd = ${
if isList cfg.lsp.package
then expToLua cfg.lsp.package
else ''{"${cfg.lsp.package}/bin/vscode-css-language-server", "--stdio"}''
}
}
'';
}; };
}; };
defaultFormat = "prettier"; defaultFormat = ["prettier"];
formats = { formats = {
prettier = { prettier = {
package = pkgs.prettier; command = getExe pkgs.prettier;
}; };
prettierd = { prettierd = {
package = pkgs.prettierd; command = getExe pkgs.prettierd;
nullConfig = ''
table.insert(
ls_sources,
null_ls.builtins.formatting.prettier.with({
command = "${cfg.format.package}/bin/prettierd",
})
)
'';
}; };
biome = { biome = {
package = pkgs.biome; command = getExe pkgs.biome;
nullConfig = ''
table.insert(
ls_sources,
null_ls.builtins.formatting.biome.with({
command = "${cfg.format.package}/bin/biome",
})
)
'';
}; };
}; };
in { in {
@ -82,17 +57,10 @@ in {
lsp = { lsp = {
enable = mkEnableOption "CSS LSP support" // {default = config.vim.lsp.enable;}; enable = mkEnableOption "CSS LSP support" // {default = config.vim.lsp.enable;};
server = mkOption { servers = mkOption {
description = "CSS LSP server to use"; type = deprecatedSingleOrListOf "vim.language.css.lsp.servers" (enum (attrNames servers));
type = enum (attrNames servers);
default = defaultServer; default = defaultServer;
}; description = "CSS LSP server to use";
package = mkOption {
description = "CSS LSP server package, or the command to run as a list of strings";
example = ''[lib.getExe pkgs.jdt-language-server " - data " " ~/.cache/jdtls/workspace "]'';
type = either package (listOf str);
default = servers.${cfg.lsp.server}.package;
}; };
}; };
@ -101,15 +69,9 @@ in {
type = mkOption { type = mkOption {
description = "CSS formatter to use"; description = "CSS formatter to use";
type = enum (attrNames formats); type = deprecatedSingleOrListOf "vim.language.css.format.type" (enum (attrNames formats));
default = defaultFormat; default = defaultFormat;
}; };
package = mkOption {
description = "CSS formatter package";
type = package;
default = formats.${cfg.format.type}.package;
};
}; };
}; };
@ -120,16 +82,25 @@ in {
}) })
(mkIf cfg.lsp.enable { (mkIf cfg.lsp.enable {
vim.lsp.lspconfig.enable = true; vim.lsp.servers =
vim.lsp.lspconfig.sources.css-lsp = servers.${cfg.lsp.server}.lspConfig; mapListToAttrs (name: {
inherit name;
value = servers.${name};
})
cfg.lsp.servers;
}) })
(mkIf cfg.format.enable { (mkIf cfg.format.enable {
vim.formatter.conform-nvim = { vim.formatter.conform-nvim = {
enable = true; enable = true;
setupOpts.formatters_by_ft.css = [cfg.format.type]; setupOpts = {
setupOpts.formatters.${cfg.format.type} = { formatters_by_ft.css = cfg.format.type;
command = getExe cfg.format.package; formatters =
mapListToAttrs (name: {
inherit name;
value = formats.${name};
})
cfg.format.type;
}; };
}; };
}) })

View file

@ -4,11 +4,17 @@
lib, lib,
... ...
}: let }: let
inherit (lib.options) mkEnableOption mkOption; inherit (lib.options) mkEnableOption;
inherit (lib.meta) getExe;
inherit (lib.modules) mkIf mkMerge; inherit (lib.modules) mkIf mkMerge;
inherit (lib.types) package;
inherit (lib.nvim.types) mkGrammarOption; inherit (lib.nvim.types) mkGrammarOption;
lspOptions = {
cmd = [(getExe pkgs.cue) "lsp"];
filetypes = ["cue"];
root_markers = ["cue.mod" ".git"];
};
cfg = config.vim.languages.cue; cfg = config.vim.languages.cue;
in { in {
options.vim.languages.cue = { options.vim.languages.cue = {
@ -22,12 +28,6 @@ in {
lsp = { lsp = {
enable = mkEnableOption "CUE LSP support" // {default = config.vim.lsp.enable;}; enable = mkEnableOption "CUE LSP support" // {default = config.vim.lsp.enable;};
package = mkOption {
type = package;
default = pkgs.cue;
description = "cue lsp implementation";
};
}; };
}; };
@ -38,14 +38,7 @@ in {
}) })
(mkIf cfg.lsp.enable { (mkIf cfg.lsp.enable {
vim.lsp.lspconfig.enable = true; vim.lsp.servers.cue = lspOptions;
vim.lsp.lspconfig.sources.cue-lsp = ''
lspconfig.cue.setup {
capabilities = capabilities,
on_attach = default_on_attach,
cmd = {"${cfg.lsp.package}/bin/cue", "lsp"},
}
'';
}) })
]); ]);
} }

View file

@ -6,34 +6,38 @@
}: let }: let
inherit (builtins) attrNames; inherit (builtins) attrNames;
inherit (lib.modules) mkIf mkMerge; inherit (lib.modules) mkIf mkMerge;
inherit (lib.meta) getExe;
inherit (lib.trivial) boolToString; inherit (lib.trivial) boolToString;
inherit (lib.lists) isList;
inherit (lib.options) mkEnableOption mkOption; inherit (lib.options) mkEnableOption mkOption;
inherit (lib.types) enum either listOf package nullOr str bool; inherit (lib.types) enum package nullOr str bool;
inherit (lib.strings) optionalString; inherit (lib.strings) optionalString;
inherit (lib.nvim.lua) expToLua; inherit (lib.nvim.types) mkGrammarOption deprecatedSingleOrListOf;
inherit (lib.nvim.types) mkGrammarOption;
inherit (lib.nvim.dag) entryAfter; inherit (lib.nvim.dag) entryAfter;
inherit (lib.nvim.attrsets) mapListToAttrs;
cfg = config.vim.languages.dart; cfg = config.vim.languages.dart;
ftcfg = cfg.flutter-tools; ftcfg = cfg.flutter-tools;
defaultServer = "dart"; defaultServers = ["dart"];
servers = { servers = {
dart = { dart = {
package = pkgs.dart; enable = true;
lspConfig = '' cmd = [(getExe pkgs.dart) "language-server" "--protocol=lsp"];
lspconfig.dartls.setup{ filetypes = ["dart"];
capabilities = capabilities; root_markers = ["pubspec.yaml"];
on_attach=default_on_attach; init_options = {
cmd = ${ onlyAnalyzeProjectsWithOpenFiles = true;
if isList cfg.lsp.package suggestFromUnimportedLibraries = true;
then expToLua cfg.lsp.package closingLabels = true;
else ''{"${cfg.lsp.package}/bin/dart", "language-server", "--protocol=lsp"}'' outline = true;
flutterOutline = true;
};
settings = {
dart = {
completeFunctionCalls = true;
showTodos = true;
}; };
${optionalString (cfg.lsp.opts != null) "init_options = ${cfg.lsp.dartOpts}"} };
}
'';
}; };
}; };
in { in {
@ -46,23 +50,11 @@ in {
}; };
lsp = { lsp = {
enable = mkEnableOption "Dart LSP support"; enable = mkEnableOption "Dart LSP support" // {default = config.vim.lsp.enable;};
server = mkOption { servers = mkOption {
description = "The Dart LSP server to use"; type = deprecatedSingleOrListOf "vim.language.dart.lsp.servers" (enum (attrNames servers));
type = enum (attrNames servers); default = defaultServers;
default = defaultServer; description = "Dart LSP server to use";
};
package = mkOption {
type = either package (listOf str);
default = servers.${cfg.lsp.server}.package;
example = ''[lib.getExe pkgs.jdt-language-server "-data" "~/.cache/jdtls/workspace"]'';
description = "Dart LSP server package, or the command to run as a list of strings";
};
opts = mkOption {
type = nullOr str;
default = null;
description = "Options to pass to Dart LSP server";
}; };
}; };
@ -131,19 +123,23 @@ in {
}; };
}; };
config.vim = mkIf cfg.enable (mkMerge [ config = mkIf cfg.enable (mkMerge [
(mkIf cfg.treesitter.enable { (mkIf cfg.treesitter.enable {
treesitter.enable = true; vim.treesitter.enable = true;
treesitter.grammars = [cfg.treesitter.package]; vim.treesitter.grammars = [cfg.treesitter.package];
}) })
(mkIf cfg.lsp.enable { (mkIf cfg.lsp.enable {
lsp.lspconfig.enable = true; vim.lsp.servers =
lsp.lspconfig.sources.dart-lsp = servers.${cfg.lsp.server}.lspConfig; mapListToAttrs (n: {
name = n;
value = servers.${n};
})
cfg.lsp.servers;
}) })
(mkIf ftcfg.enable { (mkIf ftcfg.enable {
startPlugins = [ vim.startPlugins = [
( (
if ftcfg.enableNoResolvePatch if ftcfg.enableNoResolvePatch
then "flutter-tools-patched" then "flutter-tools-patched"
@ -152,7 +148,7 @@ in {
"plenary-nvim" "plenary-nvim"
]; ];
pluginRC.flutter-tools = entryAfter ["lsp-setup"] '' vim.pluginRC.flutter-tools = entryAfter ["lsp-servers"] ''
require('flutter-tools').setup { require('flutter-tools').setup {
${optionalString (ftcfg.flutterPackage != null) "flutter_path = \"${ftcfg.flutterPackage}/bin/flutter\","} ${optionalString (ftcfg.flutterPackage != null) "flutter_path = \"${ftcfg.flutterPackage}/bin/flutter\","}
lsp = { lsp = {
@ -165,7 +161,6 @@ in {
}, },
capabilities = capabilities, capabilities = capabilities,
on_attach = default_on_attach;
}, },
${optionalString cfg.dap.enable '' ${optionalString cfg.dap.enable ''
debugger = { debugger = {

View file

@ -21,6 +21,7 @@ in {
./html.nix ./html.nix
./haskell.nix ./haskell.nix
./java.nix ./java.nix
./json.nix
./lua.nix ./lua.nix
./markdown.nix ./markdown.nix
./nim.nix ./nim.nix
@ -29,6 +30,7 @@ in {
./ocaml.nix ./ocaml.nix
./php.nix ./php.nix
./python.nix ./python.nix
./qml.nix
./r.nix ./r.nix
./rust.nix ./rust.nix
./scala.nix ./scala.nix
@ -36,6 +38,7 @@ in {
./svelte.nix ./svelte.nix
./tailwind.nix ./tailwind.nix
./terraform.nix ./terraform.nix
./toml.nix
./ts.nix ./ts.nix
./typst.nix ./typst.nix
./zig.nix ./zig.nix
@ -46,6 +49,7 @@ in {
./wgsl.nix ./wgsl.nix
./yaml.nix ./yaml.nix
./ruby.nix ./ruby.nix
./just.nix
# This is now a hard deprecation. # This is now a hard deprecation.
(mkRenamedOptionModule ["vim" "languages" "enableLSP"] ["vim" "lsp" "enable"]) (mkRenamedOptionModule ["vim" "languages" "enableLSP"] ["vim" "lsp" "enable"])

View file

@ -7,40 +7,43 @@
inherit (builtins) attrNames; inherit (builtins) attrNames;
inherit (lib.options) mkEnableOption mkOption; inherit (lib.options) mkEnableOption mkOption;
inherit (lib.modules) mkIf mkMerge; inherit (lib.modules) mkIf mkMerge;
inherit (lib.lists) isList; inherit (lib.meta) getExe;
inherit (lib.types) enum either listOf package str; inherit (lib.types) enum;
inherit (lib.nvim.types) mkGrammarOption; inherit (lib.generators) mkLuaInline;
inherit (lib.nvim.lua) expToLua; inherit (lib.nvim.types) mkGrammarOption deprecatedSingleOrListOf;
inherit (lib.nvim.dag) entryAnywhere; inherit (lib.nvim.dag) entryAnywhere;
inherit (lib.nvim.attrsets) mapListToAttrs;
cfg = config.vim.languages.elixir; cfg = config.vim.languages.elixir;
defaultServer = "elixirls"; defaultServers = ["elixirls"];
servers = { servers = {
elixirls = { elixirls = {
package = pkgs.elixir-ls; enable = true;
lspConfig = '' cmd = [(getExe pkgs.elixir-ls)];
-- elixirls setup filetypes = ["elixir" "eelixir" "heex" "surface"];
lspconfig.elixirls.setup { root_dir =
capabilities = capabilities, mkLuaInline
on_attach = default_on_attach, /*
cmd = ${ lua
if isList cfg.lsp.package */
then expToLua cfg.lsp.package ''
else ''{"${cfg.lsp.package}/bin/elixir-ls"}'' function(bufnr, on_dir)
} local fname = vim.api.nvim_buf_get_name(bufnr)
} local matches = vim.fs.find({ 'mix.exs' }, { upward = true, limit = 2, path = fname })
''; local child_or_root_path, maybe_umbrella_path = unpack(matches)
local root_dir = vim.fs.dirname(maybe_umbrella_path or child_or_root_path)
on_dir(root_dir)
end
'';
}; };
}; };
defaultFormat = "mix"; defaultFormat = ["mix"];
formats = { formats = {
mix = { mix = {
package = pkgs.elixir; command = "${pkgs.elixir}/bin/mix";
config = {
command = "${cfg.format.package}/bin/mix";
};
}; };
}; };
in { in {
@ -50,22 +53,16 @@ in {
treesitter = { treesitter = {
enable = mkEnableOption "Elixir treesitter" // {default = config.vim.languages.enableTreesitter;}; enable = mkEnableOption "Elixir treesitter" // {default = config.vim.languages.enableTreesitter;};
package = mkGrammarOption pkgs "elixir"; package = mkGrammarOption pkgs "elixir";
heexPackage = mkGrammarOption pkgs "heex";
eexPackage = mkGrammarOption pkgs "eex";
}; };
lsp = { lsp = {
enable = mkEnableOption "Elixir LSP support" // {default = config.vim.lsp.enable;}; enable = mkEnableOption "Elixir LSP support" // {default = config.vim.lsp.enable;};
servers = mkOption {
server = mkOption { type = deprecatedSingleOrListOf "vim.language.elixir.lsp.servers" (enum (attrNames servers));
default = defaultServers;
description = "Elixir LSP server to use"; description = "Elixir LSP server to use";
type = enum (attrNames servers);
default = defaultServer;
};
package = mkOption {
description = "Elixir LSP server package, or the command to run as a list of strings";
example = ''[lib.getExe pkgs.jdt-language-server " - data " " ~/.cache/jdtls/workspace "]'';
type = either package (listOf str);
default = servers.${cfg.lsp.server}.package;
}; };
}; };
@ -73,15 +70,9 @@ in {
enable = mkEnableOption "Elixir formatting" // {default = config.vim.languages.enableFormat;}; enable = mkEnableOption "Elixir formatting" // {default = config.vim.languages.enableFormat;};
type = mkOption { type = mkOption {
description = "Elixir formatter to use"; type = deprecatedSingleOrListOf "vim.language.elixir.format.type" (enum (attrNames formats));
type = enum (attrNames formats);
default = defaultFormat; default = defaultFormat;
}; description = "Elixir formatter to use";
package = mkOption {
description = "Elixir formatter package";
type = package;
default = formats.${cfg.format.type}.package;
}; };
}; };
@ -93,20 +84,34 @@ in {
config = mkIf cfg.enable (mkMerge [ config = mkIf cfg.enable (mkMerge [
(mkIf cfg.treesitter.enable { (mkIf cfg.treesitter.enable {
vim.treesitter.enable = true; vim.treesitter.enable = true;
vim.treesitter.grammars = [cfg.treesitter.package]; vim.treesitter.grammars = [
cfg.treesitter.package
cfg.treesitter.heexPackage
cfg.treesitter.eexPackage
];
}) })
(mkIf cfg.lsp.enable { (mkIf cfg.lsp.enable {
vim.lsp.lspconfig.enable = true; vim.lsp.servers =
vim.lsp.lspconfig.sources.elixir-lsp = servers.${cfg.lsp.server}.lspConfig; mapListToAttrs (n: {
name = n;
value = servers.${n};
})
cfg.lsp.servers;
}) })
(mkIf cfg.format.enable { (mkIf cfg.format.enable {
vim.formatter.conform-nvim = { vim.formatter.conform-nvim = {
enable = true; enable = true;
setupOpts.formatters_by_ft.elixir = [cfg.format.type]; setupOpts = {
setupOpts.formatters.${cfg.format.type} = formatters_by_ft.elixir = cfg.format.type;
formats.${cfg.format.type}.config; formatters =
mapListToAttrs (name: {
inherit name;
value = formats.${name};
})
cfg.format.type;
};
}; };
}) })

View file

@ -6,36 +6,55 @@
}: let }: let
inherit (builtins) attrNames; inherit (builtins) attrNames;
inherit (lib.options) mkEnableOption mkOption; inherit (lib.options) mkEnableOption mkOption;
inherit (lib.types) either listOf package str enum; inherit (lib.types) enum;
inherit (lib.meta) getExe; inherit (lib.meta) getExe;
inherit (lib.modules) mkIf mkMerge; inherit (lib.modules) mkIf mkMerge;
inherit (lib.lists) isList; inherit (lib.generators) mkLuaInline;
inherit (lib.nvim.types) mkGrammarOption; inherit (lib.nvim.types) mkGrammarOption deprecatedSingleOrListOf;
inherit (lib.nvim.lua) expToLua; inherit (lib.nvim.attrsets) mapListToAttrs;
defaultServer = "fsautocomplete"; defaultServer = ["fsautocomplete"];
servers = { servers = {
fsautocomplete = { fsautocomplete = {
package = pkgs.fsautocomplete; cmd = [(getExe pkgs.fsautocomplete) "--adaptive-lsp-server-enabled"];
internalFormatter = false; filetypes = ["fsharp"];
lspConfig = '' root_dir = mkLuaInline ''
lspconfig.fsautocomplete.setup { function(bufnr, on_dir)
capabilities = capabilities; on_dir(vim.fs.root(bufnr, function(name, path)
on_attach = default_on_attach; return name == ".git" or name:match("%.sln$") or name:match("%.fsproj$")
cmd = ${ end))
if isList cfg.lsp.package end
then expToLua cfg.lsp.package
else "{'${cfg.lsp.package}/bin/fsautocomplete'}"
},
}
''; '';
init_options = {
AutomaticWorkspaceInit = true;
};
settings = {
FSharp = {
keywordsAutocomplete = true;
ExternalAutocomplete = false;
Linter = true;
UnionCaseStubGeneration = true;
UnionCaseStubGenerationBody = ''failwith "Not Implemented"'';
RecordStubGeneration = true;
RecordStubGenerationBody = ''failwith "Not Implemented"'';
InterfaceStubGeneration = true;
InterfaceStubGenerationObjectIdentifier = "this";
InterfaceStubGenerationMethodBody = ''failwith "Not Implemented"'';
UnusedOpensAnalyzer = true;
UnusedDeclarationsAnalyzer = true;
UseSdkScripts = true;
SimplifyNameAnalyzer = true;
ResolveNamespaces = true;
EnableReferenceCodeLens = true;
};
};
}; };
}; };
defaultFormat = "fantomas"; defaultFormat = ["fantomas"];
formats = { formats = {
fantomas = { fantomas = {
package = pkgs.fantomas; command = getExe pkgs.fantomas;
}; };
}; };
@ -52,33 +71,20 @@ in {
lsp = { lsp = {
enable = mkEnableOption "F# LSP support" // {default = config.vim.lsp.enable;}; enable = mkEnableOption "F# LSP support" // {default = config.vim.lsp.enable;};
server = mkOption { servers = mkOption {
type = enum (attrNames servers); type = deprecatedSingleOrListOf "vim.language.fsharp.lsp.servers" (enum (attrNames servers));
default = defaultServer; default = defaultServer;
description = "F# LSP server to use"; description = "F# LSP server to use";
}; };
package = mkOption {
type = either package (listOf str);
default = servers.${cfg.lsp.server}.package;
example = ''[lib.getExe pkgs.fsautocomplete "--state-directory" "~/.cache/fsautocomplete"]'';
description = "F# LSP server package, or the command to run as a list of strings";
};
}; };
format = { format = {
enable = mkEnableOption "F# formatting" // {default = config.vim.languages.enableFormat;}; enable = mkEnableOption "F# formatting" // {default = config.vim.languages.enableFormat;};
type = mkOption { type = mkOption {
type = enum (attrNames formats); type = deprecatedSingleOrListOf "vim.language.fsharp.format.type" (enum (attrNames formats));
default = defaultFormat; default = defaultFormat;
description = "F# formatter to use"; description = "F# formatter to use";
}; };
package = mkOption {
type = package;
default = formats.${cfg.format.type}.package;
description = "F# formatter package";
};
}; };
}; };
}; };
@ -90,16 +96,25 @@ in {
}) })
(mkIf cfg.lsp.enable { (mkIf cfg.lsp.enable {
vim.lsp.lspconfig.enable = true; vim.lsp.servers =
vim.lsp.lspconfig.sources.fsharp-lsp = servers.${cfg.lsp.server}.lspConfig; mapListToAttrs (name: {
inherit name;
value = servers.${name};
})
cfg.lsp.servers;
}) })
(mkIf cfg.format.enable { (mkIf cfg.format.enable {
vim.formatter.conform-nvim = { vim.formatter.conform-nvim = {
enable = true; enable = true;
setupOpts.formatters_by_ft.fsharp = [cfg.format.type]; setupOpts = {
setupOpts.formatters.${cfg.format.type} = { formatters_by_ft.fsharp = cfg.format.type;
command = getExe cfg.format.package; formatters =
mapListToAttrs (name: {
inherit name;
value = formats.${name};
})
cfg.format.type;
}; };
}; };
}) })

View file

@ -7,28 +7,20 @@
inherit (builtins) attrNames; inherit (builtins) attrNames;
inherit (lib.options) mkEnableOption mkOption; inherit (lib.options) mkEnableOption mkOption;
inherit (lib.modules) mkIf mkMerge; inherit (lib.modules) mkIf mkMerge;
inherit (lib.lists) isList; inherit (lib.meta) getExe;
inherit (lib.types) enum either listOf package str; inherit (lib.types) enum;
inherit (lib.nvim.lua) expToLua; inherit (lib.nvim.types) mkGrammarOption deprecatedSingleOrListOf;
inherit (lib.nvim.types) mkGrammarOption; inherit (lib.nvim.attrsets) mapListToAttrs;
cfg = config.vim.languages.gleam; cfg = config.vim.languages.gleam;
defaultServer = "gleam"; defaultServers = ["gleam"];
servers = { servers = {
gleam = { gleam = {
package = pkgs.gleam; enable = true;
lspConfig = '' cmd = [(getExe pkgs.gleam) "lsp"];
lspconfig.gleam.setup{ filetypes = ["gleam"];
capabilities = capabilities, root_markers = ["gleam.toml" ".git"];
on_attach = default_on_attach,
cmd = ${
if isList cfg.lsp.package
then expToLua cfg.lsp.package
else ''{"${cfg.lsp.package}/bin/gleam", "lsp"}''
}
}
'';
}; };
}; };
in { in {
@ -42,18 +34,11 @@ in {
lsp = { lsp = {
enable = mkEnableOption "Gleam LSP support" // {default = config.vim.lsp.enable;}; enable = mkEnableOption "Gleam LSP support" // {default = config.vim.lsp.enable;};
servers = mkOption {
server = mkOption { type = deprecatedSingleOrListOf "vim.language.gleam.lsp.servers" (enum (attrNames servers));
type = enum (attrNames servers); default = defaultServers;
default = defaultServer;
description = "Gleam LSP server to use"; description = "Gleam LSP server to use";
}; };
package = mkOption {
type = either package (listOf str);
default = servers.${cfg.lsp.server}.package;
description = "Gleam LSP server package, or the command to run as a list of strings";
};
}; };
}; };
@ -64,8 +49,12 @@ in {
}) })
(mkIf cfg.lsp.enable { (mkIf cfg.lsp.enable {
vim.lsp.lspconfig.enable = true; vim.lsp.servers =
vim.lsp.lspconfig.sources.gleam-lsp = servers.${cfg.lsp.server}.lspConfig; mapListToAttrs (n: {
name = n;
value = servers.${n};
})
cfg.lsp.servers;
}) })
]); ]);
} }

View file

@ -8,45 +8,67 @@
inherit (lib.options) mkEnableOption mkOption literalMD; inherit (lib.options) mkEnableOption mkOption literalMD;
inherit (lib.modules) mkIf mkMerge; inherit (lib.modules) mkIf mkMerge;
inherit (lib.meta) getExe; inherit (lib.meta) getExe;
inherit (lib.lists) isList; inherit (lib.generators) mkLuaInline;
inherit (lib.types) bool enum either listOf package str; inherit (lib.types) bool enum package;
inherit (lib.nvim.types) mkGrammarOption; inherit (lib.nvim.types) mkGrammarOption deprecatedSingleOrListOf;
inherit (lib.nvim.lua) expToLua;
inherit (lib.nvim.dag) entryAfter; inherit (lib.nvim.dag) entryAfter;
inherit (lib.nvim.attrsets) mapListToAttrs;
cfg = config.vim.languages.go; cfg = config.vim.languages.go;
defaultServer = "gopls"; defaultServers = ["gopls"];
servers = { servers = {
gopls = { gopls = {
package = pkgs.gopls; cmd = [(getExe pkgs.gopls)];
lspConfig = '' filetypes = ["go" "gomod" "gowork" "gotmpl"];
lspconfig.gopls.setup { root_dir = mkLuaInline ''
capabilities = capabilities; function(bufnr, on_dir)
on_attach = default_on_attach; local fname = vim.api.nvim_buf_get_name(bufnr)
cmd = ${
if isList cfg.lsp.package local function get_root(fname)
then expToLua cfg.lsp.package if _G.nvf_gopls_mod_cache and fname:sub(1, #_G.nvf_gopls_mod_cache) == _G.nvf_gopls_mod_cache then
else ''{"${cfg.lsp.package}/bin/gopls", "serve"}'' local clients = vim.lsp.get_clients { name = 'gopls' }
}, if #clients > 0 then
} return clients[#clients].config.root_dir
end
end
return vim.fs.root(fname, 'go.work') or vim.fs.root(fname, 'go.mod') or vim.fs.root(fname, '.git')
end
-- see: https://github.com/neovim/nvim-lspconfig/issues/804
if _G.nvf_gopls_mod_cache then
on_dir(get_root(fname))
return
end
local cmd = { 'go', 'env', 'GOMODCACHE' }
local ok, err = pcall(vim.system, cmd, { text = true }, function(output)
if output.code == 0 then
if output.stdout then
_G.nvf_gopls_mod_cache = vim.trim(output.stdout)
end
on_dir(get_root(fname))
else
vim.schedule(function()
vim.notify(('[gopls] cmd failed with code %d: %s\n%s'):format(output.code, cmd, output.stderr))
end)
end
end)
if not ok then vim.notify(('[gopls] cmd failed: %s\n%s'):format(cmd, err)) end
end
''; '';
}; };
}; };
defaultFormat = "gofmt"; defaultFormat = ["gofmt"];
formats = { formats = {
gofmt = { gofmt = {
package = pkgs.go; command = "${pkgs.go}/bin/gofmt";
config.command = "${cfg.format.package}/bin/gofmt";
}; };
gofumpt = { gofumpt = {
package = pkgs.gofumpt; command = getExe pkgs.gofumpt;
config.command = getExe cfg.format.package;
}; };
golines = { golines = {
package = pkgs.golines; command = "${pkgs.golines}/bin/golines";
config.command = "${cfg.format.package}/bin/golines";
}; };
}; };
@ -69,17 +91,10 @@ in {
lsp = { lsp = {
enable = mkEnableOption "Go LSP support" // {default = config.vim.lsp.enable;}; enable = mkEnableOption "Go LSP support" // {default = config.vim.lsp.enable;};
server = mkOption { servers = mkOption {
type = deprecatedSingleOrListOf "vim.language.go.lsp.servers" (enum (attrNames servers));
default = defaultServers;
description = "Go LSP server to use"; description = "Go LSP server to use";
type = enum (attrNames servers);
default = defaultServer;
};
package = mkOption {
description = "Go LSP server package, or the command to run as a list of strings";
example = ''[lib.getExe pkgs.jdt-language-server " - data " " ~/.cache/jdtls/workspace "]'';
type = either package (listOf str);
default = servers.${cfg.lsp.server}.package;
}; };
}; };
@ -95,15 +110,9 @@ in {
type = mkOption { type = mkOption {
description = "Go formatter to use"; description = "Go formatter to use";
type = enum (attrNames formats); type = deprecatedSingleOrListOf "vim.language.go.format.type" (enum (attrNames formats));
default = defaultFormat; default = defaultFormat;
}; };
package = mkOption {
description = "Go formatter package";
type = package;
default = formats.${cfg.format.type}.package;
};
}; };
dap = { dap = {
@ -134,15 +143,26 @@ in {
}) })
(mkIf cfg.lsp.enable { (mkIf cfg.lsp.enable {
vim.lsp.lspconfig.enable = true; vim.lsp.servers =
vim.lsp.lspconfig.sources.go-lsp = servers.${cfg.lsp.server}.lspConfig; mapListToAttrs (name: {
inherit name;
value = servers.${name};
})
cfg.lsp.servers;
}) })
(mkIf cfg.format.enable { (mkIf cfg.format.enable {
vim.formatter.conform-nvim = { vim.formatter.conform-nvim = {
enable = true; enable = true;
setupOpts.formatters_by_ft.go = [cfg.format.type]; setupOpts = {
setupOpts.formatters.${cfg.format.type} = formats.${cfg.format.type}.config; formatters_by_ft.go = cfg.format.type;
formatters =
mapListToAttrs (name: {
inherit name;
value = formats.${name};
})
cfg.format.type;
};
}; };
}) })

View file

@ -4,17 +4,64 @@
pkgs, pkgs,
... ...
}: let }: let
inherit (builtins) isList; inherit (builtins) isList attrNames;
inherit (lib.types) either package listOf str; inherit (lib.types) either package enum listOf str;
inherit (lib.options) mkEnableOption mkOption; inherit (lib.options) mkEnableOption mkOption;
inherit (lib.strings) optionalString; inherit (lib.strings) optionalString;
inherit (lib.modules) mkIf mkMerge; inherit (lib.modules) mkIf mkMerge;
inherit (lib.nvim.types) mkGrammarOption; inherit (lib.nvim.types) mkGrammarOption;
inherit (lib.nvim.dag) entryAfter; inherit (lib.nvim.dag) entryAfter;
inherit (lib.nvim.lua) expToLua; inherit (lib.nvim.lua) toLuaObject;
inherit (lib.meta) getExe';
inherit (lib.generators) mkLuaInline;
inherit (pkgs) haskellPackages; inherit (pkgs) haskellPackages;
cfg = config.vim.languages.haskell; cfg = config.vim.languages.haskell;
defaultServers = ["hls"];
servers = {
hls = {
enable = false;
cmd = [(getExe' pkgs.haskellPackages.haskell-language-server "haskell-language-server-wrapper") "--lsp"];
filetypes = ["haskell" "lhaskell"];
on_attach =
mkLuaInline
/*
lua
*/
''
function(client, bufnr)
local ht = require("haskell-tools")
local opts = { noremap = true, silent = true, buffer = bufnr }
vim.keymap.set('n', '<localleader>cl', vim.lsp.codelens.run, opts)
vim.keymap.set('n', '<localleader>hs', ht.hoogle.hoogle_signature, opts)
vim.keymap.set('n', '<localleader>ea', ht.lsp.buf_eval_all, opts)
vim.keymap.set('n', '<localleader>rr', ht.repl.toggle, opts)
vim.keymap.set('n', '<localleader>rf', function()
ht.repl.toggle(vim.api.nvim_buf_get_name(0))
end, opts)
vim.keymap.set('n', '<localleader>rq', ht.repl.quit, opts)
end
'';
root_dir =
mkLuaInline
/*
lua
*/
''
function(bufnr, on_dir)
local fname = vim.api.nvim_buf_get_name(bufnr)
on_dir(util.root_pattern('hie.yaml', 'stack.yaml', 'cabal.project', '*.cabal', 'package.yaml')(fname))
end
'';
settings = {
haskell = {
formattingProvider = "ormolu";
cabalFormattingProvider = "cabalfmt";
};
};
};
};
in { in {
options.vim.languages.haskell = { options.vim.languages.haskell = {
enable = mkEnableOption "Haskell support"; enable = mkEnableOption "Haskell support";
@ -25,21 +72,20 @@ in {
}; };
lsp = { lsp = {
enable = mkEnableOption "LSP support for Haskell" // {default = config.vim.lsp.enable;}; enable = mkEnableOption "Haskell LSP support" // {default = config.vim.lsp.enable;};
package = mkOption { servers = mkOption {
description = "Haskell LSP package or command to run the Haskell LSP"; type = listOf (enum (attrNames servers));
example = ''[ (lib.getExe pkgs.haskellPackages.haskell-language-server) "--debug" ]''; default = defaultServers;
default = haskellPackages.haskell-language-server; description = "Haskell LSP server to use";
type = either package (listOf str);
}; };
}; };
dap = { dap = {
enable = mkEnableOption "DAP support for Haskell" // {default = config.vim.languages.enableDAP;}; enable = mkEnableOption "DAP support for Haskell" // {default = config.vim.languages.enableDAP;};
package = mkOption { package = mkOption {
description = "Haskell DAP package or command to run the Haskell DAP";
default = haskellPackages.haskell-debug-adapter; default = haskellPackages.haskell-debug-adapter;
type = either package (listOf str); type = either package (listOf str);
description = "Haskell DAP package or command to run the Haskell DAP";
}; };
}; };
}; };
@ -57,7 +103,7 @@ in {
startPlugins = ["haskell-tools-nvim"]; startPlugins = ["haskell-tools-nvim"];
luaConfigRC.haskell-tools-nvim = luaConfigRC.haskell-tools-nvim =
entryAfter entryAfter
["lsp-setup"] ["lsp-servers"]
'' ''
vim.g.haskell_tools = { vim.g.haskell_tools = {
${optionalString cfg.lsp.enable '' ${optionalString cfg.lsp.enable ''
@ -67,31 +113,13 @@ in {
enable = true, enable = true,
}, },
}, },
hls = { hls = ${toLuaObject servers.hls},
cmd = ${
if isList cfg.lsp.package
then expToLua cfg.lsp.package
else ''{"${cfg.lsp.package}/bin/haskell-language-server-wrapper", "--lsp"}''
},
on_attach = function(client, bufnr, ht)
default_on_attach(client, bufnr, ht)
local opts = { noremap = true, silent = true, buffer = bufnr }
vim.keymap.set('n', '<localleader>cl', vim.lsp.codelens.run, opts)
vim.keymap.set('n', '<localleader>hs', ht.hoogle.hoogle_signature, opts)
vim.keymap.set('n', '<localleader>ea', ht.lsp.buf_eval_all, opts)
vim.keymap.set('n', '<localleader>rr', ht.repl.toggle, opts)
vim.keymap.set('n', '<localleader>rf', function()
ht.repl.toggle(vim.api.nvim_buf_get_name(0))
end, opts)
vim.keymap.set('n', '<localleader>rq', ht.repl.quit, opts)
end,
},
''} ''}
${optionalString cfg.dap.enable '' ${optionalString cfg.dap.enable ''
dap = { dap = {
cmd = ${ cmd = ${
if isList cfg.dap.package if isList cfg.dap.package
then expToLua cfg.dap.package then toLuaObject cfg.dap.package
else ''{"${cfg.dap.package}/bin/haskell-debug-adapter"}'' else ''{"${cfg.dap.package}/bin/haskell-debug-adapter"}''
}, },
}, },

View file

@ -8,29 +8,26 @@
inherit (lib.options) mkEnableOption mkOption; inherit (lib.options) mkEnableOption mkOption;
inherit (lib.meta) getExe; inherit (lib.meta) getExe;
inherit (lib.modules) mkIf mkMerge; inherit (lib.modules) mkIf mkMerge;
inherit (lib.types) package bool enum; inherit (lib.types) bool enum listOf;
inherit (lib.nvim.types) mkGrammarOption; inherit (lib.nvim.types) mkGrammarOption deprecatedSingleOrListOf;
inherit (lib.nvim.attrsets) mapListToAttrs;
cfg = config.vim.languages.hcl; cfg = config.vim.languages.hcl;
defaultServer = "terraform-ls"; defaultServers = ["terraform-ls"];
servers = { servers = {
terraform-ls = { terraform-ls = {
package = pkgs.terraform-ls; enable = true;
lspConfig = '' cmd = [(getExe pkgs.terraform-ls) "serve"];
lspconfig.terraformls.setup { filetypes = ["terraform" "terraform-vars"];
capabilities = capabilities, root_markers = [".terraform" ".git"];
on_attach=default_on_attach,
cmd = {"${lib.getExe cfg.lsp.package}", "serve"},
}
'';
}; };
}; };
defaultFormat = "hclfmt"; defaultFormat = ["hclfmt"];
formats = { formats = {
hclfmt = { hclfmt = {
package = pkgs.hclfmt; command = getExe pkgs.hclfmt;
}; };
}; };
in { in {
@ -43,12 +40,11 @@ in {
}; };
lsp = { lsp = {
enable = mkEnableOption "HCL LSP support (terraform-ls)" // {default = config.vim.lsp.enable;}; enable = mkEnableOption "HCL LSP support" // {default = config.vim.lsp.enable;};
# TODO: (maybe, is it better?) it would be cooler to use vscode-extensions.hashicorp.hcl probably, shouldn't be too hard servers = mkOption {
package = mkOption { type = listOf (enum (attrNames servers));
type = package; default = defaultServers;
default = servers.${defaultServer}.package; description = "HCL LSP server to use";
description = "HCL language server package (terraform-ls)";
}; };
}; };
@ -59,15 +55,10 @@ in {
description = "Enable HCL formatting"; description = "Enable HCL formatting";
}; };
type = mkOption { type = mkOption {
type = enum (attrNames formats); type = deprecatedSingleOrListOf "vim.language.hcl.format.type" (enum (attrNames formats));
default = defaultFormat; default = defaultFormat;
description = "HCL formatter to use"; description = "HCL formatter to use";
}; };
package = mkOption {
type = package;
default = formats.${cfg.format.type}.package;
description = "HCL formatter package";
};
}; };
}; };
@ -96,18 +87,25 @@ in {
}) })
(mkIf cfg.lsp.enable { (mkIf cfg.lsp.enable {
vim.lsp.lspconfig.enable = true; vim.lsp.servers =
vim.lsp.lspconfig.sources = lib.optionalAttrs (! config.vim.languages.terraform.lsp.enable) { mapListToAttrs (n: {
terraform-ls = servers.${cfg.lsp.server}.lspConfig; name = n;
}; value = servers.${n};
})
cfg.lsp.servers;
}) })
(mkIf cfg.format.enable { (mkIf cfg.format.enable {
vim.formatter.conform-nvim = { vim.formatter.conform-nvim = {
enable = true; enable = true;
setupOpts.formatters_by_ft.hcl = [cfg.format.type]; setupOpts = {
setupOpts.formatters.${cfg.format.type} = { formatters_by_ft.hcl = cfg.format.type;
command = getExe cfg.format.package; formatters =
mapListToAttrs (name: {
inherit name;
value = formats.${name};
})
cfg.format.type;
}; };
}; };
}) })

View file

@ -4,44 +4,39 @@
lib, lib,
... ...
}: let }: let
inherit (builtins) attrNames; inherit (builtins) attrNames head;
inherit (lib.options) mkEnableOption mkOption; inherit (lib.options) mkEnableOption mkOption;
inherit (lib.modules) mkIf mkMerge; inherit (lib.modules) mkDefault mkIf mkMerge;
inherit (lib.lists) isList; inherit (lib.meta) getExe;
inherit (lib.types) enum either listOf package str; inherit (lib.types) enum;
inherit (lib.nvim.types) mkGrammarOption; inherit (lib.nvim.types) mkGrammarOption deprecatedSingleOrListOf;
inherit (lib.nvim.lua) expToLua; inherit (lib.nvim.attrsets) mapListToAttrs;
cfg = config.vim.languages.helm; cfg = config.vim.languages.helm;
yamlCfg = config.vim.languages.yaml; yamlCfg = config.vim.languages.yaml;
helmCmd = defaultServers = ["helm-ls"];
if isList cfg.lsp.package
then cfg.lsp.package
else ["${cfg.lsp.package}/bin/helm_ls" "serve"];
yamlCmd =
if isList yamlCfg.lsp.package
then builtins.elemAt yamlCfg.lsp.package 0
else "${yamlCfg.lsp.package}/bin/yaml-language-server";
defaultServer = "helm-ls";
servers = { servers = {
helm-ls = { helm-ls = {
package = pkgs.helm-ls; enable = true;
lspConfig = '' cmd = [(getExe pkgs.helm-ls) "serve"];
lspconfig.helm_ls.setup { filetypes = ["helm" "yaml.helm-values"];
capabilities = capabilities, root_markers = ["Chart.yaml"];
on_attach = default_on_attach, capabilities = {
cmd = ${expToLua helmCmd}, didChangeWatchedFiles = {
settings = { dynamicRegistration = true;
['helm-ls'] = { };
yamlls = { };
path = "${yamlCmd}" settings = mkIf (yamlCfg.enable && yamlCfg.lsp.enable) {
} helm-ls = {
} yamlls = {
} # Without this being enabled, the YAML language module will look broken in helmfiles
} # if both modules are enabled at once.
''; enabled = mkDefault yamlCfg.lsp.enable;
path = head config.vim.lsp.servers.${head yamlCfg.lsp.servers}.cmd;
};
};
};
}; };
}; };
in { in {
@ -55,17 +50,10 @@ in {
lsp = { lsp = {
enable = mkEnableOption "Helm LSP support" // {default = config.vim.lsp.enable;}; enable = mkEnableOption "Helm LSP support" // {default = config.vim.lsp.enable;};
servers = mkOption {
server = mkOption { type = deprecatedSingleOrListOf "vim.language.helm.lsp.servers" (enum (attrNames servers));
default = defaultServers;
description = "Helm LSP server to use"; description = "Helm LSP server to use";
type = enum (attrNames servers);
default = defaultServer;
};
package = mkOption {
description = "Helm LSP server package";
type = either package (listOf str);
default = servers.${cfg.lsp.server}.package;
}; };
}; };
}; };
@ -77,8 +65,12 @@ in {
}) })
(mkIf cfg.lsp.enable { (mkIf cfg.lsp.enable {
vim.lsp.lspconfig.enable = true; vim.lsp.servers =
vim.lsp.lspconfig.sources.helm-lsp = servers.${cfg.lsp.server}.lspConfig; mapListToAttrs (n: {
name = n;
value = servers.${n};
})
cfg.lsp.servers;
}) })
{ {

View file

@ -4,14 +4,46 @@
lib, lib,
... ...
}: let }: let
inherit (builtins) attrNames;
inherit (lib.meta) getExe;
inherit (lib.options) mkEnableOption mkOption; inherit (lib.options) mkEnableOption mkOption;
inherit (lib.modules) mkIf mkMerge; inherit (lib.modules) mkIf mkMerge;
inherit (lib.types) bool; inherit (lib.types) bool enum;
inherit (lib.lists) optional; inherit (lib.lists) optional;
inherit (lib.nvim.types) mkGrammarOption; inherit (lib.nvim.types) mkGrammarOption diagnostics deprecatedSingleOrListOf;
inherit (lib.nvim.dag) entryAnywhere; inherit (lib.nvim.dag) entryAnywhere;
inherit (lib.nvim.attrsets) mapListToAttrs;
cfg = config.vim.languages.html; cfg = config.vim.languages.html;
defaultServers = ["superhtml"];
servers = {
superhtml = {
cmd = [(getExe pkgs.superhtml) "lsp"];
filetypes = ["html" "shtml" "htm"];
root_markers = ["index.html" ".git"];
};
emmet-ls = {
cmd = [(getExe pkgs.emmet-ls) "--stdio"];
filetypes = ["html" "shtml" "htm"];
root_markers = ["index.html" ".git"];
};
};
defaultFormat = ["superhtml"];
formats = {
superhtml = {
command = "${pkgs.superhtml}/bin/superhtml";
args = ["fmt" "-"];
};
};
defaultDiagnosticsProvider = ["htmlhint"];
diagnosticsProviders = {
htmlhint = {
config.cmd = getExe pkgs.htmlhint;
};
};
in { in {
options.vim.languages.html = { options.vim.languages.html = {
enable = mkEnableOption "HTML language support"; enable = mkEnableOption "HTML language support";
@ -19,9 +51,38 @@ in {
enable = mkEnableOption "HTML treesitter support" // {default = config.vim.languages.enableTreesitter;}; enable = mkEnableOption "HTML treesitter support" // {default = config.vim.languages.enableTreesitter;};
package = mkGrammarOption pkgs "html"; package = mkGrammarOption pkgs "html";
autotagHtml = mkOption { autotagHtml = mkOption {
description = "Enable autoclose/autorename of html tags (nvim-ts-autotag)";
type = bool; type = bool;
default = true; default = true;
description = "Enable autoclose/autorename of html tags (nvim-ts-autotag)";
};
};
lsp = {
enable = mkEnableOption "HTML LSP support" // {default = config.vim.lsp.enable;};
servers = mkOption {
type = deprecatedSingleOrListOf "vim.language.html.lsp.servers" (enum (attrNames servers));
default = defaultServers;
description = "HTML LSP server to use";
};
};
format = {
enable = mkEnableOption "HTML formatting" // {default = config.vim.languages.enableFormat;};
type = mkOption {
type = deprecatedSingleOrListOf "vim.language.html.format.type" (enum (attrNames formats));
default = defaultFormat;
description = "HTML formatter to use";
};
};
extraDiagnostics = {
enable = mkEnableOption "extra HTML diagnostics" // {default = config.vim.languages.enableExtraDiagnostics;};
types = diagnostics {
langDesc = "HTML";
inherit diagnosticsProviders;
inherit defaultDiagnosticsProvider;
}; };
}; };
}; };
@ -41,5 +102,40 @@ in {
''); '');
}; };
}) })
(mkIf cfg.lsp.enable {
vim.lsp.servers =
mapListToAttrs (n: {
name = n;
value = servers.${n};
})
cfg.lsp.servers;
})
(mkIf (cfg.format.enable && !cfg.lsp.enable) {
vim.formatter.conform-nvim = {
enable = true;
setupOpts = {
formatters_by_ft.html = cfg.format.type;
formatters =
mapListToAttrs (name: {
inherit name;
value = formats.${name};
})
cfg.format.type;
};
};
})
(mkIf cfg.extraDiagnostics.enable {
vim.diagnostics.nvim-lint = {
enable = true;
linters_by_ft.html = cfg.extraDiagnostics.types;
linters = mkMerge (map (name: {
${name} = diagnosticsProviders.${name}.config;
})
cfg.extraDiagnostics.types);
};
})
]); ]);
} }

Some files were not shown because too many files have changed in this diff Show more