{ pkgs, lib, ... }: { programs.nixvim = { extraPackages = with pkgs; [ shellcheck shellharden shfmt ruff stylua nixfmt-rfc-style clang-tools csharpier ]; plugins = { conform-nvim = { enable = true; settings = { formatters_by_ft = { bash = [ "shellcheck" "shellharden" "shfmt" ]; python = [ "ruff_fix" "ruff_format" "ruff_organize_imports" ]; c = [ "clang-format" ]; cpp = [ "clang-format" ]; cs = [ "csharpier" ]; csharp = [ "csharpier" ]; lua = [ "stylua" ]; nix = [ "nixfmt" ]; javascript = [ "prettier" ]; javascriptreact = [ "prettier" ]; typescript = [ "prettier" ]; typescriptreact = [ "prettier" ]; markdown = [ "prettier" ]; yaml = [ "prettier" ]; json = [ "prettier" ]; svelte = [ "prettier" ]; html = [ "prettier" ]; css = [ "prettier" ]; graphql = [ "prettier" ]; "_" = [ "trim_whitespace" "trim_newlines" ]; }; log_level = "warn"; notify_on_error = true; notify_no_formatters = true; default_format_opts = { lsp_format = "fallback"; timeout_ms = 300; }; formatters = { shellcheck = { command = lib.getExe pkgs.shellcheck; }; shfmt = { command = lib.getExe pkgs.shfmt; }; shellharden = { command = lib.getExe pkgs.shellharden; }; nixfmt = { command = lib.getExe pkgs.nixfmt-rfc-style; }; stylua = { command = lib.getExe pkgs.stylua; }; clang-format = { command = "${pkgs.clang-tools}/bin/clang-format"; }; csharpier = { command = lib.getExe pkgs.csharpier; }; ruff_fix = { command = lib.getExe pkgs.ruff; }; ruff_format = { command = lib.getExe pkgs.ruff; }; ruff_organize_imports = { command = lib.getExe pkgs.ruff; }; }; format_on_save = # lua '' function(bufnr) if vim.g.disable_autoformat or vim.b[bufnr].disable_autoformat then return end if slow_format_filetypes[vim.bo[bufnr].filetype] then return end local function on_format(err) if err and err:match("timeout$") then slow_format_filetypes[vim.bo[bufnr].filetype] = true end end return { timeout_ms = 200, lsp_fallback = true }, on_format end ''; format_after_save = # lua '' function(bufnr) if vim.g.disable_autoformat or vim.b[bufnr].disable_autoformat then return end if not slow_format_filetypes[vim.bo[bufnr].filetype] then return end return { lsp_fallback = true } end ''; }; luaConfig.post = # lua '' slow_format_filetypes = {} -- Filetypes that are slow to format, and should be formatted after saving a buffer instead of before require("conform").formatters.injected = { options = { lang_to_ext = { c = "c", cpp = "cpp", cs = "cs", csharp = "cs", lua = "lua", nix = "nix", python = "py", bash = "sh", javascript = "js", javascriptreact = "jsx", typescript = "ts", typescriptreact = "tsx", markdown = "md", yaml = "yaml", json = "json", svelte = "svelte", html = "html", css = "css", graphql = "graphql", }, }, } vim.api.nvim_create_user_command("Format", function(args) local range = nil if args.count ~= -1 then local end_line = vim.api.nvim_buf_get_lines(0, args.line2 - 1, args.line2, true)[1] range = { start = { args.line1, 0 }, ["end"] = { args.line2, end_line:len() }, } end require("conform").format({ async = true, lsp_format = "fallback", range = range }) end, { range = true }) ''; }; }; keymaps = [ { mode = "n"; key = "f"; action = ":Format"; options = { desc = "Format"; silent = true; }; } ]; }; }