plugins/completion: move to by-name

- Move nvim-cmp to plugins/cmp
- Move other completion plugins to plugins/by-name
This commit is contained in:
Matt Sturgeon 2024-09-05 02:36:41 +01:00
parent 3211a63306
commit ad85cd760e
No known key found for this signature in database
GPG key ID: 4F91844CED1A8299
36 changed files with 2 additions and 9 deletions

View file

@ -0,0 +1,32 @@
{
lib,
helpers,
pkgs,
...
}:
{
pluginName,
sourceName,
package ? lib.mkPackageOption pkgs [
"vimPlugins"
pluginName
] { },
maintainers ? [ lib.maintainers.GaetanLepage ],
imports ? [ ],
...
}@args:
helpers.vim-plugin.mkVimPlugin (
builtins.removeAttrs args [
"pluginName"
"sourceName"
]
// {
inherit package maintainers;
name = pluginName;
imports = imports ++ [
# Register the source -> plugin name association
{ cmpSourcePlugins.${sourceName} = pluginName; }
];
}
)

View file

@ -0,0 +1,95 @@
{
lib,
helpers,
config,
...
}:
with lib;
let
cfg = config.plugins.cmp-ai;
in
{
meta.maintainers = [ maintainers.GaetanLepage ];
options.plugins.cmp-ai = {
settings = helpers.mkSettingsOption {
description = "Options provided to the `require('cmp_ai.config'):setup` function.";
options = {
max_lines = helpers.defaultNullOpts.mkUnsignedInt 50 ''
How many lines of buffer context to use.
'';
run_on_every_keystroke = helpers.defaultNullOpts.mkBool true ''
Generate new completion items on every keystroke.
'';
provider = helpers.defaultNullOpts.mkStr "HF" ''
Which AI provider to use.
Check the [README](https://github.com/tzachar/cmp-ai/blob/main/README.md) to learn about
available options.
'';
provider_options = helpers.defaultNullOpts.mkAttrsOf types.anything { } ''
Options to forward to the provider.
'';
notify = helpers.defaultNullOpts.mkBool true ''
As some completion sources can be quit slow, setting this to `true` will trigger a
notification when a completion starts and ends using `vim.notify`.
'';
notify_callback = helpers.defaultNullOpts.mkLuaFn' {
description = ''
The default notify function uses `vim.notify`, but an override can be configured.
'';
pluginDefault = ''
function(msg)
vim.notify(msg)
end
'';
example = ''
function(msg)
require('notify').notify(msg, vim.log.levels.INFO, {
title = 'OpenAI',
render = 'compact',
})
end
'';
};
ignored_file_types = helpers.defaultNullOpts.mkAttrsOf' {
type = types.bool;
description = "Which filetypes to ignore.";
pluginDefault = { };
example = {
lua = true;
html = true;
};
};
};
example = {
max_lines = 1000;
provider = "HF";
notify = true;
notify_callback = ''
function(msg)
vim.notify(msg)
end
'';
run_on_every_keystroke = true;
ignored_file_types = {
lua = true;
};
};
};
};
config = mkIf cfg.enable {
extraConfigLua = ''
require('cmp_ai.config'):setup(${helpers.toLuaObject cfg.settings})
'';
};
}

View file

@ -0,0 +1,22 @@
{
lib,
config,
pkgs,
helpers,
...
}:
with lib;
let
cfg = config.plugins.cmp-fish;
in
{
meta.maintainers = [ maintainers.GaetanLepage ];
options.plugins.cmp-fish = {
fishPackage = lib.mkPackageOption pkgs "fish" {
nullable = true;
};
};
config = mkIf cfg.enable { extraPackages = [ cfg.fishPackage ]; };
}

View file

