fix(lists): VimwikiToggleRejectedListItem -range parity (P3)
CI / cargo fmt --check (push) Successful in 7m3s
CI / cargo clippy (push) Successful in 17m14s
CI / cargo test (push) Successful in 31m54s
CI / editor keymaps (push) Successful in 1m51s

Upstream's :VimwikiToggleRejectedListItem is -range and binds glx in
visual mode; nuwiki's four defs were bare, so a ranged invocation raised
E481 and acted cursor-only. Same -range class already fixed for
ToggleListItem/Increment/Decrement -- ToggleRejected was missed.

All four defs (Vim+Neovim x Vimwiki*/Nuwiki*) are now -range, routed
through a new reject_list_item_range(l1, l2) looping over_range in both
clients, mirroring toggle_list_item_range. Visual glx stays cursor-only,
consistent with its <C-Space>/gln/glp siblings.

Also logs the 2026-06-02 re-audit findings in development/vimwiki-gap.md:
RemoveDone lost -range (low pri); config gaps list_margin
semantics/markdown-default, diary_months, markdown_header_style,
diary_caption_level=-1; and the path_html/template_path default-location
divergences. Mappings audit came back clean.

Tests: cmd.reject_list_item_range (test-keymaps.lua),
cmd.VimwikiToggleRejectedListItem_accepts_range (test-keymaps-vim.vim).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
2026-06-02 01:02:48 +00:00
parent d8d1e9e39e
commit 079e7246ac
6 changed files with 116 additions and 4 deletions
+3
View File
@@ -554,6 +554,9 @@ endfunction
function! nuwiki#commands#list_cycle_symbol_range(direction, l1, l2) abort function! nuwiki#commands#list_cycle_symbol_range(direction, l1, l2) abort
call s:over_range(a:l1, a:l2, { -> nuwiki#commands#list_cycle_symbol(a:direction) }) call s:over_range(a:l1, a:l2, { -> nuwiki#commands#list_cycle_symbol(a:direction) })
endfunction endfunction
function! nuwiki#commands#reject_list_item_range(l1, l2) abort
call s:over_range(a:l1, a:l2, function('nuwiki#commands#reject_list_item'))
endfunction
function! nuwiki#commands#cycle_list_item() abort function! nuwiki#commands#cycle_list_item() abort
call s:exec_pos('nuwiki.list.cycleCheckbox') call s:exec_pos('nuwiki.list.cycleCheckbox')
endfunction endfunction
+18
View File
@@ -669,6 +669,24 @@ call s:record(
\ 'cmd.VimwikiListChangeLvl_accepts_range_and_args', \ 'cmd.VimwikiListChangeLvl_accepts_range_and_args',
\ 'err=' . s:lcl_err) \ 'err=' . s:lcl_err)
" ===== :VimwikiToggleRejectedListItem -range =====
" Was bare (range-less): `:1,3VimwikiToggleRejectedListItem` raised E481. The
" reject is an LSP roundtrip (no server here), so assert only the attribute
" parse: no E481.
call s:set_buf(['- [ ] a', '- [ ] b', '- [ ] c'])
let s:trl_err = ''
try
silent 1,3VimwikiToggleRejectedListItem
catch /E481/
let s:trl_err = v:exception
catch
" non-E481 (e.g. no LSP attached) is expected and fine here.
endtry
call s:record(
\ s:trl_err ==# '' ? 1 : 0,
\ 'cmd.VimwikiToggleRejectedListItem_accepts_range',
\ 'err=' . s:trl_err)
" ===== :VimwikiSplitLink -nargs=* ===== " ===== :VimwikiSplitLink -nargs=* =====
" Upstream takes optional reuse/move-cursor flags; nuwiki's defs took none, so " Upstream takes optional reuse/move-cursor flags; nuwiki's defs took none, so
" `:VimwikiSplitLink 0 1` raised E488. Now -nargs=*: assert the arg parse " `:VimwikiSplitLink 0 1` raised E488. Now -nargs=*: assert the arg parse
+16
View File
@@ -808,6 +808,22 @@ vim.defer_fn(function()
error('range toggle incomplete: ' .. vim.inspect(vim.api.nvim_buf_get_lines(0, 0, -1, false))) error('range toggle incomplete: ' .. vim.inspect(vim.api.nvim_buf_get_lines(0, 0, -1, false)))
end end
end) end)
-- `:1,3VimwikiToggleRejectedListItem` — now -range (was bare → E481 on a
-- ranged invocation, and cursor-only). Each line should gain a rejected
-- checkbox `[-]`.
tobj_case('cmd.reject_list_item_range', function()
set_buf({ '- [ ] a', '- [ ] b', '- [ ] c' })
vim.cmd('1,3VimwikiToggleRejectedListItem')
local done = vim.wait(2000, function()
for _, l in ipairs(vim.api.nvim_buf_get_lines(0, 0, -1, false)) do
if not l:match('%[%-%]') then return false end
end
return true
end, 30)
if not done then
error('range reject incomplete: ' .. vim.inspect(vim.api.nvim_buf_get_lines(0, 0, -1, false)))
end
end)
-- `:VimwikiTable {cols} [rows]` — now -nargs=* (was -nargs=1, which dropped -- `:VimwikiTable {cols} [rows]` — now -nargs=* (was -nargs=1, which dropped
-- the args entirely). A 4-col table has 5 pipes per row; 3 data rows give -- the args entirely). A 4-col table has 5 pipes per row; 3 data rows give
-- header + separator + 3 = 5 table lines. -- header + separator + 3 = 5 table lines.
+71
View File
@@ -317,6 +317,27 @@ fix site.
`cmd.Vimwiki{MakeDiaryNote,DiaryIndex}_accepts_count` (`test-keymaps-vim.vim`). `cmd.Vimwiki{MakeDiaryNote,DiaryIndex}_accepts_count` (`test-keymaps-vim.vim`).
_(The `Index`/`TabIndex` family was already `-count=0`, mapping the count to _(The `Index`/`TabIndex` family was already `-count=0`, mapping the count to
the wiki number via `wiki_index`/`wiki_tab_index`.)_ the wiki number via `wiki_index`/`wiki_tab_index`.)_
- [x] **`VimwikiToggleRejectedListItem` / `NuwikiToggleRejected` lack `-range`**
_(new, 2026-06-02 re-audit; fixed same day)_ — upstream is `-range`
(`ftplugin/vimwiki.vim:351`) and binds it in **visual** mode (`glx`, line 543);
nuwiki's four defs were bare, so `:'<,'>VimwikiToggleRejectedListItem` raised
E481 and a ranged invocation acted cursor-only. This is the same `-range` class
fixed above for `ToggleListItem`/`Increment`/`Decrement``ToggleRejected` was
simply missed in that pass. _Fix:_ all four defs (Vim+Neovim × `Vimwiki*`/
`Nuwiki*`) are now `-range`, routed through a new `reject_list_item_range(l1,
l2)` looping `over_range` (both clients), mirroring `toggle_list_item_range`.
The visual `glx` keymap stays cursor-only, consistent with its `<C-Space>`/
`gln`/`glp` siblings (the keymap-range question is a separate, family-wide
item). Covered by `cmd.reject_list_item_range` (`test-keymaps.lua`) +
`cmd.VimwikiToggleRejectedListItem_accepts_range` (`test-keymaps-vim.vim`).
- [ ] **`VimwikiRemoveDone` dropped upstream's `-range`** _(new, 2026-06-02
re-audit)_ — upstream is `-range` (`ftplugin/vimwiki.vim:362`, "remove done
items in the selection"); nuwiki repurposed it to `-bang` only (the documented
redesign at the top of this doc), so `:'<,'>VimwikiRemoveDone` raises E481. The
`-bang` whole-buffer sweep is intentional; the lost `-range`/E481 is an
undocumented side effect. Low priority — decide whether to also accept a range
(filter the sweep to selected lines) or just note it as part of the documented
divergence.
- [x] **`-complete=` specs** _(new; done 2026-05-31 command-attribute pass)_ - [x] **`-complete=` specs** _(new; done 2026-05-31 command-attribute pass)_
upstream attaches command-line completion to several commands; nuwiki had upstream attaches command-line completion to several commands; nuwiki had
none, so `<Tab>` at the `:` line never completed page / tag / colour names. none, so `<Tab>` at the `:` line never completed page / tag / colour names.
@@ -361,6 +382,36 @@ fix site.
`cmd.VimwikiSplitLink_accepts_args` (`test-keymaps-vim.vim`, no E488). `cmd.VimwikiSplitLink_accepts_args` (`test-keymaps-vim.vim`, no E488).
### Config ### Config
- [ ] **`list_margin` — wrong semantics + wrong markdown default** _(new,
2026-06-02 re-audit)_ — upstream (`vars.vim:516`, doc `vimwiki.txt:2667`):
left-margin **width in spaces for buffer-side generated lists** — generated
links (`:VimwikiGenerateLinks`), the TOC, and the list-manipulation commands —
default `-1` (⇒ use `'shiftwidth'`) but **`0` for markdown** wikis
(`vars.vim:651`). nuwiki instead applies it **only** as an HTML CSS
`margin-left:<n>em` on the outermost `<ul>/<ol>` (`html.rs:337`) and never
indents the generated buffer content; it also defaults `-1` for all syntaxes
(`config.rs:417`), so markdown wikis get the wrong default. Two parts:
(a) the documented primary effect (buffer indentation in `build_links_text` /
TOC / `diary::build_index_body`) is absent; (b) derive `0` when
`syntax == "markdown"` and the key is unset. _(The HTML `em` reinterpretation
may have been deliberate — decide: implement buffer-side indent + markdown-0,
or keep the HTML meaning and document the divergence.)_
- [ ] **`diary_months` — absent (month names hardcoded)** _(new, 2026-06-02
re-audit)_ — upstream global (`vars.vim:141`) maps month numbers → names for
the generated diary-index tree; nuwiki hardcodes English in `diary.rs`
`month_name()`. i18n only — low. _Fix:_ optional `diary_months` map on
`RawWiki`/`WikiConfig`, threaded into `build_index_body`'s month labels.
- [ ] **`markdown_header_style` — absent** _(new, 2026-06-02 re-audit)_
upstream global (`vars.vim:174`, default `1`): number of blank lines inserted
after a **generated** header in markdown syntax (generated links, TOC, tags,
diary index). nuwiki's `caption_line` (`commands.rs`) emits no configurable
trailing blank line. Cosmetic, markdown-only.
- [ ] **`diary_caption_level = -1` not representable** _(new, 2026-06-02
re-audit)_ — upstream allows `-1` ("read no headers from diary pages",
`vars.vim:507` `min: -1`); nuwiki types the field as `u8` (`config.rs`,
`RawWiki`), so a `-1` config fails deserialization and silently falls back to
`0`. The *default* (`0`) is correct — only the `-1` value is lost. _Fix:_ widen
to `i8` (and honour `-1` if/when caption-from-page-headers lands). Edge case.
- [ ] `auto_header` — auto H1-from-filename on new page (server-side). - [ ] `auto_header` — auto H1-from-filename on new page (server-side).
- [ ] `create_link` — toggle to suppress link-target creation. - [ ] `create_link` — toggle to suppress link-target creation.
- [ ] `dir_link` — index file to open when following a directory link. - [ ] `dir_link` — index file to open when following a directory link.
@@ -462,6 +513,14 @@ audits don't re-flag them.
a behavioural one. a behavioural one.
- `CJK_length`, `listing_hl*`, `schemes_*`, `w32_dir_enc`, `menu`, - `CJK_length`, `listing_hl*`, `schemes_*`, `w32_dir_enc`, `menu`,
`rx_todo` / `tag_format` — syntax internals, menu, or Vim/Win shims. `rx_todo` / `tag_format` — syntax internals, menu, or Vim/Win shims.
- **Default output-location derivations** _(noted 2026-06-02 re-audit)_ — where a
key is unset, nuwiki derives a different default *location* than upstream, by
design (root-relative, self-contained per wiki): `path_html`
`<root>/_html` (upstream: sibling `<wikidir>_html/`); `template_path`
`<root>/_templates` (upstream: global `~/vimwiki/templates/`); `diary_rel_path`
`diary` vs upstream `diary/` (trailing slash only — paths are joined
identically, so behaviour matches). Listed so future audits stop re-flagging
them; users can still set any of these explicitly.
--- ---
@@ -487,3 +546,15 @@ audits don't re-flag them.
`VimwikiSplitLink`/`VSplitLink` missing `-nargs=*`; mouse-maps-opt-in noted as `VimwikiSplitLink`/`VSplitLink` missing `-nargs=*`; mouse-maps-opt-in noted as
an intentional divergence. Config pass found no new gaps; all shipped defaults an intentional divergence. Config pass found no new gaps; all shipped defaults
match upstream except the documented `syntax`-name divergence. match upstream except the documented `syntax`-name divergence.
- Re-audited 2026-06-02 (fourth pass — commands / config / mappings, three
parallel agents) against vimwiki `a54a300` (cloned locally; upstream had **no
commits since the 2026-05-31 pass**, so this was miss-catching, not new
upstream surface). **Mappings: clean** (~55 keys + the global family verified
identical in both clients; no new gaps, no regressions). **Commands:** one real
bug — `VimwikiToggleRejectedListItem` missing `-range` (fixed same day, see
P3); plus `VimwikiRemoveDone`'s lost `-range` logged as low-priority.
**Config:** four new items logged (`list_margin` semantics/markdown-default,
`diary_months`, `markdown_header_style`, `diary_caption_level = -1`); the
default output-location derivations (`path_html`/`template_path`/
`diary_rel_path`) recorded as intentional divergences. No previously-closed
item regressed.
+4 -4
View File
@@ -77,7 +77,7 @@ if !has('nvim')
command! -buffer VimwikiRenameLink call nuwiki#commands#rename_file() command! -buffer VimwikiRenameLink call nuwiki#commands#rename_file()
command! -buffer VimwikiNextTask call nuwiki#commands#next_task() command! -buffer VimwikiNextTask call nuwiki#commands#next_task()
command! -buffer -range VimwikiToggleListItem call nuwiki#commands#toggle_list_item_range(<line1>, <line2>) command! -buffer -range VimwikiToggleListItem call nuwiki#commands#toggle_list_item_range(<line1>, <line2>)
command! -buffer VimwikiToggleRejectedListItem call nuwiki#commands#reject_list_item() command! -buffer -range VimwikiToggleRejectedListItem call nuwiki#commands#reject_list_item_range(<line1>, <line2>)
command! -buffer VimwikiListToggle call nuwiki#commands#list_toggle_or_add_checkbox() command! -buffer VimwikiListToggle call nuwiki#commands#list_toggle_or_add_checkbox()
command! -buffer -range VimwikiIncrementListItem call nuwiki#commands#list_cycle_symbol_range(1, <line1>, <line2>) command! -buffer -range VimwikiIncrementListItem call nuwiki#commands#list_cycle_symbol_range(1, <line1>, <line2>)
command! -buffer -range VimwikiDecrementListItem call nuwiki#commands#list_cycle_symbol_range(-1, <line1>, <line2>) command! -buffer -range VimwikiDecrementListItem call nuwiki#commands#list_cycle_symbol_range(-1, <line1>, <line2>)
@@ -139,7 +139,7 @@ if !has('nvim')
command! -buffer NuwikiRenameFile call nuwiki#commands#rename_file() command! -buffer NuwikiRenameFile call nuwiki#commands#rename_file()
command! -buffer NuwikiNextTask call nuwiki#commands#next_task() command! -buffer NuwikiNextTask call nuwiki#commands#next_task()
command! -buffer -range NuwikiToggleListItem call nuwiki#commands#toggle_list_item_range(<line1>, <line2>) command! -buffer -range NuwikiToggleListItem call nuwiki#commands#toggle_list_item_range(<line1>, <line2>)
command! -buffer NuwikiToggleRejected call nuwiki#commands#reject_list_item() command! -buffer -range NuwikiToggleRejected call nuwiki#commands#reject_list_item_range(<line1>, <line2>)
command! -buffer NuwikiExport call nuwiki#commands#export_current() command! -buffer NuwikiExport call nuwiki#commands#export_current()
command! -buffer NuwikiExportBrowse call nuwiki#commands#export_browse() command! -buffer NuwikiExportBrowse call nuwiki#commands#export_browse()
command! -buffer -bang NuwikiExportAll if <bang>0 | call nuwiki#commands#export_all_force() | else | call nuwiki#commands#export_all() | endif command! -buffer -bang NuwikiExportAll if <bang>0 | call nuwiki#commands#export_all_force() | else | call nuwiki#commands#export_all() | endif
@@ -426,7 +426,7 @@ command! -buffer VimwikiRenameLink lua require('nuwiki.commands').rename_
command! -buffer VimwikiNextTask lua require('nuwiki.commands').next_task() command! -buffer VimwikiNextTask lua require('nuwiki.commands').next_task()
command! -buffer -range VimwikiToggleListItem lua require('nuwiki.commands').toggle_list_item_range(<line1>, <line2>) command! -buffer -range VimwikiToggleListItem lua require('nuwiki.commands').toggle_list_item_range(<line1>, <line2>)
command! -buffer VimwikiToggleRejectedListItem lua require('nuwiki.commands').reject_list_item() command! -buffer -range VimwikiToggleRejectedListItem lua require('nuwiki.commands').reject_list_item_range(<line1>, <line2>)
command! -buffer VimwikiListToggle lua require('nuwiki.commands').list_toggle_or_add_checkbox() command! -buffer VimwikiListToggle lua require('nuwiki.commands').list_toggle_or_add_checkbox()
command! -buffer -range VimwikiIncrementListItem lua require('nuwiki.commands').list_cycle_symbol_range(1, <line1>, <line2>) command! -buffer -range VimwikiIncrementListItem lua require('nuwiki.commands').list_cycle_symbol_range(1, <line1>, <line2>)
command! -buffer -range VimwikiDecrementListItem lua require('nuwiki.commands').list_cycle_symbol_range(-1, <line1>, <line2>) command! -buffer -range VimwikiDecrementListItem lua require('nuwiki.commands').list_cycle_symbol_range(-1, <line1>, <line2>)
@@ -484,7 +484,7 @@ command! -buffer NuwikiDeleteFile lua require('nuwiki.commands').delete_f
command! -buffer NuwikiRenameFile lua require('nuwiki.commands').rename_file() command! -buffer NuwikiRenameFile lua require('nuwiki.commands').rename_file()
command! -buffer NuwikiNextTask lua require('nuwiki.commands').next_task() command! -buffer NuwikiNextTask lua require('nuwiki.commands').next_task()
command! -buffer -range NuwikiToggleListItem lua require('nuwiki.commands').toggle_list_item_range(<line1>, <line2>) command! -buffer -range NuwikiToggleListItem lua require('nuwiki.commands').toggle_list_item_range(<line1>, <line2>)
command! -buffer NuwikiToggleRejected lua require('nuwiki.commands').reject_list_item() command! -buffer -range NuwikiToggleRejected lua require('nuwiki.commands').reject_list_item_range(<line1>, <line2>)
command! -buffer NuwikiExport lua require('nuwiki.commands').export_current() command! -buffer NuwikiExport lua require('nuwiki.commands').export_current()
command! -buffer NuwikiExportBrowse lua require('nuwiki.commands').export_browse() command! -buffer NuwikiExportBrowse lua require('nuwiki.commands').export_browse()
command! -buffer -bang NuwikiExportAll execute (<bang>0 ? "lua require('nuwiki.commands').export_all_force()" : "lua require('nuwiki.commands').export_all()") command! -buffer -bang NuwikiExportAll execute (<bang>0 ? "lua require('nuwiki.commands').export_all_force()" : "lua require('nuwiki.commands').export_all()")
+4
View File
@@ -385,6 +385,10 @@ function M.list_cycle_symbol_range(direction, l1, l2)
over_range(l1, l2, function() M.list_cycle_symbol(direction) end) over_range(l1, l2, function() M.list_cycle_symbol(direction) end)
end end
function M.reject_list_item_range(l1, l2)
over_range(l1, l2, M.reject_list_item)
end
M.heading_add_level = _exec_pos('nuwiki.heading.addLevel') M.heading_add_level = _exec_pos('nuwiki.heading.addLevel')
M.heading_remove_level = _exec_pos('nuwiki.heading.removeLevel') M.heading_remove_level = _exec_pos('nuwiki.heading.removeLevel')