docs(filetype): consolidate comments in dev_vimpatch.txt

This commit is contained in:
Christian Clason 2024-08-03 13:04:47 +02:00
parent 37910f2703
commit 3b58d93aae
2 changed files with 42 additions and 39 deletions

View File

@ -308,41 +308,54 @@ used in new documentation:
FILETYPE DETECTION *dev-vimpatch-filetype*
Nvim's filetype detection behavior matches Vim, but is implemented as part of
|vim.filetype| (see $VIMRUNTIME/lua/vim/filetype.lua).
|vim.filetype| (see `$VIMRUNTIME/lua/vim/filetype.lua`). The logic is encoded in
three tables, listed in order of precedence (the first match is returned):
1. `filename` for literal full path or basename lookup;
2. `pattern` for matching filenames or paths against |lua-patterns|, optimized
for fast lookup;
3. `extension` for literal extension lookup.
Prefer explicit filenames/extensions over patterns, especially for case
Logic that requires checking file contents or buffer variables is implemented
in `$VIMRUNTIME/lua/vim/filetype/detect.lua`.
When porting filetype patches from Vim, keep the following in mind:
Prefer explicit filenames or extensions over patterns, especially for case
insensitive matches (see https://github.com/neovim/neovim/pull/29800): >
"*[mM]akefile" regex -> "makefile", "Makefile" filenames
"*.js\c" regex -> "js", "jS", "Js", "jS" extensions
Pattern matching has several differences:
- It is done using explicit Lua patterns (without implicit anchoring) instead
- It is done using explicit Lua patterns without implicit anchoring instead
of Vim regexes: >
"*/debian/changelog" -> "/debian/changelog$"
"*/bind/db.*" -> "/bind/db%."
<
- Filetype patterns are grouped by their parent pattern to improve matching
performance. For this to work properly, parent pattern should:
- Match at least the same set of strings as filetype patterns inside it.
But not too much more.
- Be fast to match.
performance: If the parent pattern does not match, skip testing all child
patterns. Note that unlike leaf patterns, parent patterns do not have
special matching behaviour if they contain a `/`.
When adding a new filetype with pattern matching, consider the following:
- If there is already a group with appropriate parent pattern, use it.
- If there can be a fast and specific enough pattern to group at least
3 filetype patterns, add it as a separate grouped entry.
- If there can be a fast and specific enough pattern to group at least 3
filetype patterns, add it as a separate grouped entry.
Good new parent pattern should be:
- Fast. Good rule of thumb is that it should be a short explicit string
(i.e. no quantifiers or character sets).
- Specific. Good rules of thumb (from best to worst):
- Full directory name (like "/etc/", "/log/").
- Part of a rare enough directory name (like "/conf", "git/").
- String reasonably rarely used in real full paths (like "nginx").
New parent patterns should be
- fast: rule of thumb is that it should be a short explicit string
(i.e. no quantifiers or character sets);
- specific: rules of thumb, in order:
- full directory name (e.g., `"/etc/"`, `"/log/"`);
- part of a rare enough directory name (e.g., `"/conf"`, `"git/"`);
- string rarely used in real full paths (e.g., `"nginx"`).
Example:
- Filetype pattern: ".*/etc/a2ps/.*%.cfg"
- Good parent: "/etc/"; "%.cfg$"
- Bad parent: "%." - fast, not specific; "/a2ps/.*%." - slow, specific
- Filetype pattern: `".*/etc/a2ps/.*%.cfg"`
- Good parents: `"/etc/"` or `"%.cfg$"`
- Bad parents: `"%."` (fast but not specific) or `"/a2ps/.*%."` (specific
but slow)
When modifying an existing regular pattern, make sure that it still fits its
group.
vim:tw=78:ts=8:noet:ft=help:norl:

View File

@ -174,9 +174,15 @@ end
-- luacheck: push no unused args
-- luacheck: push ignore 122
-- Filetypes based on file extension
-- Filetype detection logic is encoded in three tables:
-- 1. `extension` for literal extension lookup
-- 2. `filename` for literal full path or basename lookup;
-- 3. `pattern` for matching filenames or paths against Lua patterns,
-- optimized for fast lookup.
-- See `:h dev-vimpatch-filetype` for guidance when porting Vim filetype patches.
---@diagnostic disable: unused-local
--- @type vim.filetype.mapping
---@type vim.filetype.mapping
local extension = {
-- BEGIN EXTENSION
['8th'] = '8th',
@ -273,8 +279,6 @@ local extension = {
cfm = 'cf',
cfi = 'cf',
hgrc = 'cfg',
-- Extension match does not conflict with specific patterns such as '.*/etc/a2ps/.*%.cfg', etc.,
-- as it is done after those are tried to match
cfg = detect.cfg,
cfG = detect.cfg,
cFg = detect.cfg,
@ -1418,7 +1422,7 @@ local extension = {
-- END EXTENSION
}
--- @type vim.filetype.mapping
---@type vim.filetype.mapping
local filename = {
-- BEGIN FILENAME
['a2psrc'] = 'a2ps',
@ -1884,21 +1888,7 @@ local detect_muttrc = starsetf('muttrc', { parent = 'utt' })
local detect_neomuttrc = starsetf('neomuttrc', { parent = 'utt' })
local detect_xkb = starsetf('xkb', { parent = '/usr/' })
--- Table of filetype pattern matching rules grouped by their parent pattern.
---
--- Every filetype pattern match is prefaced with a matching of its parent pattern.
--- If there is no match, skip all matching inside group.
--- Note that unlike leaf patterns, parent patterns do not have special matching behaviour if they
--- contain a `/`.
---
--- When modifying an existing regular pattern, make sure that it still fits its group.
---
--- Vim regexes are converted into explicit Lua patterns (without implicit anchoring):
--- '*/debian/changelog' -> '/debian/changelog$'
--- '*/bind/db.*' -> '/bind/db%.'
---
--- See more info in `:h dev-vimpatch-filetype`.
--- @type table<string,vim.filetype.mapping>
---@type table<string,vim.filetype.mapping>
local pattern = {
-- BEGIN PATTERN
['/debian/'] = {