@ -0,0 +1,298 @@
{
lib,
helpers,
config,
...
}:
with lib;
let
cfg = config.plugins.cmp-git;
mkAction =
action: target:
helpers.defaultNullOpts.mkLuaFn "require('cmp_git.${action}').git.${target}" ''
Function used to ${action} the ${replaceStrings [ "_" ] [ " " ] target}.
'';
in
{
options.plugins.cmp-git.settings = helpers.mkSettingsOption {
description = "Options provided to the `require('cmp_git').setup` function.";
options = {
filetypes = helpers.defaultNullOpts.mkListOf types.str [
"gitcommit"
"octo"
] "Filetypes for which to trigger.";
remotes = helpers.defaultNullOpts.mkListOf types.str [
"upstream"
"origin"
] "List of git remotes.";
enableRemoteUrlRewrites = helpers.defaultNullOpts.mkBool false ''
Whether to enable remote URL rewrites.
'';
git = {
commits = {
limit = helpers.defaultNullOpts.mkUnsignedInt 100 ''
Max number of git commits to fetch.
'';
sort_by = mkAction "sort" "commits";
format = mkAction "format" "commits";
};
};
github = {
hosts = helpers.defaultNullOpts.mkListOf types.str [ ] ''
List of private instances of github.
'';
issues = {
fields = helpers.defaultNullOpts.mkListOf types.str [
"title"
"number"
"body"
"updatedAt"
"state"
] "The fields used for issues.";
filter = helpers.defaultNullOpts.mkStr "all" ''
The filter to use when fetching issues.
'';
limit = helpers.defaultNullOpts.mkUnsignedInt 100 ''
Max number of issues to fetch.
'';
state = helpers.defaultNullOpts.mkStr "open" ''
Which issues to fetch (`"open"`, `"closed"` or `"all"`).
'';
sort_by = mkAction "sort" "issues";
format = mkAction "format" "issues";
};
mentions = {
limit = helpers.defaultNullOpts.mkUnsignedInt 100 ''
Max number of mentions to fetch.
'';
sort_by = mkAction "sort" "mentions";
format = mkAction "format" "mentions";
};
pull_requests = {
fields = helpers.defaultNullOpts.mkListOf types.str [
"title"
"number"
"body"
"updatedAt"
"state"
] "The fields used for pull requests.";
limit = helpers.defaultNullOpts.mkUnsignedInt 100 ''
Max number of pull requests to fetch.
'';
state = helpers.defaultNullOpts.mkStr "open" ''
Which issues to fetch (`"open"`, `"closed"`, `"merged"` or `"all"`).
'';
sort_by = mkAction "sort" "pull_requests";
format = mkAction "format" "pull_requests";
};
};
gitlab = {
hosts = helpers.defaultNullOpts.mkListOf types.str [ ] ''
List of private instances of gitlab.
'';
issues = {
limit = helpers.defaultNullOpts.mkUnsignedInt 100 ''
Max number of issues to fetch.
'';
state = helpers.defaultNullOpts.mkStr "open" ''
Which issues to fetch (`"open"`, `"closed"` or `"all"`).
'';
sort_by = mkAction "sort" "issues";
format = mkAction "format" "issues";
};
mentions = {
limit = helpers.defaultNullOpts.mkUnsignedInt 100 ''
Max number of mentions to fetch.
'';
sort_by = mkAction "sort" "mentions";
format = mkAction "format" "mentions";
};
merge_requests = {
limit = helpers.defaultNullOpts.mkUnsignedInt 100 ''
Max number of merge requests to fetch.
'';
state = helpers.defaultNullOpts.mkStr "open" ''
Which issues to fetch (`"open"`, `"closed"`, `"locked"` or `"merged"`).
'';
sort_by = mkAction "sort" "merge_requests";
format = mkAction "format" "merge_requests";
};
};
trigger_actions =
helpers.defaultNullOpts.mkListOf
(types.submodule {
options = {
debug_name = helpers.mkNullOrStr "Debug name.";
trigger_character = mkOption {
type = types.str;
example = ":";
description = ''
The trigger character.
Has to be a single character
'';
};
action = mkOption {
type = helpers.nixvimTypes.strLuaFn;
apply = helpers.mkRaw;
description = ''
The parameters to the action function are the different sources (currently `git`,
`gitlab` and `github`), the completion callback, the trigger character, the
parameters passed to complete from nvim-cmp, and the current git info.
'';
example = ''
function(sources, trigger_char, callback, params, git_info)
return sources.git:get_commits(callback, params, trigger_char)
end
'';
};
};
})
[
{
debug_name = "git_commits";
trigger_character = ":";
action = ''
function(sources, trigger_char, callback, params, git_info)
return sources.git:get_commits(callback, params, trigger_char)
end
'';
}
{
debug_name = "gitlab_issues";
trigger_character = "#";
action = ''
function(sources, trigger_char, callback, params, git_info)
return sources.gitlab:get_issues(callback, git_info, trigger_char)
end
'';
}
{
debug_name = "gitlab_mentions";
trigger_character = "@";
action = ''
function(sources, trigger_char, callback, params, git_info)
return sources.gitlab:get_mentions(callback, git_info, trigger_char)
end
'';
}
{
debug_name = "gitlab_mrs";
trigger_character = "!";
action = ''
function(sources, trigger_char, callback, params, git_info)
return sources.gitlab:get_merge_requests(callback, git_info, trigger_char)
end
'';
}
{
debug_name = "github_issues_and_pr";
trigger_character = "#";
action = ''
function(sources, trigger_char, callback, params, git_info)
return sources.github:get_issues_and_prs(callback, git_info, trigger_char)
end
'';
}
{
debug_name = "github_mentions";
trigger_character = "@";
action = ''
function(sources, trigger_char, callback, params, git_info)
return sources.github:get_mentions(callback, git_info, trigger_char)
end
'';
}
]
''
If you want specific behaviour for a trigger or new behaviour for a trigger, you need to
add an entry in the `trigger_actions` list of the config.
The two necessary fields are the `trigger_character` and the `action`.
'';
};
example = {
remotes = [
"upstream"
"origin"
"foo"
];
github.issues = {
filter = "all";
limit = 250;
state = "all";
format = ''
function(_, issue)
local icon = ({
open = '',
closed = '',
})[string.lower(issue.state)]
return string.format('%s #%d: %s', icon, issue.number, issue.title)
end
'';
sort_by = ''
function(issue)
local kind_rank = issue.pull_request and 1 or 0
local state_rank = issue.state == 'open' and 0 or 1
local age = os.difftime(os.time(), require('cmp_git.utils').parse_github_date(issue.updatedAt))
return string.format('%d%d%010d', kind_rank, state_rank, age)
end
'';
};
trigger_actions = [
{
debug_name = "git_commits";
trigger_character = ":";
action = ''
function(sources, trigger_char, callback, params, git_info)
return sources.git:get_commits(callback, params, trigger_char)
end
'';
}
{
debug_name = "github_issues";
trigger_character = "#";
action = ''
function(sources, trigger_char, callback, params, git_info)
return sources.github:get_issues(callback, git_info, trigger_char)
end
'';
}
];
};
};
config = mkIf cfg.enable {
extraConfigLua = ''
require('cmp_git').setup(${helpers.toLuaObject cfg.settings})
'';
};
}

