1{ config, lib, pkgs, ... }:
2
3let
4 cfg = config.programs.neovim;
5in
6{
7 options.programs.neovim = {
8 enable = lib.mkOption {
9 type = lib.types.bool;
10 default = false;
11 example = true;
12 description = ''
13 Whether to enable Neovim.
14
15 When enabled through this option, Neovim is wrapped to use a
16 configuration managed by this module. The configuration file in the
17 user's home directory at {file}`~/.config/nvim/init.vim` is no longer
18 loaded by default.
19 '';
20 };
21
22 defaultEditor = lib.mkOption {
23 type = lib.types.bool;
24 default = false;
25 description = ''
26 When enabled, installs neovim and configures neovim to be the default editor
27 using the EDITOR environment variable.
28 '';
29 };
30
31 viAlias = lib.mkOption {
32 type = lib.types.bool;
33 default = false;
34 description = ''
35 Symlink {command}`vi` to {command}`nvim` binary.
36 '';
37 };
38
39 vimAlias = lib.mkOption {
40 type = lib.types.bool;
41 default = false;
42 description = ''
43 Symlink {command}`vim` to {command}`nvim` binary.
44 '';
45 };
46
47 withRuby = lib.mkOption {
48 type = lib.types.bool;
49 default = true;
50 description = "Enable Ruby provider.";
51 };
52
53 withPython3 = lib.mkOption {
54 type = lib.types.bool;
55 default = true;
56 description = "Enable Python 3 provider.";
57 };
58
59 withNodeJs = lib.mkOption {
60 type = lib.types.bool;
61 default = false;
62 description = "Enable Node provider.";
63 };
64
65 configure = lib.mkOption {
66 type = lib.types.attrs;
67 default = { };
68 example = lib.literalExpression ''
69 {
70 customRC = '''
71 " here your custom configuration goes!
72 ''';
73 packages.myVimPackage = with pkgs.vimPlugins; {
74 # loaded on launch
75 start = [ fugitive ];
76 # manually loadable by calling `:packadd $plugin-name`
77 opt = [ ];
78 };
79 }
80 '';
81 description = ''
82 Generate your init file from your list of plugins and custom commands.
83 Neovim will then be wrapped to load {command}`nvim -u /nix/store/«hash»-vimrc`
84 '';
85 };
86
87 package = lib.mkPackageOption pkgs "neovim-unwrapped" { };
88
89 finalPackage = lib.mkOption {
90 type = lib.types.package;
91 visible = false;
92 readOnly = true;
93 description = "Resulting customized neovim package.";
94 };
95
96 runtime = lib.mkOption {
97 default = { };
98 example = lib.literalExpression ''
99 { "ftplugin/c.vim".text = "setlocal omnifunc=v:lua.vim.lsp.omnifunc"; }
100 '';
101 description = ''
102 Set of files that have to be linked in {file}`runtime`.
103 '';
104
105 type = with lib.types; attrsOf (submodule (
106 { name, config, ... }:
107 {
108 options = {
109
110 enable = lib.mkOption {
111 type = lib.types.bool;
112 default = true;
113 description = ''
114 Whether this runtime directory should be generated. This
115 option allows specific runtime files to be disabled.
116 '';
117 };
118
119 target = lib.mkOption {
120 type = lib.types.str;
121 description = ''
122 Name of symlink. Defaults to the attribute
123 name.
124 '';
125 };
126
127 text = lib.mkOption {
128 default = null;
129 type = lib.types.nullOr lib.types.lines;
130 description = "Text of the file.";
131 };
132
133 source = lib.mkOption {
134 default = null;
135 type = lib.types.nullOr lib.types.path;
136 description = "Path of the source file.";
137 };
138
139 };
140
141 config.target = lib.mkDefault name;
142 }
143 ));
144
145 };
146 };
147
148 config = lib.mkIf cfg.enable {
149 environment.systemPackages = [
150 cfg.finalPackage
151 ];
152 environment.variables.EDITOR = lib.mkIf cfg.defaultEditor (lib.mkOverride 900 "nvim");
153
154 environment.etc = builtins.listToAttrs (builtins.attrValues (builtins.mapAttrs
155 (name: value: {
156 name = "xdg/nvim/${name}";
157 value = builtins.removeAttrs
158 (value // {
159 target = "xdg/nvim/${value.target}";
160 })
161 (lib.optionals (builtins.isNull value.source) [ "source" ]);
162 })
163 cfg.runtime));
164
165 programs.neovim.finalPackage = pkgs.wrapNeovim cfg.package {
166 inherit (cfg) viAlias vimAlias withPython3 withNodeJs withRuby configure;
167 };
168 };
169}