View file

@ -0,0 +1,69 @@
{
lib,
helpers,
config,
...
}:
with lib;
let
cfg = config.plugins.cmp-tabby;
in
{
meta.maintainers = [ maintainers.GaetanLepage ];
# TODO: introduced 24-06-18, remove after 24.11
imports =
let
basePluginPath = [
"plugins"
"cmp-tabby"
];
settingsPath = basePluginPath ++ [ "settings" ];
in
[
(mkRenamedOptionModule (basePluginPath ++ [ "extraOptions" ]) settingsPath)
(mkRenamedOptionModule (basePluginPath ++ [ "host" ]) (settingsPath ++ [ "host" ]))
(mkRenamedOptionModule (basePluginPath ++ [ "maxLines" ]) (settingsPath ++ [ "max_lines" ]))
(mkRenamedOptionModule (basePluginPath ++ [ "runOnEveryKeyStroke" ]) (
settingsPath ++ [ "run_on_every_keystroke" ]
))
(mkRenamedOptionModule (basePluginPath ++ [ "stop" ]) (settingsPath ++ [ "stop" ]))
];
options.plugins.cmp-tabby = {
settings = helpers.mkSettingsOption {
description = "Options provided to the `require('cmp_ai.config'):setup` function.";
options = {
host = helpers.defaultNullOpts.mkStr "http://localhost:5000" ''
The address of the tabby host server.
'';
max_lines = helpers.defaultNullOpts.mkUnsignedInt 100 ''
The max number of lines to complete.
'';
run_on_every_keystroke = helpers.defaultNullOpts.mkBool true ''
Whether to run the completion on every keystroke.
'';
stop = helpers.defaultNullOpts.mkListOf types.str [ "\n" ] ''
Stop character.
'';
};
example = {
host = "http://localhost:5000";
max_lines = 100;
run_on_every_keystroke = true;
stop = [ "\n" ];
};
};
};
config = mkIf cfg.enable {
extraConfigLua = ''
require('cmp_tabby.config'):setup(${helpers.toLuaObject cfg.settings})
'';
};
}

View file

@ -0,0 +1,19 @@
{
lib,
helpers,
config,
...
}:
with lib;
let
cfg = config.plugins.cmp-tabnine;
in
{
options.plugins.cmp-tabnine = helpers.neovim-plugin.extraOptionsOptions;
config = mkIf cfg.enable {
extraConfigLua = ''
require('cmp_tabnine.config'):setup(${helpers.toLuaObject cfg.extraOptions})
'';
};
}

View file

@ -0,0 +1,65 @@
{
lib,
helpers,
config,
...
}:
with lib;
let
copilot-lua-cfg = config.plugins.copilot-lua;
cfg = config.plugins.copilot-cmp;
in
{
options.plugins.copilot-cmp = helpers.neovim-plugin.extraOptionsOptions // {
event =
helpers.defaultNullOpts.mkListOf types.str
[
"InsertEnter"
"LspAttach"
]
''
Configures when the source is registered.
Unless you have a unique problem for your particular configuration you probably don't want
to touch this.
'';
fixPairs = helpers.defaultNullOpts.mkBool true ''
Suppose you have the following code: `print('h')`.
Copilot might try to account for the `'` and `)` and complete it with this: `print('hello`.
This is not good behavior for consistency reasons and will just end up deleting the two ending
characters.
This option fixes that.
Don't turn this off unless you are having problems with pairs and believe this might be
causing them.
'';
};
config = mkIf cfg.enable {
warnings =
optional ((!isBool copilot-lua-cfg.suggestion.enabled) || copilot-lua-cfg.suggestion.enabled) ''
It is recommended to disable copilot's `suggestion` module, as it can interfere with
completions properly appearing in copilot-cmp.
''
++ optional ((!isBool copilot-lua-cfg.panel.enabled) || copilot-lua-cfg.panel.enabled) ''
It is recommended to disable copilot's `panel` module, as it can interfere with completions
properly appearing in copilot-cmp.
'';
plugins.copilot-lua.enable = true;
extraConfigLua =
let
setupOptions =
with cfg;
{
inherit event;
fix_pairs = fixPairs;
}
// cfg.extraOptions;
in
''
require('copilot_cmp').setup(${helpers.toLuaObject setupOptions})
'';
};
}

View file

@ -0,0 +1,19 @@
{
lib,
helpers,
config,
...
}:
with lib;
let
cfg = config.plugins.crates-nvim;
in
{
options.plugins.crates-nvim = helpers.neovim-plugin.extraOptionsOptions;
config = mkIf cfg.enable {
extraConfigLua = ''
require('crates').setup(${helpers.toLuaObject cfg.extraOptions})
'';
};
}

View file

@ -0,0 +1,204 @@
{
lib,
helpers,
pkgs,
...
}@args:
let
# A list of most cmp source plugins, passed to mkCmpSourcePlugin.
# More complex cmp sources can instead be defined as their own plugin
# and register their source-name association using the `cmpSourcePlugins` option.
sources = [
{
pluginName = "cmp-async-path";
sourceName = "async_path";
}
{
pluginName = "cmp-buffer";
sourceName = "buffer";
}
{
pluginName = "cmp-calc";
sourceName = "calc";
}
{
pluginName = "cmp-dap";
sourceName = "dap";
}
{
pluginName = "cmp-cmdline";
sourceName = "cmdline";
}
{
pluginName = "cmp-ai";
sourceName = "cmp_ai";
}
{
pluginName = "cmp-clippy";
sourceName = "cmp-clippy";
}
{
pluginName = "cmp-cmdline-history";
sourceName = "cmp-cmdline-history";
}
{
pluginName = "cmp-pandoc-nvim";
sourceName = "cmp_pandoc";
}
{
pluginName = "cmp-tabby";
sourceName = "cmp_tabby";
}
{
pluginName = "cmp-tabnine";
sourceName = "cmp_tabnine";
}
{
pluginName = "cmp-conventionalcommits";
sourceName = "conventionalcommits";
}
{
pluginName = "copilot-cmp";
sourceName = "copilot";
}
{
pluginName = "crates-nvim";
sourceName = "crates";
}
{
pluginName = "cmp-dictionary";
sourceName = "dictionary";
}
{
pluginName = "cmp-digraphs";
sourceName = "digraphs";
}
{
pluginName = "cmp-emoji";
sourceName = "emoji";
}
{
pluginName = "cmp-fish";
sourceName = "fish";
}
{
pluginName = "cmp-fuzzy-buffer";
sourceName = "fuzzy_buffer";
}
{
pluginName = "cmp-fuzzy-path";
sourceName = "fuzzy_path";
}
{
pluginName = "cmp-git";
sourceName = "git";
}
{
pluginName = "cmp-greek";
sourceName = "greek";
}
{
pluginName = "cmp-latex-symbols";
sourceName = "latex_symbols";
}
{
pluginName = "cmp-look";
sourceName = "look";
}
{
pluginName = "cmp_luasnip";
sourceName = "luasnip";
}
{
pluginName = "cmp-nvim-lsp";
sourceName = "nvim_lsp";
}
{
pluginName = "cmp-nvim-lsp-document-symbol";
sourceName = "nvim_lsp_document_symbol";
}
{
pluginName = "cmp-nvim-lsp-signature-help";
sourceName = "nvim_lsp_signature_help";
}
{
pluginName = "cmp-nvim-lua";
sourceName = "nvim_lua";
}
{
pluginName = "cmp-npm";
sourceName = "npm";
}
{
pluginName = "cmp-omni";
sourceName = "omni";
}
{
pluginName = "cmp-pandoc-references";
sourceName = "pandoc_references";
}
{
pluginName = "cmp-path";
sourceName = "path";
}
{
pluginName = "cmp-rg";
sourceName = "rg";
}
{
pluginName = "cmp-snippy";
sourceName = "snippy";
}
{
pluginName = "cmp-spell";
sourceName = "spell";
}
{
pluginName = "cmp-tmux";
sourceName = "tmux";
}
{
pluginName = "cmp-treesitter";
sourceName = "treesitter";
}
{
pluginName = "cmp-nvim-ultisnips";
sourceName = "ultisnips";
}
{
pluginName = "cmp-vim-lsp";
sourceName = "vim_lsp";
}
{
pluginName = "cmp-vimwiki-tags";
sourceName = "vimwiki-tags";
}
{
pluginName = "cmp-vsnip";
sourceName = "vsnip";
}
{
pluginName = "cmp_yanky";
sourceName = "yanky";
}
{
pluginName = "cmp-zsh";
sourceName = "zsh";
}
];
mkCmpSourcePlugin = import ./_mk-cmp-plugin.nix args;
pluginModules = builtins.map mkCmpSourcePlugin sources;
in
{
# For extra cmp plugins
imports = [
./copilot-cmp.nix
./cmp-ai.nix
./cmp-fish.nix
./cmp-git.nix
./cmp-tabby.nix
./cmp-tabnine.nix
./crates-nvim.nix
] ++ pluginModules;
}