From 0193b3a3917d426bb5798759c3629e9d4f3eb7a8 Mon Sep 17 00:00:00 2001 From: Sean Dewar Date: Fri, 27 Aug 2021 22:07:34 +0100 Subject: [PATCH 1/9] vim-patch:8.1.1336: some eval functionality is not covered by tests Problem: Some eval functionality is not covered by tests. Solution: Add a few more test cases. (Masato Nishihata, closes vim/vim#4374) https://github.com/vim/vim/commit/17aca707f92235b6f962e637e8073162d18e6de2 Test_expand() changes are required for v8.1.1921. Test_call() and Test_cindent_func() are already ported. --- src/nvim/testdir/test_bufline.vim | 6 +++++- src/nvim/testdir/test_cursor_func.vim | 6 ++++++ src/nvim/testdir/test_expand_func.vim | 9 +++++++++ src/nvim/testdir/test_float_func.vim | 1 + src/nvim/testdir/test_functions.vim | 12 ++++++++++++ test/functional/legacy/delete_spec.lua | 7 +++++++ test/functional/legacy/fnamemodify_spec.lua | 11 ----------- 7 files changed, 40 insertions(+), 12 deletions(-) diff --git a/src/nvim/testdir/test_bufline.vim b/src/nvim/testdir/test_bufline.vim index b4e8a0bc71..52a60b7b85 100644 --- a/src/nvim/testdir/test_bufline.vim +++ b/src/nvim/testdir/test_bufline.vim @@ -9,7 +9,7 @@ func Test_setbufline_getbufline() hide call assert_equal(0, setbufline(b, 1, ['foo', 'bar'])) call assert_equal(['foo'], getbufline(b, 1)) - call assert_equal(['bar'], getbufline(b, 2)) + call assert_equal(['bar'], getbufline(b, '$')) call assert_equal(['foo', 'bar'], getbufline(b, 1, 2)) exe "bd!" b call assert_equal([], getbufline(b, 1, 2)) @@ -82,6 +82,7 @@ func Test_appendbufline() call setline(1, ['a', 'b', 'c']) let b = bufnr('%') wincmd w + call assert_equal(1, appendbufline(b, -1, ['x'])) call assert_equal(1, appendbufline(b, 4, ['x'])) call assert_equal(1, appendbufline(1234, 1, ['x'])) call assert_equal(0, appendbufline(b, 3, ['d', 'e'])) @@ -104,8 +105,11 @@ func Test_deletebufline() exe "bd!" b call assert_equal(1, b->deletebufline(1)) + call assert_equal(1, deletebufline(-1, 1)) + split Xtest call setline(1, ['a', 'b', 'c']) + call cursor(line('$'), 1) let b = bufnr('%') wincmd w call assert_equal(1, deletebufline(b, 4)) diff --git a/src/nvim/testdir/test_cursor_func.vim b/src/nvim/testdir/test_cursor_func.vim index 53b7da517e..46847e0663 100644 --- a/src/nvim/testdir/test_cursor_func.vim +++ b/src/nvim/testdir/test_cursor_func.vim @@ -25,6 +25,12 @@ func Test_move_cursor() call cursor(9, 1) call assert_equal([4, 1, 0, 1], getcurpos()[1:]) + call setline(1, ["\"]) + call cursor(1, 1, 1) + call assert_equal([1, 1, 1], getcurpos()[1:3]) + + call assert_equal(-1, cursor(-1, -1)) + quit! endfunc diff --git a/src/nvim/testdir/test_expand_func.vim b/src/nvim/testdir/test_expand_func.vim index 9588d3b89d..4d9e89fe3e 100644 --- a/src/nvim/testdir/test_expand_func.vim +++ b/src/nvim/testdir/test_expand_func.vim @@ -37,6 +37,15 @@ func Test_expand_sflnum() delcommand Flnum endfunc +func Test_expand() + new + call assert_equal("", expand('%:S')) + call assert_equal('3', expand('')) + call assert_equal(['4'], expand('', v:false, v:true)) + " Don't add any line above this, otherwise will change. + quit +endfunc + func Test_expand_sfile() call assert_match('test_expand_func\.vim$', s:sfile) call assert_match('^function .*\.\.Test_expand_sfile$', expand('')) diff --git a/src/nvim/testdir/test_float_func.vim b/src/nvim/testdir/test_float_func.vim index 78675d7016..1e0c75c49d 100644 --- a/src/nvim/testdir/test_float_func.vim +++ b/src/nvim/testdir/test_float_func.vim @@ -15,6 +15,7 @@ func Test_abs() call assert_equal("str2float('inf')", string(abs(1.0/0.0))) call assert_equal("str2float('inf')", string(abs(-1.0/0.0))) call assert_equal("str2float('nan')", string(abs(0.0/0.0))) + call assert_equal('12', string(abs('12abc'))) call assert_equal('12', string(abs('-12abc'))) call assert_fails("call abs([])", 'E745:') call assert_fails("call abs({})", 'E728:') diff --git a/src/nvim/testdir/test_functions.vim b/src/nvim/testdir/test_functions.vim index 366615821c..9268a13d4e 100644 --- a/src/nvim/testdir/test_functions.vim +++ b/src/nvim/testdir/test_functions.vim @@ -56,6 +56,7 @@ func Test_empty() endif call assert_equal(0, empty(function('Test_empty'))) + call assert_equal(0, empty(function('Test_empty', [0]))) endfunc func Test_len() @@ -999,6 +1000,7 @@ func Test_count() call assert_equal(1, count(l, 'a', 0, 1)) call assert_equal(2, count(l, 'a', 1, 1)) call assert_fails('call count(l, "a", 0, 10)', 'E684:') + call assert_fails('call count(l, "a", [])', 'E745:') let d = {1: 'a', 2: 'a', 3: 'A', 4: 'b'} call assert_equal(2, count(d, 'a')) @@ -1026,6 +1028,8 @@ func Test_count() call assert_equal(2, count("foo", "O", 1)) call assert_equal(2, count("fooooo", "oo")) call assert_equal(0, count("foo", "")) + + call assert_fails('call count(0, 0)', 'E712:') endfunc func Test_changenr() @@ -1589,6 +1593,14 @@ func Test_call() call assert_fails("call call('Mylen', [], 0)", 'E715:') endfunc +func Test_char2nr() + call assert_equal(12354, char2nr('あ', 1)) +endfunc + +func Test_eventhandler() + call assert_equal(0, eventhandler()) +endfunc + " Test for the eval() function func Test_eval() call assert_fails("call eval('5 a')", 'E488:') diff --git a/test/functional/legacy/delete_spec.lua b/test/functional/legacy/delete_spec.lua index f2ced8942d..b4ed8ff136 100644 --- a/test/functional/legacy/delete_spec.lua +++ b/test/functional/legacy/delete_spec.lua @@ -1,6 +1,7 @@ local helpers = require('test.functional.helpers')(after_each) local clear, source = helpers.clear, helpers.source local eq, eval, command = helpers.eq, helpers.eval, helpers.command +local exc_exec = helpers.exc_exec describe('Test for delete()', function() before_each(clear) @@ -114,4 +115,10 @@ describe('Test for delete()', function() eq(0, eval("delete('Xdir4/Xfile')")) eq(0, eval("delete('Xdir4', 'd')")) end) + + it('gives correct emsgs', function() + eq('Vim(call):E474: Invalid argument', exc_exec("call delete('')")) + eq('Vim(call):E15: Invalid expression: 0', + exc_exec("call delete('foo', 0)")) + end) end) diff --git a/test/functional/legacy/fnamemodify_spec.lua b/test/functional/legacy/fnamemodify_spec.lua index 7e859bf0cf..6a5538c26f 100644 --- a/test/functional/legacy/fnamemodify_spec.lua +++ b/test/functional/legacy/fnamemodify_spec.lua @@ -60,12 +60,6 @@ describe('filename modifiers', function() call assert_equal("'abc\\\ndef'", fnamemodify("abc\ndef", ':S')) endif endfunc - - func Test_expand() - new - call assert_equal("", expand('%:S')) - quit - endfunc ]=]) end) @@ -73,9 +67,4 @@ describe('filename modifiers', function() call('Test_fnamemodify') expected_empty() end) - - it('works for :S in an unnamed buffer', function() - call('Test_expand') - expected_empty() - end) end) From 6110480c290011d96af37c0cba1e7309ef645efb Mon Sep 17 00:00:00 2001 From: Sean Dewar Date: Sun, 8 Aug 2021 16:07:40 +0100 Subject: [PATCH 2/9] feat(eval/method): partially port v8.1.1921 Adds method call support for all functions in the patch, but it cannot be fully ported due to missing tests for: - filereadable(): requires v8.1.1378 for Test_delete_rf(), but there appears to have been some trouble porting it. (#12784) - confirm(): requires v8.1.0832 for Test_confirm() and v8.1.0815 for feedkeys()'s "L" flag. (I did attempt to port the test using nvim_input() instead, but seems that input handling for confirm() doesn't work in --headless mode?) Note that confirm() was actually added as a method in v8.1.1915. Uncomment use of method call syntax in Test_Executable() previously included instead from v8.2.2259. --- runtime/doc/eval.txt | 60 +++++++++++++++++++++++++- src/nvim/eval.lua | 42 +++++++++--------- src/nvim/testdir/test_expand_func.vim | 2 +- src/nvim/testdir/test_expr.vim | 4 +- src/nvim/testdir/test_findfile.vim | 4 +- src/nvim/testdir/test_fnameescape.vim | 2 +- src/nvim/testdir/test_fnamemodify.vim | 2 +- src/nvim/testdir/test_fold.vim | 8 ++-- src/nvim/testdir/test_functions.vim | 13 +++--- src/nvim/testdir/test_search.vim | 2 +- src/nvim/testdir/test_vimscript.vim | 2 +- test/functional/legacy/expand_spec.lua | 2 +- 12 files changed, 100 insertions(+), 43 deletions(-) diff --git a/runtime/doc/eval.txt b/runtime/doc/eval.txt index d9ecdb40de..832fc6bc1b 100644 --- a/runtime/doc/eval.txt +++ b/runtime/doc/eval.txt @@ -3831,6 +3831,9 @@ escape({string}, {chars}) *escape()* c:\\program\ files\\vim < Also see |shellescape()| and |fnameescape()|. + Can also be used as a |method|: > + GetText()->escape(' \') +< *eval()* eval({string}) Evaluate {string} and return the result. Especially useful to turn the result of |string()| back into the original value. @@ -3870,6 +3873,9 @@ executable({expr}) *executable()* -1 not implemented on this system |exepath()| can be used to get the full path of an executable. + Can also be used as a |method|: > + GetCommand()->executable() + execute({command} [, {silent}]) *execute()* Execute {command} and capture its output. If {command} is a |String|, returns {command} output. @@ -3897,12 +3903,18 @@ execute({command} [, {silent}]) *execute()* To execute a command in another window than the current one use `win_execute()`. + Can also be used as a |method|: > + GetCommand()->execute() + exepath({expr}) *exepath()* Returns the full path of {expr} if it is an executable and given as a (partial or full) path or is found in $PATH. Returns empty string otherwise. If {expr} starts with "./" the |current-directory| is used. + Can also be used as a |method|: > + GetCommand()->exepath() + *exists()* exists({expr}) The result is a Number, which is |TRUE| if {expr} is defined, zero otherwise. @@ -3988,6 +4000,9 @@ exists({expr}) The result is a Number, which is |TRUE| if {expr} is < This doesn't check for existence of the "bufcount" variable, but gets the value of "bufcount", and checks if that exists. + Can also be used as a |method|: > + Varname()->exists() + exp({expr}) *exp()* Return the exponential of {expr} as a |Float| in the range [0, inf]. @@ -4094,6 +4109,9 @@ expand({string} [, {nosuf} [, {list}]]) *expand()* See |glob()| for finding existing files. See |system()| for getting the raw output of an external command. + Can also be used as a |method|: > + Getpattern()->expand() + expandcmd({expr}) *expandcmd()* Expand special items in {expr} like what is done for an Ex command such as `:edit`. This expands special keywords, like @@ -4101,6 +4119,9 @@ expandcmd({expr}) *expandcmd()* {expr}. "~user" and "~/path" are only expanded at the start. Returns the expanded string. Example: > :echo expandcmd('make %<.o') + +< Can also be used as a |method|: > + GetCommand()->expandcmd() < extend({expr1}, {expr2} [, {expr3}]) *extend()* {expr1} and {expr2} must be both |Lists| or both @@ -4186,6 +4207,9 @@ feedkeys({string} [, {mode}]) *feedkeys()* Return value is always 0. + Can also be used as a |method|: > + GetInput()->feedkeys() + filereadable({file}) *filereadable()* The result is a Number, which is |TRUE| when a file with the name {file} exists, and can be read. If {file} doesn't exist, @@ -4199,12 +4223,17 @@ filereadable({file}) *filereadable()* echo filereadable(expand('~/.vimrc')) 1 +< Can also be used as a |method|: > + GetName()->filereadable() + filewritable({file}) *filewritable()* The result is a Number, which is 1 when a file with the name {file} exists, and can be written. If {file} doesn't exist, or is not writable, the result is 0. If {file} is a directory, and we can write to it, the result is 2. + Can also be used as a |method|: > + GetName()->filewriteable() filter({expr1}, {expr2}) *filter()* {expr1} must be a |List|, |Blob|, or a |Dictionary|. @@ -4275,6 +4304,9 @@ finddir({name} [, {path} [, {count}]]) *finddir()* This is quite similar to the ex-command `:find`. + Can also be used as a |method|: > + GetName()->finddir() + findfile({name} [, {path} [, {count}]]) *findfile()* Just like |finddir()|, but find a file instead of a directory. Uses 'suffixesadd'. @@ -4283,6 +4315,9 @@ findfile({name} [, {path} [, {count}]]) *findfile()* < Searches from the directory of the current file upwards until it finds the file "tags.vim". + Can also be used as a |method|: > + GetName()->findfile() + flatten({list} [, {maxdepth}]) *flatten()* Flatten {list} up to {maxdepth} levels. Without {maxdepth} the result is a |List| without nesting, as if {maxdepth} is @@ -4372,6 +4407,9 @@ fnameescape({string}) *fnameescape()* :exe "edit " . fnameescape(fname) < results in executing: > edit \+some\ str\%nge\|name +< + Can also be used as a |method|: > + GetName()->fnameescape() fnamemodify({fname}, {mods}) *fnamemodify()* Modify file name {fname} according to {mods}. {mods} is a @@ -4385,6 +4423,9 @@ fnamemodify({fname}, {mods}) *fnamemodify()* Note: Environment variables don't work in {fname}, use |expand()| first then. + Can also be used as a |method|: > + GetName()->fnamemodify(':p:h') + foldclosed({lnum}) *foldclosed()* The result is a Number. If the line {lnum} is in a closed fold, the result is the number of the first line in that fold. @@ -4392,6 +4433,9 @@ foldclosed({lnum}) *foldclosed()* {lnum} is used like with |getline()|. Thus "." is the current line, "'m" mark m, etc. + Can also be used as a |method|: > + GetLnum()->foldclosed() + foldclosedend({lnum}) *foldclosedend()* The result is a Number. If the line {lnum} is in a closed fold, the result is the number of the last line in that fold. @@ -4399,6 +4443,9 @@ foldclosedend({lnum}) *foldclosedend()* {lnum} is used like with |getline()|. Thus "." is the current line, "'m" mark m, etc. + Can also be used as a |method|: > + GetLnum()->foldclosedend() + foldlevel({lnum}) *foldlevel()* The result is a Number, which is the foldlevel of line {lnum} in the current buffer. For nested folds the deepest level is @@ -4411,6 +4458,9 @@ foldlevel({lnum}) *foldlevel()* {lnum} is used like with |getline()|. Thus "." is the current line, "'m" mark m, etc. + Can also be used as a |method|: > + GetLnum()->foldlevel() + *foldtext()* foldtext() Returns a String, to be displayed for a closed fold. This is the default function used for the 'foldtext' option and should @@ -4436,6 +4486,9 @@ foldtextresult({lnum}) *foldtextresult()* line, "'m" mark m, etc. Useful when exporting folded text, e.g., to HTML. + Can also be used as a |method|: > + GetLnum()->foldtextresult() +< *foreground()* foreground() Move the Vim window to the foreground. Useful when sent from a client to a Vim server. |remote_send()| @@ -4454,6 +4507,9 @@ funcref({name} [, {arglist}] [, {dict}]) Also for autoloaded functions. {name} cannot be a builtin function. + Can also be used as a |method|: > + GetFuncname()->funcref([arg]) +< *function()* *E700* *E922* *E923* function({name} [, {arglist}] [, {dict}]) Return a |Funcref| variable that refers to function {name}. @@ -4503,7 +4559,9 @@ function({name} [, {arglist}] [, {dict}]) call Func(500) < Invokes the function as with: > call context.Callback('one', 500) - +< + Can also be used as a |method|: > + GetFuncname()->function([arg]) garbagecollect([{atexit}]) *garbagecollect()* Cleanup unused |Lists| and |Dictionaries| that have circular diff --git a/src/nvim/eval.lua b/src/nvim/eval.lua index c6ac27b269..f9f6af3bfd 100644 --- a/src/nvim/eval.lua +++ b/src/nvim/eval.lua @@ -102,38 +102,38 @@ return { diff_hlID={args=2, base=1}, empty={args=1, base=1}, environ={}, - escape={args=2}, + escape={args=2, base=1}, eval={args=1, base=1}, eventhandler={}, - executable={args=1}, - execute={args={1, 2}}, - exepath={args=1}, - exists={args=1}, + executable={args=1, base=1}, + execute={args={1, 2}, base=1}, + exepath={args=1, base=1}, + exists={args=1, base=1}, exp={args=1, base=1, func="float_op_wrapper", data="&exp"}, - expand={args={1, 3}}, - expandcmd={args=1}, + expand={args={1, 3}, base=1}, + expandcmd={args=1, base=1}, extend={args={2, 3}, base=1}, - feedkeys={args={1, 2}}, - file_readable={args=1, func='f_filereadable'}, -- obsolete - filereadable={args=1}, - filewritable={args=1}, + feedkeys={args={1, 2}, base=1}, + file_readable={args=1, base=1, func='f_filereadable'}, -- obsolete + filereadable={args=1, base=1}, + filewritable={args=1, base=1}, filter={args=2, base=1}, - finddir={args={1, 3}}, - findfile={args={1, 3}}, + finddir={args={1, 3}, base=1}, + findfile={args={1, 3}, base=1}, flatten={args={1, 2}}, float2nr={args=1, base=1}, floor={args=1, base=1, func="float_op_wrapper", data="&floor"}, fmod={args=2, base=1}, - fnameescape={args=1}, - fnamemodify={args=2}, - foldclosed={args=1}, - foldclosedend={args=1}, - foldlevel={args=1}, + fnameescape={args=1, base=1}, + fnamemodify={args=2, base=1}, + foldclosed={args=1, base=1}, + foldclosedend={args=1, base=1}, + foldlevel={args=1, base=1}, foldtext={}, - foldtextresult={args=1}, + foldtextresult={args=1, base=1}, foreground={}, - funcref={args={1, 3}}, - ['function']={args={1, 3}}, + funcref={args={1, 3}, base=1}, + ['function']={args={1, 3}, base=1}, garbagecollect={args={0, 1}}, get={args={2, 3}, base=1}, getbufinfo={args={0, 1}}, diff --git a/src/nvim/testdir/test_expand_func.vim b/src/nvim/testdir/test_expand_func.vim index 4d9e89fe3e..44d2c156d5 100644 --- a/src/nvim/testdir/test_expand_func.vim +++ b/src/nvim/testdir/test_expand_func.vim @@ -40,7 +40,7 @@ endfunc func Test_expand() new call assert_equal("", expand('%:S')) - call assert_equal('3', expand('')) + call assert_equal('3', ''->expand()) call assert_equal(['4'], expand('', v:false, v:true)) " Don't add any line above this, otherwise will change. quit diff --git a/src/nvim/testdir/test_expr.vim b/src/nvim/testdir/test_expr.vim index c49285621a..6343c47fde 100644 --- a/src/nvim/testdir/test_expr.vim +++ b/src/nvim/testdir/test_expr.vim @@ -147,7 +147,7 @@ function Test_printf_spec_s() call assert_equal(string(value), printf('%s', value)) " funcref - call assert_equal('printf', printf('%s', function('printf'))) + call assert_equal('printf', printf('%s', 'printf'->function())) " partial call assert_equal(string(function('printf', ['%s'])), printf('%s', function('printf', ['%s']))) @@ -477,7 +477,7 @@ func Test_funcref() endfunc call assert_equal(2, OneByName()) call assert_equal(1, OneByRef()) - let OneByRef = funcref('One') + let OneByRef = 'One'->funcref() call assert_equal(2, OneByRef()) call assert_fails('echo funcref("{")', 'E475:') let OneByRef = funcref("One", repeat(["foo"], 20)) diff --git a/src/nvim/testdir/test_findfile.vim b/src/nvim/testdir/test_findfile.vim index 2195bf527e..d92706dbe5 100644 --- a/src/nvim/testdir/test_findfile.vim +++ b/src/nvim/testdir/test_findfile.vim @@ -50,7 +50,7 @@ func Test_findfile() set path=. call assert_equal('Xdir2/foo', findfile('foo')) call assert_equal('', findfile('bar')) - call assert_equal('Xdir2/foobar', findfile('foobar')) + call assert_equal('Xdir2/foobar', 'foobar'->findfile()) " Empty {path} 2nd argument is the same as no 2nd argument. call assert_equal('Xdir2/foo', findfile('foo', '')) @@ -138,7 +138,7 @@ func Test_finddir() cd Xdir1 call assert_equal('Xdir2', finddir('Xdir2')) - call assert_equal('', finddir('Xdir3')) + call assert_equal('', 'Xdir3'->finddir()) " Files should not be found (findfile() finds them). call assert_equal('', finddir('foo')) diff --git a/src/nvim/testdir/test_fnameescape.vim b/src/nvim/testdir/test_fnameescape.vim index 0bafdc29fb..cdb96ba5ff 100644 --- a/src/nvim/testdir/test_fnameescape.vim +++ b/src/nvim/testdir/test_fnameescape.vim @@ -13,7 +13,7 @@ func Test_fnameescape() let fname = 'Xemark!' let status = v:false try - exe "w! " . fnameescape(fname) + exe "w! " . fname->fnameescape() let status = v:true endtry call assert_true(status, "ExclamationMark") diff --git a/src/nvim/testdir/test_fnamemodify.vim b/src/nvim/testdir/test_fnamemodify.vim index fe1df8fd4a..411f7ebbb3 100644 --- a/src/nvim/testdir/test_fnamemodify.vim +++ b/src/nvim/testdir/test_fnamemodify.vim @@ -13,7 +13,7 @@ func Test_fnamemodify() call assert_equal('a', fnamemodify('../testdir/a', ':.')) call assert_equal('~/testdir/test.out', fnamemodify('test.out', ':~')) call assert_equal('~/testdir/a', fnamemodify('../testdir/a', ':~')) - call assert_equal('a', fnamemodify('../testdir/a', ':t')) + call assert_equal('a', '../testdir/a'->fnamemodify(':t')) call assert_equal('', fnamemodify('.', ':p:t')) call assert_equal('test.out', fnamemodify('test.out', ':p:t')) call assert_equal('out', fnamemodify('test.out', ':p:e')) diff --git a/src/nvim/testdir/test_fold.vim b/src/nvim/testdir/test_fold.vim index 2cc5b47cb0..5586fe2151 100644 --- a/src/nvim/testdir/test_fold.vim +++ b/src/nvim/testdir/test_fold.vim @@ -88,7 +88,7 @@ func Test_indent_fold2() setl fen fdm=marker 2 norm! >> - let a=map(range(1,5), 'foldclosed(v:val)') + let a=map(range(1,5), 'v:val->foldclosed()') call assert_equal([-1,-1,-1,4,4], a) bw! endfunc @@ -132,7 +132,7 @@ func Test_indent_fold_with_read() call assert_equal(0, foldlevel(3)) call assert_equal(0, foldlevel(4)) call assert_equal(1, foldlevel(5)) - call assert_equal(7, foldclosedend(5)) + call assert_equal(7, 5->foldclosedend()) bwipe! set foldmethod& @@ -207,7 +207,7 @@ func Test_update_folds_expr_read() %foldclose call assert_equal(2, foldclosedend(1)) call assert_equal(0, foldlevel(3)) - call assert_equal(0, foldlevel(4)) + call assert_equal(0, 4->foldlevel()) call assert_equal(6, foldclosedend(5)) call assert_equal(10, foldclosedend(7)) call assert_equal(14, foldclosedend(11)) @@ -663,7 +663,7 @@ func Test_fold_move() call assert_equal(10, foldclosed(10)) call assert_equal(11, foldclosedend(10)) call assert_equal('+-- 2 lines: Line2', foldtextresult(2)) - call assert_equal('+-- 2 lines: Line8', foldtextresult(10)) + call assert_equal('+-- 2 lines: Line8', 10->foldtextresult()) set fdm& sw& fdl& enew! diff --git a/src/nvim/testdir/test_functions.vim b/src/nvim/testdir/test_functions.vim index 9268a13d4e..e3a80be6d5 100644 --- a/src/nvim/testdir/test_functions.vim +++ b/src/nvim/testdir/test_functions.vim @@ -1057,7 +1057,7 @@ func Test_filewritable() call assert_equal(0, filewritable('Xfilewritable')) call assert_notequal(0, setfperm('Xfilewritable', 'rw-r-----')) - call assert_equal(1, filewritable('Xfilewritable')) + call assert_equal(1, 'Xfilewritable'->filewritable()) call assert_equal(0, filewritable('doesnotexist')) @@ -1068,12 +1068,12 @@ endfunc func Test_Executable() if has('win32') call assert_equal(1, executable('notepad')) - call assert_equal(1, executable('notepad.exe')) + call assert_equal(1, 'notepad.exe'->executable()) call assert_equal(0, executable('notepad.exe.exe')) call assert_equal(0, executable('shell32.dll')) call assert_equal(0, executable('win.ini')) elseif has('unix') - call assert_equal(1, executable('cat')) + call assert_equal(1, 'cat'->executable()) call assert_equal(0, executable('nodogshere')) " get "cat" path and remove the leading / @@ -1082,8 +1082,7 @@ func Test_Executable() " check that the relative path works in / lcd / call assert_equal(1, executable(catcmd)) - " let result = catcmd->exepath() - let result = exepath(catcmd) + let result = catcmd->exepath() " when using chroot looking for sbin/cat can return bin/cat, that is OK if catcmd =~ '\' && result =~ '\' call assert_equal('/' .. substitute(catcmd, '\', 'bin', ''), result) @@ -1320,7 +1319,7 @@ func Test_func_exists_on_reload() call writefile(['func ExistingFunction()', 'echo "yes"', 'endfunc'], 'Xfuncexists') call assert_equal(0, exists('*ExistingFunction')) source Xfuncexists - call assert_equal(1, exists('*ExistingFunction')) + call assert_equal(1, '*ExistingFunction'->exists()) " Redefining a function when reloading a script is OK. source Xfuncexists call assert_equal(1, exists('*ExistingFunction')) @@ -1351,7 +1350,7 @@ func Test_func_sandbox() sandbox let F = {-> 'hello'} call assert_equal('hello', F()) - sandbox let F = {-> execute("normal ix\")} + sandbox let F = {-> "normal ix\"->execute()} call assert_fails('call F()', 'E48:') unlet F diff --git a/src/nvim/testdir/test_search.vim b/src/nvim/testdir/test_search.vim index 5ba24d047c..7570049e7c 100644 --- a/src/nvim/testdir/test_search.vim +++ b/src/nvim/testdir/test_search.vim @@ -1338,7 +1338,7 @@ func Test_search_display_pattern() call cursor(1, 1) let @/ = 'foo' - let pat = escape(@/, '()*?'. '\s\+') + let pat = @/->escape('()*?'. '\s\+') let g:a = execute(':unsilent :norm! n') call assert_match(pat, g:a) diff --git a/src/nvim/testdir/test_vimscript.vim b/src/nvim/testdir/test_vimscript.vim index b18ce563d3..34733f127f 100644 --- a/src/nvim/testdir/test_vimscript.vim +++ b/src/nvim/testdir/test_vimscript.vim @@ -635,7 +635,7 @@ function! MSG(enr, emsg) if v:errmsg == "" Xout "Message missing." else - let v:errmsg = escape(v:errmsg, '"') + let v:errmsg = v:errmsg->escape('"') Xout "Unexpected message:" v:errmsg endif endif diff --git a/test/functional/legacy/expand_spec.lua b/test/functional/legacy/expand_spec.lua index f238128b31..cd3713eabe 100644 --- a/test/functional/legacy/expand_spec.lua +++ b/test/functional/legacy/expand_spec.lua @@ -81,7 +81,7 @@ describe('expand file name', function() call assert_equal('e Xfile1', expandcmd('e %')) edit Xfile2 edit Xfile1 - call assert_equal('e Xfile2', expandcmd('e #')) + call assert_equal('e Xfile2', 'e #'->expandcmd()) edit Xfile2 edit Xfile3 edit Xfile4 From 3137c7d63574a86ddc44f11c839e8e58c2994bf9 Mon Sep 17 00:00:00 2001 From: Sean Dewar Date: Fri, 27 Aug 2021 21:09:37 +0100 Subject: [PATCH 3/9] feat(eval/method): partially port v8.1.1925 Adds method call support for all functions in the patch, but it cannot be fully ported due to missing tests for: - getcwd(): requires chdir() and Test_chdir_func() from v8.1.1291. Note that the method call tests for getreg() and getregtype() were removed in v8.2.1547, which has already been ported, but doesn't seem to have been replaced with a new test... This patch also makes getchangelist()'s argument optional (defaults to the current buffer). eval.txt includes a typo for gettabwinvar(), which is fixed in v8.1.1952. --- runtime/doc/eval.txt | 60 ++++++++++++++++++++++- src/nvim/eval.lua | 38 +++++++------- src/nvim/eval/funcs.c | 14 ++++-- src/nvim/testdir/test_bufline.vim | 2 +- src/nvim/testdir/test_bufwintabinfo.vim | 4 +- src/nvim/testdir/test_changelist.vim | 4 +- src/nvim/testdir/test_cmdline.vim | 2 +- src/nvim/testdir/test_edit.vim | 6 +-- src/nvim/testdir/test_environ.vim | 2 +- src/nvim/testdir/test_getvar.vim | 4 +- src/nvim/testdir/test_jumplist.vim | 2 +- src/nvim/testdir/test_stat.vim | 6 +-- test/functional/legacy/file_perm_spec.lua | 7 +-- 13 files changed, 107 insertions(+), 44 deletions(-) diff --git a/runtime/doc/eval.txt b/runtime/doc/eval.txt index 832fc6bc1b..24b6e6da6d 100644 --- a/runtime/doc/eval.txt +++ b/runtime/doc/eval.txt @@ -4701,6 +4701,9 @@ getbufline({buf}, {lnum} [, {end}]) Example: > :let lines = getbufline(bufnr("myfile"), 1, "$") +< Can also be used as a |method|: > + GetBufnr()->getbufline(lnum) + getbufvar({buf}, {varname} [, {def}]) *getbufvar()* The result is the value of option or local buffer variable {varname} in buffer {buf}. Note that the name without "b:" @@ -4721,8 +4724,11 @@ getbufvar({buf}, {varname} [, {def}]) *getbufvar()* Examples: > :let bufmodified = getbufvar(1, "&mod") :echo "todo myvar = " . getbufvar("todo", "myvar") + +< Can also be used as a |method|: > + GetBufnr()->getbufvar(varname) < -getchangelist({buf}) *getchangelist()* +getchangelist([{buf}]) *getchangelist()* Returns the |changelist| for the buffer {buf}. For the use of {buf}, see |bufname()| above. If buffer {buf} doesn't exist, an empty list is returned. @@ -4738,6 +4744,9 @@ getchangelist({buf}) *getchangelist()* position refers to the position in the list. For other buffers, it is set to the length of the list. + Can also be used as a |method|: > + GetBufnr()->getchangelist() + getchar([expr]) *getchar()* Get a single character from the user or input stream. If [expr] is omitted, wait until a character is available. @@ -4948,6 +4957,9 @@ getcompletion({pat}, {type} [, {filtered}]) *getcompletion()* If there are no matches, an empty list is returned. An invalid value for {type} produces an error. + Can also be used as a |method|: > + GetPattern()->getcompletion('color') +< *getcurpos()* getcurpos() Get the position of the cursor. This is like getpos('.'), but includes an extra "curswant" in the list: @@ -4976,6 +4988,9 @@ getcwd([{winnr}[, {tabnr}]]) *getcwd()* < If {winnr} is -1 it is ignored, only the tab is resolved. {winnr} can be the window number or the |window-ID|. + Can also be used as a |method|: > + GetWinnr()->getcwd() + getenv({name}) *getenv()* Return the value of environment variable {name}. The {name} argument is a string, without a leading '$'. Example: > @@ -4985,6 +5000,9 @@ getenv({name}) *getenv()* is different from a variable set to an empty string. See also |expr-env|. + Can also be used as a |method|: > + GetVarname()->getenv() + getfontname([{name}]) *getfontname()* Without an argument returns the name of the normal font being used. Like what is used for the Normal highlight group @@ -5012,6 +5030,9 @@ getfperm({fname}) *getfperm()* < This will hopefully (from a security point of view) display the string "rw-r--r--" or even "rw-------". + Can also be used as a |method|: > + GetFilename()->getfperm() +< For setting permissions use |setfperm()|. getfsize({fname}) *getfsize()* @@ -5022,6 +5043,9 @@ getfsize({fname}) *getfsize()* If the size of {fname} is too big to fit in a Number then -2 is returned. + Can also be used as a |method|: > + GetFilename()->getfsize() + getftime({fname}) *getftime()* The result is a Number, which is the last modification time of the given file {fname}. The value is measured as seconds @@ -5029,6 +5053,9 @@ getftime({fname}) *getftime()* |localtime()| and |strftime()|. If the file {fname} can't be found -1 is returned. + Can also be used as a |method|: > + GetFilename()->getftime() + getftype({fname}) *getftype()* The result is a String, which is a description of the kind of file of the given file {fname}. @@ -5049,6 +5076,9 @@ getftype({fname}) *getftype()* systems that support it. On some systems only "dir" and "file" are returned. + Can also be used as a |method|: > + GetFilename()->getftype() + getjumplist([{winnr} [, {tabnr}]]) *getjumplist()* Returns the |jumplist| for the specified window. @@ -5068,7 +5098,10 @@ getjumplist([{winnr} [, {tabnr}]]) *getjumplist()* filename filename if available lnum line number - *getline()* + Can also be used as a |method|: > + GetWinnr()->getjumplist() + +< *getline()* getline({lnum} [, {end}]) Without {end} the result is a String, which is line {lnum} from the current buffer. Example: > @@ -5091,6 +5124,9 @@ getline({lnum} [, {end}]) :let end = search("^$") - 1 :let lines = getline(start, end) +< Can also be used as a |method|: > + ComputeLnum()->getline() + < To get lines from another buffer see |getbufline()| getloclist({nr},[, {what}]) *getloclist()* @@ -5221,6 +5257,8 @@ getpos({expr}) Get the position for String {expr}. For possible values of call setpos("'a", save_a_mark) < Also see |getcurpos()| and |setpos()|. + Can also be used as a |method|: > + GetMark()->getpos() getqflist([{what}]) *getqflist()* Returns a |List| with all the current quickfix errors. Each @@ -5339,6 +5377,9 @@ getreg([{regname} [, 1 [, {list}]]]) *getreg()* If {regname} is not specified, |v:register| is used. + Can also be used as a |method|: > + GetRegname()->getreg() + getreginfo([{regname}]) *getreginfo()* Returns detailed information about register {regname} as a Dictionary with the following entries: @@ -5377,6 +5418,9 @@ getregtype([{regname}]) *getregtype()* The {regname} argument is a string. If {regname} is not specified, |v:register| is used. + Can also be used as a |method|: > + GetRegname()->getregtype() + gettabinfo([{tabnr}]) *gettabinfo()* If {tabnr} is not specified, then information about all the tab pages is returned as a |List|. Each List item is a @@ -5390,6 +5434,9 @@ gettabinfo([{tabnr}]) *gettabinfo()* tabpage-local variables windows List of |window-ID|s in the tab page. + Can also be used as a |method|: > + GetTabnr()->gettabinfo() + gettabvar({tabnr}, {varname} [, {def}]) *gettabvar()* Get the value of a tab-local variable {varname} in tab page {tabnr}. |t:var| @@ -5400,6 +5447,9 @@ gettabvar({tabnr}, {varname} [, {def}]) *gettabvar()* When the tab or variable doesn't exist {def} or an empty string is returned, there is no error message. + Can also be used as a |method|: > + GetTabnr()->gettabvar(varname) + gettabwinvar({tabnr}, {winnr}, {varname} [, {def}]) *gettabwinvar()* Get the value of window-local variable {varname} in window {winnr} in tab page {tabnr}. @@ -5426,6 +5476,9 @@ gettabwinvar({tabnr}, {winnr}, {varname} [, {def}]) *gettabwinvar()* To obtain all window-local variables use: > gettabwinvar({tabnr}, {winnr}, '&') +< Can also be used as a |method|: > + GetTabnr()->gettabvar(winnr, varname) + gettagstack([{winnr}]) *gettagstack()* The result is a Dict, which is the tag stack of window {winnr}. {winnr} can be the window number or the |window-ID|. @@ -8339,6 +8392,9 @@ setfperm({fname}, {mode}) *setfperm()* *chmod* Returns non-zero for success, zero for failure. + Can also be used as a |method|: > + GetFilename()->setfperm(mode) +< To read permissions see |getfperm()|. setline({lnum}, {text}) *setline()* diff --git a/src/nvim/eval.lua b/src/nvim/eval.lua index f9f6af3bfd..83a72cc233 100644 --- a/src/nvim/eval.lua +++ b/src/nvim/eval.lua @@ -137,9 +137,9 @@ return { garbagecollect={args={0, 1}}, get={args={2, 3}, base=1}, getbufinfo={args={0, 1}}, - getbufline={args={2, 3}}, - getbufvar={args={2, 3}}, - getchangelist={args={1, 1}}, + getbufline={args={2, 3}, base=1}, + getbufvar={args={2, 3}, base=1}, + getchangelist={args={0, 1}, base=1}, getchar={args={0, 1}}, getcharmod={}, getcharsearch={}, @@ -148,30 +148,30 @@ return { getcmdpos={}, getcmdtype={}, getcmdwintype={}, - getcompletion={args={2, 3}}, + getcompletion={args={2, 3}, base=1}, getcurpos={}, - getcwd={args={0,2}}, - getenv={args={1}}, + getcwd={args={0, 2}, base=1}, + getenv={args={1}, base=1}, getfontname={args={0, 1}}, - getfperm={args=1}, - getfsize={args=1}, - getftime={args=1}, - getftype={args=1}, - getjumplist={args={0, 2}}, - getline={args={1, 2}}, + getfperm={args=1, base=1}, + getfsize={args=1, base=1}, + getftime={args=1, base=1}, + getftype={args=1, base=1}, + getjumplist={args={0, 2}, base=1}, + getline={args={1, 2}, base=1}, getloclist={args={1, 2}}, getmarklist={args={0, 1}}, getmatches={args={0, 1}}, getmousepos={}, getpid={}, - getpos={args=1}, + getpos={args=1, base=1}, getqflist={args={0, 1}}, - getreg={args={0, 3}}, + getreg={args={0, 3}, base=1}, getreginfo={args={0, 1}, base=1}, - getregtype={args={0, 1}}, - gettabinfo={args={0, 1}}, - gettabvar={args={2, 3}}, - gettabwinvar={args={3, 4}}, + getregtype={args={0, 1}, base=1}, + gettabinfo={args={0, 1}, base=1}, + gettabvar={args={2, 3}, base=1}, + gettabwinvar={args={3, 4}, base=1}, gettagstack={args={0, 1}}, getwininfo={args={0, 1}}, getwinpos={args={0, 1}}, @@ -311,7 +311,7 @@ return { setcharsearch={args=1}, setcmdpos={args=1}, setenv={args=2}, - setfperm={args=2}, + setfperm={args=2, base=1}, setline={args=2}, setloclist={args={2, 4}}, setmatches={args={1, 2}}, diff --git a/src/nvim/eval/funcs.c b/src/nvim/eval/funcs.c index 5569d74413..b53b50e766 100644 --- a/src/nvim/eval/funcs.c +++ b/src/nvim/eval/funcs.c @@ -3088,10 +3088,16 @@ f_getbufvar_end: static void f_getchangelist(typval_T *argvars, typval_T *rettv, FunPtr fptr) { tv_list_alloc_ret(rettv, 2); - vim_ignored = tv_get_number(&argvars[0]); // issue errmsg if type error - emsg_off++; - const buf_T *const buf = tv_get_buf(&argvars[0], false); - emsg_off--; + + const buf_T *buf; + if (argvars[0].v_type == VAR_UNKNOWN) { + buf = curbuf; + } else { + vim_ignored = tv_get_number(&argvars[0]); // issue errmsg if type error + emsg_off++; + buf = tv_get_buf(&argvars[0], false); + emsg_off--; + } if (buf == NULL) { return; } diff --git a/src/nvim/testdir/test_bufline.vim b/src/nvim/testdir/test_bufline.vim index 52a60b7b85..765ae17736 100644 --- a/src/nvim/testdir/test_bufline.vim +++ b/src/nvim/testdir/test_bufline.vim @@ -21,7 +21,7 @@ func Test_setbufline_getbufline() call assert_equal(1, setbufline(b, 5, ['x'])) call assert_equal(1, setbufline(1234, 1, ['x'])) call assert_equal(0, setbufline(b, 4, ['d', 'e'])) - call assert_equal(['c'], getbufline(b, 3)) + call assert_equal(['c'], b->getbufline(3)) call assert_equal(['d'], getbufline(b, 4)) call assert_equal(['e'], getbufline(b, 5)) call assert_equal([], getbufline(b, 6)) diff --git a/src/nvim/testdir/test_bufwintabinfo.vim b/src/nvim/testdir/test_bufwintabinfo.vim index 4b5b55e6bf..b0258547b8 100644 --- a/src/nvim/testdir/test_bufwintabinfo.vim +++ b/src/nvim/testdir/test_bufwintabinfo.vim @@ -88,7 +88,7 @@ function Test_getbufwintabinfo() call assert_equal(2, tablist[1].tabnr) call assert_equal('build', tablist[0].variables.space) call assert_equal(w2_id, tablist[0].windows[0]) - call assert_equal([], gettabinfo(3)) + call assert_equal([], 3->gettabinfo()) tabonly | only @@ -106,7 +106,7 @@ function Test_getbufwintabinfo() endfunction function Test_get_buf_options() - let opts = getbufvar(bufnr('%'), '&') + let opts = bufnr()->getbufvar('&') call assert_equal(v:t_dict, type(opts)) call assert_equal(8, opts.tabstop) endfunc diff --git a/src/nvim/testdir/test_changelist.vim b/src/nvim/testdir/test_changelist.vim index dd6ea9600c..ce77c1f3c7 100644 --- a/src/nvim/testdir/test_changelist.vim +++ b/src/nvim/testdir/test_changelist.vim @@ -8,8 +8,8 @@ func Test_getchangelist() bwipe! enew - call assert_equal([], getchangelist(10)) - call assert_equal([[], 0], getchangelist('%')) + call assert_equal([], 10->getchangelist()) + call assert_equal([[], 0], getchangelist()) call writefile(['line1', 'line2', 'line3'], 'Xfile1.txt') call writefile(['line1', 'line2', 'line3'], 'Xfile2.txt') diff --git a/src/nvim/testdir/test_cmdline.vim b/src/nvim/testdir/test_cmdline.vim index 5a6824b5c1..ffca415282 100644 --- a/src/nvim/testdir/test_cmdline.vim +++ b/src/nvim/testdir/test_cmdline.vim @@ -260,7 +260,7 @@ func Test_getcompletion() endif let groupcount = len(getcompletion('', 'event')) call assert_true(groupcount > 0) - let matchcount = len(getcompletion('File', 'event')) + let matchcount = len('File'->getcompletion('event')) call assert_true(matchcount > 0) call assert_true(groupcount > matchcount) diff --git a/src/nvim/testdir/test_edit.vim b/src/nvim/testdir/test_edit.vim index e1393e875b..2b389c015f 100644 --- a/src/nvim/testdir/test_edit.vim +++ b/src/nvim/testdir/test_edit.vim @@ -201,11 +201,11 @@ func Test_edit_07() endfu au InsertCharPre :call DoIt() call feedkeys("A\\u\\\", 'tx') - call assert_equal(["Jan\",''], getline(1,'$')) + call assert_equal(["Jan\",''], 1->getline('$')) %d call setline(1, 'J') call feedkeys("A\\u\\\", 'tx') - call assert_equal(["January"], getline(1,'$')) + call assert_equal(["January"], 1->getline('$')) delfu ListMonths delfu DoIt @@ -348,7 +348,7 @@ func Test_edit_12() call cursor(2, 4) call feedkeys("R^\", 'tnix') call assert_equal(["\tabc", "def"], getline(1, '$')) - call assert_equal([0, 2, 2, 0], getpos('.')) + call assert_equal([0, 2, 2, 0], '.'->getpos()) %d call setline(1, ["\tabc", "\t\tdef"]) call cursor(2, 2) diff --git a/src/nvim/testdir/test_environ.vim b/src/nvim/testdir/test_environ.vim index a25d83753c..cc15b63824 100644 --- a/src/nvim/testdir/test_environ.vim +++ b/src/nvim/testdir/test_environ.vim @@ -15,7 +15,7 @@ endfunc func Test_getenv() unlet! $TESTENV - call assert_equal(v:null, getenv('TESTENV')) + call assert_equal(v:null, 'TESTENV'->getenv()) let $TESTENV = 'foo' call assert_equal('foo', getenv('TESTENV')) endfunc diff --git a/src/nvim/testdir/test_getvar.vim b/src/nvim/testdir/test_getvar.vim index 3b61d68ebc..e9868c7887 100644 --- a/src/nvim/testdir/test_getvar.vim +++ b/src/nvim/testdir/test_getvar.vim @@ -31,7 +31,7 @@ func Test_var() let t:other = 777 let def_list = [4, 5, 6, 7] tabrewind - call assert_equal([1, 2, 3], gettabvar(3, 'var_list')) + call assert_equal([1, 2, 3], 3->gettabvar('var_list')) call assert_equal([1, 2, 3], gettabvar(3, 'var_list', def_list)) call assert_equal({'var_list': [1, 2, 3], 'other': 777}, gettabvar(3, '')) call assert_equal({'var_list': [1, 2, 3], 'other': 777}, @@ -61,7 +61,7 @@ func Test_var() let def_dict = {'dict2': 'newval'} wincmd b tabrewind - call assert_equal({'dict': 'tabwin'}, gettabwinvar(2, 3, 'var_dict')) + call assert_equal({'dict': 'tabwin'}, 2->gettabwinvar(3, 'var_dict')) call assert_equal({'dict': 'tabwin'}, \ gettabwinvar(2, 3, 'var_dict', def_dict)) call assert_equal({'var_dict': {'dict': 'tabwin'}}, gettabwinvar(2, 3, '')) diff --git a/src/nvim/testdir/test_jumplist.vim b/src/nvim/testdir/test_jumplist.vim index be1af5e705..9cfbbe2029 100644 --- a/src/nvim/testdir/test_jumplist.vim +++ b/src/nvim/testdir/test_jumplist.vim @@ -39,7 +39,7 @@ func Test_getjumplist() " Traverse the jump list and verify the results 5 exe "normal \" - call assert_equal(2, getjumplist(1)[1]) + call assert_equal(2, 1->getjumplist()[1]) exe "normal 2\" call assert_equal(0, getjumplist(1, 1)[1]) exe "normal 3\" diff --git a/src/nvim/testdir/test_stat.vim b/src/nvim/testdir/test_stat.vim index 5b7df33d2c..170358e023 100644 --- a/src/nvim/testdir/test_stat.vim +++ b/src/nvim/testdir/test_stat.vim @@ -10,7 +10,7 @@ func CheckFileTime(doSleep) let fl = ['Hello World!'] for fname in fnames call writefile(fl, fname) - call add(times, getftime(fname)) + call add(times, fname->getftime()) if a:doSleep sleep 1 endif @@ -19,8 +19,8 @@ func CheckFileTime(doSleep) let time_correct = (times[0] <= times[1] && times[1] <= times[2]) if a:doSleep || time_correct call assert_true(time_correct, printf('Expected %s <= %s <= %s', times[0], times[1], times[2])) - call assert_equal(strlen(fl[0] . "\n"), getfsize(fnames[0])) - call assert_equal('file', getftype(fnames[0])) + call assert_equal(strlen(fl[0] . "\n"), fnames[0]->getfsize()) + call assert_equal('file', fnames[0]->getftype()) call assert_equal('rw-', getfperm(fnames[0])[0:2]) let result = 1 endif diff --git a/test/functional/legacy/file_perm_spec.lua b/test/functional/legacy/file_perm_spec.lua index 8fdee95e91..ccdbfe0534 100644 --- a/test/functional/legacy/file_perm_spec.lua +++ b/test/functional/legacy/file_perm_spec.lua @@ -3,7 +3,7 @@ require('os') local helpers = require('test.functional.helpers')(after_each) local clear, call, eq = helpers.clear, helpers.call, helpers.eq -local neq, exc_exec = helpers.neq, helpers.exc_exec +local neq, exc_exec, eval = helpers.neq, helpers.exc_exec, helpers.eval describe('Test getting and setting file permissions', function() local tempfile = helpers.tmpname() @@ -14,11 +14,12 @@ describe('Test getting and setting file permissions', function() end) it('file permissions', function() + -- eval() is used to test VimL method syntax for setfperm() and getfperm() eq('', call('getfperm', tempfile)) - eq(0, call('setfperm', tempfile, 'r--------')) + eq(0, eval("'" .. tempfile .. "'->setfperm('r--------')")) call('writefile', {'one'}, tempfile) - eq(9, call('len', call('getfperm', tempfile))) + eq(9, eval("len('" .. tempfile .. "'->getfperm())")) eq(1, call('setfperm', tempfile, 'rwx------')) if helpers.is_os('win') then From 8b7615c735325245cff20907fbd7e0470a0d00d0 Mon Sep 17 00:00:00 2001 From: Sean Dewar Date: Tue, 31 Aug 2021 22:41:44 +0100 Subject: [PATCH 4/9] vim-patch:8.1.1952: more functions can be used as a method Problem: More functions can be used as a method. Solution: Allow more functions to be used as a method. https://github.com/vim/vim/commit/5d69fdb7c4b91faf2d92b8d449cc9460f3035fb3 --- runtime/doc/eval.txt | 25 +++++++++++++++++++++++-- src/nvim/eval.lua | 14 +++++++------- src/nvim/testdir/test_bufwintabinfo.vim | 2 +- src/nvim/testdir/test_escaped_glob.vim | 6 +++--- src/nvim/testdir/test_getvar.vim | 4 ++-- src/nvim/testdir/test_glob2regpat.vim | 2 +- src/nvim/testdir/test_tagjump.vim | 2 +- 7 files changed, 38 insertions(+), 17 deletions(-) diff --git a/runtime/doc/eval.txt b/runtime/doc/eval.txt index 24b6e6da6d..ffc6221818 100644 --- a/runtime/doc/eval.txt +++ b/runtime/doc/eval.txt @@ -5477,7 +5477,7 @@ gettabwinvar({tabnr}, {winnr}, {varname} [, {def}]) *gettabwinvar()* gettabwinvar({tabnr}, {winnr}, '&') < Can also be used as a |method|: > - GetTabnr()->gettabvar(winnr, varname) + GetTabnr()->gettabwinvar(winnr, varname) gettagstack([{winnr}]) *gettagstack()* The result is a Dict, which is the tag stack of window {winnr}. @@ -5507,6 +5507,9 @@ gettagstack([{winnr}]) *gettagstack()* See |tagstack| for more information about the tag stack. + Can also be used as a |method|: > + GetWinnr()->gettagstack() + getwininfo([{winid}]) *getwininfo()* Returns information about windows as a |List| with Dictionaries. @@ -5538,6 +5541,9 @@ getwininfo([{winid}]) *getwininfo()* winrow topmost screen line of the window; "row" from |win_screenpos()| + Can also be used as a |method|: > + GetWinnr()->getwininfo() + getwinpos([{timeout}]) *getwinpos()* The result is a |List| with two numbers, the result of |getwinposx()| and |getwinposy()| combined: @@ -5557,6 +5563,9 @@ getwinpos([{timeout}]) *getwinpos()* endif " Do some work here endwhile +< + Can also be used as a |method|: > + GetTimeout()->getwinpos() < *getwinposx()* getwinposx() The result is a Number, which is the X coordinate in pixels of @@ -5575,6 +5584,9 @@ getwinvar({winnr}, {varname} [, {def}]) *getwinvar()* Examples: > :let list_is_on = getwinvar(2, '&list') :echo "myvar = " . getwinvar(1, 'myvar') + +< Can also be used as a |method|: > + GetWinnr()->getwinvar(varname) < glob({expr} [, {nosuf} [, {list} [, {alllinks}]]]) *glob()* Expand the file wildcards in {expr}. See |wildcards| for the @@ -5612,6 +5624,9 @@ glob({expr} [, {nosuf} [, {list} [, {alllinks}]]]) *glob()* See |expand()| for expanding special Vim variables. See |system()| for getting the raw output of an external command. + Can also be used as a |method|: > + GetExpr()->glob() + glob2regpat({string}) *glob2regpat()* Convert a file pattern, as used by glob(), into a search pattern. The result can be used to match with a string that @@ -5624,7 +5639,9 @@ glob2regpat({string}) *glob2regpat()* Note that the result depends on the system. On MS-Windows a backslash usually means a path separator. - *globpath()* + Can also be used as a |method|: > + GetExpr()->glob2regpat() +< *globpath()* globpath({path}, {expr} [, {nosuf} [, {list} [, {allinks}]]]) Perform glob() for String {expr} on all directories in {path} and concatenate the results. Example: > @@ -5660,6 +5677,10 @@ globpath({path}, {expr} [, {nosuf} [, {list} [, {allinks}]]]) < Upwards search and limiting the depth of "**" is not supported, thus using 'path' will not always work properly. + Can also be used as a |method|, the base is passed as the + second argument: > + GetExpr()->globpath(&rtp) +< *has()* has({feature}) Returns 1 if {feature} is supported, 0 otherwise. The {feature} argument is a feature name like "nvim-0.2.1" or diff --git a/src/nvim/eval.lua b/src/nvim/eval.lua index 83a72cc233..cc38a0734e 100644 --- a/src/nvim/eval.lua +++ b/src/nvim/eval.lua @@ -172,15 +172,15 @@ return { gettabinfo={args={0, 1}, base=1}, gettabvar={args={2, 3}, base=1}, gettabwinvar={args={3, 4}, base=1}, - gettagstack={args={0, 1}}, - getwininfo={args={0, 1}}, - getwinpos={args={0, 1}}, + gettagstack={args={0, 1}, base=1}, + getwininfo={args={0, 1}, base=1}, + getwinpos={args={0, 1}, base=1}, getwinposx={}, getwinposy={}, - getwinvar={args={2, 3}}, - glob={args={1, 4}}, - glob2regpat={args=1}, - globpath={args={2, 5}}, + getwinvar={args={2, 3}, base=1}, + glob={args={1, 4}, base=1}, + glob2regpat={args=1, base=1}, + globpath={args={2, 5}, base=2}, has={args=1}, has_key={args=2, base=1}, haslocaldir={args={0,2}}, diff --git a/src/nvim/testdir/test_bufwintabinfo.vim b/src/nvim/testdir/test_bufwintabinfo.vim index b0258547b8..bb672cf0ec 100644 --- a/src/nvim/testdir/test_bufwintabinfo.vim +++ b/src/nvim/testdir/test_bufwintabinfo.vim @@ -77,7 +77,7 @@ function Test_getbufwintabinfo() call assert_equal('green', winlist[2].variables.signal) call assert_equal(w4_id, winlist[3].winid) - let winfo = getwininfo(w5_id)[0] + let winfo = w5_id->getwininfo()[0] call assert_equal(2, winfo.tabnr) call assert_equal([], getwininfo(3)) diff --git a/src/nvim/testdir/test_escaped_glob.vim b/src/nvim/testdir/test_escaped_glob.vim index 2bfd82c296..1a4fd8bdab 100644 --- a/src/nvim/testdir/test_escaped_glob.vim +++ b/src/nvim/testdir/test_escaped_glob.vim @@ -16,7 +16,7 @@ function Test_glob() " Execute these commands in the sandbox, so that using the shell fails. " Setting 'shell' to an invalid name causes a memory leak. sandbox call assert_equal("", glob('Xxx\{')) - sandbox call assert_equal("", glob('Xxx\$')) + sandbox call assert_equal("", 'Xxx\$'->glob()) w! Xxx\{ " } to fix highlighting w! Xxx\$ @@ -28,7 +28,7 @@ endfunction function Test_globpath() sandbox call assert_equal(expand("sautest/autoload/globone.vim\nsautest/autoload/globtwo.vim"), - \ globpath('sautest/autoload', 'glob*.vim')) + \ globpath('sautest/autoload', 'glob*.vim')) sandbox call assert_equal([expand('sautest/autoload/globone.vim'), expand('sautest/autoload/globtwo.vim')], - \ globpath('sautest/autoload', 'glob*.vim', 0, 1)) + \ 'glob*.vim'->globpath('sautest/autoload', 0, 1)) endfunction diff --git a/src/nvim/testdir/test_getvar.vim b/src/nvim/testdir/test_getvar.vim index e9868c7887..5a96548893 100644 --- a/src/nvim/testdir/test_getvar.vim +++ b/src/nvim/testdir/test_getvar.vim @@ -12,8 +12,8 @@ func Test_var() let def_str = "Chance" call assert_equal('Dance', getwinvar(1, 'var_str')) call assert_equal('Dance', getwinvar(1, 'var_str', def_str)) - call assert_equal({'var_str': 'Dance'}, getwinvar(1, '')) - call assert_equal({'var_str': 'Dance'}, getwinvar(1, '', def_str)) + call assert_equal({'var_str': 'Dance'}, 1->getwinvar('')) + call assert_equal({'var_str': 'Dance'}, 1->getwinvar('', def_str)) unlet w:var_str call assert_equal('Chance', getwinvar(1, 'var_str', def_str)) call assert_equal({}, getwinvar(1, '')) diff --git a/src/nvim/testdir/test_glob2regpat.vim b/src/nvim/testdir/test_glob2regpat.vim index 354f239ef1..a423a4a9f0 100644 --- a/src/nvim/testdir/test_glob2regpat.vim +++ b/src/nvim/testdir/test_glob2regpat.vim @@ -10,7 +10,7 @@ endfunc func Test_glob2regpat_valid() call assert_equal('^foo\.', glob2regpat('foo.*')) - call assert_equal('^foo.$', glob2regpat('foo?')) + call assert_equal('^foo.$', 'foo?'->glob2regpat()) call assert_equal('\.vim$', glob2regpat('*.vim')) call assert_equal('^[abc]$', glob2regpat('[abc]')) call assert_equal('^foo bar$', glob2regpat('foo\ bar')) diff --git a/src/nvim/testdir/test_tagjump.vim b/src/nvim/testdir/test_tagjump.vim index 0fa7f85f0d..15182893e9 100644 --- a/src/nvim/testdir/test_tagjump.vim +++ b/src/nvim/testdir/test_tagjump.vim @@ -316,7 +316,7 @@ func Test_getsettagstack() enew | only call settagstack(1, {'items' : []}) call assert_equal(0, gettagstack(1).length) - call assert_equal([], gettagstack(1).items) + call assert_equal([], 1->gettagstack().items) " Error cases call assert_equal({}, gettagstack(100)) call assert_equal(-1, settagstack(100, {'items' : []})) From 59c8a1fd5158886cb13b56070ebf15259d12eba2 Mon Sep 17 00:00:00 2001 From: Sean Dewar Date: Tue, 31 Aug 2021 22:51:29 +0100 Subject: [PATCH 5/9] feat(eval/method): partially port v8.1.1953 Adds method call support for all functions in the patch, but it cannot be fully ported due to missing tests for: - index(): requires Blobs from v8.1.0735. Note that index() was already added as a method in v8.1.1803; this patch only adds a test. - iconv(): requires v8.1.1136 for test_termcodes.vim. Nvim deprecated inputdialog(), so it no longer has an eval.txt entry. Keep the test for hlexists() commented-out, just like previously. (Nvim always defines the Number group, so it always returns 1 instead) Cannot include both changes to test_syn_attr.vim as Nvim doesn't support ":hi term=..."; however, both test the same ->hlID() syntax anyway. --- runtime/doc/eval.txt | 47 ++++++++++++++++++++++++++ src/nvim/eval.lua | 36 ++++++++++---------- src/nvim/testdir/test_breakindent.vim | 6 ++-- src/nvim/testdir/test_functions.vim | 25 ++++++++++++-- src/nvim/testdir/test_getcwd.vim | 2 +- src/nvim/testdir/test_history.vim | 8 ++--- src/nvim/testdir/test_listdict.vim | 2 +- src/nvim/testdir/test_syn_attr.vim | 2 +- src/nvim/testdir/test_true_false.vim | 2 +- test/functional/legacy/delete_spec.lua | 2 +- 10 files changed, 99 insertions(+), 33 deletions(-) diff --git a/runtime/doc/eval.txt b/runtime/doc/eval.txt index ffc6221818..f998c5750a 100644 --- a/runtime/doc/eval.txt +++ b/runtime/doc/eval.txt @@ -5763,6 +5763,9 @@ haslocaldir([{winnr}[, {tabnr}]]) *haslocaldir()* {winnr} can be the window number or the |window-ID|. If {winnr} is -1 it is ignored, only the tab is resolved. + Can also be used as a |method|: > + GetWinnr()->haslocaldir() + hasmapto({what} [, {mode} [, {abbr}]]) *hasmapto()* The result is a Number, which is TRUE if there is a mapping that contains {what} in somewhere in the rhs (what it is @@ -5792,6 +5795,9 @@ hasmapto({what} [, {mode} [, {abbr}]]) *hasmapto()* < This installs the mapping to "\ABCdoit" only if there isn't already a mapping to "\ABCdoit". + Can also be used as a |method|: > + GetRHS()->hasmapto() + histadd({history}, {item}) *histadd()* Add the String {item} to the history {history} which can be one of: *hist-names* @@ -5813,6 +5819,10 @@ histadd({history}, {item}) *histadd()* :let date=input("Enter date: ") < This function is not available in the |sandbox|. + Can also be used as a |method|, the base is used for the + second argument: > + GetPattern()->histadd('search') + histdel({history} [, {item}]) *histdel()* Clear {history}, i.e. delete all its entries. See |hist-names| for the possible values of {history}. @@ -5844,6 +5854,9 @@ histdel({history} [, {item}]) *histdel()* the "n" command and 'hlsearch': > :call histdel("search", -1) :let @/ = histget("search", -1) +< + Can also be used as a |method|: > + GetHistory()->histdel() histget({history} [, {index}]) *histget()* The result is a String, the entry with Number {index} from @@ -5860,6 +5873,9 @@ histget({history} [, {index}]) *histget()* the {num}th entry from the output of |:history|. > :command -nargs=1 H execute histget("cmd", 0+) < + Can also be used as a |method|: > + GetHistory()->histget() + histnr({history}) *histnr()* The result is the Number of the current entry in {history}. See |hist-names| for the possible values of {history}. @@ -5867,6 +5883,9 @@ histnr({history}) *histnr()* Example: > :let inp_index = histnr("expr") + +< Can also be used as a |method|: > + GetHistory()->histnr() < hlexists({name}) *hlexists()* The result is a Number, which is TRUE if a highlight group @@ -5875,6 +5894,9 @@ hlexists({name}) *hlexists()* been defined for it, it may also have been used for a syntax item. + Can also be used as a |method|: > + GetName()->hlexists() +< *hlID()* hlID({name}) The result is a Number, which is the ID of the highlight group with name {name}. When the highlight group doesn't exist, @@ -5883,6 +5905,9 @@ hlID({name}) The result is a Number, which is the ID of the highlight group group. For example, to get the background color of the "Comment" group: > :echo synIDattr(synIDtrans(hlID("Comment")), "bg") +< + Can also be used as a |method|: > + GetName()->hlID() hostname() *hostname()* The result is a String, which is the name of the machine on @@ -5901,6 +5926,9 @@ iconv({string}, {from}, {to}) *iconv()* from/to UCS-2 is automatically changed to use UTF-8. You cannot use UCS-2 in a string anyway, because of the NUL bytes. + Can also be used as a |method|: > + GetText()->iconv('latin1', 'utf-8') +< *indent()* indent({lnum}) The result is a Number, which is indent of line {lnum} in the current buffer. The indent is counted in spaces, the value @@ -5908,6 +5936,8 @@ indent({lnum}) The result is a Number, which is indent of line {lnum} in the |getline()|. When {lnum} is invalid -1 is returned. + Can also be used as a |method|: > + GetLnum()->indent() index({object}, {expr} [, {start} [, {ic}]]) *index()* If {object} is a |List| return the lowest index where the item @@ -5928,6 +5958,8 @@ index({object}, {expr} [, {start} [, {ic}]]) *index()* :let idx = index(words, "the") :if index(numbers, 123) >= 0 +< Can also be used as a |method|: > + GetObject()->index(what) input({prompt} [, {text} [, {completion}]]) *input()* input({opts}) @@ -6040,6 +6072,9 @@ input({opts}) : call inputrestore() :endfunction +< Can also be used as a |method|: > + GetPrompt()->input() + inputlist({textlist}) *inputlist()* {textlist} must be a |List| of strings. This |List| is displayed, one string per line. The user will be prompted to @@ -6057,6 +6092,9 @@ inputlist({textlist}) *inputlist()* let color = inputlist(['Select color:', '1. red', \ '2. green', '3. blue']) +< Can also be used as a |method|: > + GetChoices()->inputlist() + inputrestore() *inputrestore()* Restore typeahead that was saved with a previous |inputsave()|. Should be called the same number of times inputsave() is @@ -6082,6 +6120,9 @@ inputsecret({prompt} [, {text}]) *inputsecret()* typed on the command-line in response to the issued prompt. NOTE: Command-line completion is not supported. + Can also be used as a |method|: > + GetPrompt()->inputsecret() + insert({object}, {item} [, {idx}]) *insert()* When {object} is a |List| or a |Blob| insert {item} at the start of it. @@ -6128,6 +6169,9 @@ isdirectory({directory}) *isdirectory()* exist, or isn't a directory, the result is |FALSE|. {directory} is any expression, which is used as a String. + Can also be used as a |method|: > + GetName()->isdirectory() + isinf({expr}) *isinf()* Return 1 if {expr} is a positive infinity, or -1 a negative infinity, otherwise 0. > @@ -6153,6 +6197,9 @@ islocked({expr}) *islocked()* *E786* < When {expr} is a variable that does not exist you get an error message. Use |exists()| to check for existence. + Can also be used as a |method|: > + GetName()->islocked() + id({expr}) *id()* Returns a |String| which is a unique identifier of the container type (|List|, |Dict|, |Blob| and |Partial|). It is diff --git a/src/nvim/eval.lua b/src/nvim/eval.lua index cc38a0734e..f600b4ce06 100644 --- a/src/nvim/eval.lua +++ b/src/nvim/eval.lua @@ -183,32 +183,32 @@ return { globpath={args={2, 5}, base=2}, has={args=1}, has_key={args=2, base=1}, - haslocaldir={args={0,2}}, - hasmapto={args={1, 3}}, - highlightID={args=1, func='f_hlID'}, -- obsolete - highlight_exists={args=1, func='f_hlexists'}, -- obsolete - histadd={args=2}, - histdel={args={1, 2}}, - histget={args={1, 2}}, - histnr={args=1}, - hlID={args=1}, - hlexists={args=1}, + haslocaldir={args={0, 2}, base=1}, + hasmapto={args={1, 3}, base=1}, + highlightID={args=1, base=1, func='f_hlID'}, -- obsolete + highlight_exists={args=1, base=1, func='f_hlexists'}, -- obsolete + histadd={args=2, base=2}, + histdel={args={1, 2}, base=1}, + histget={args={1, 2}, base=1}, + histnr={args=1, base=1}, + hlID={args=1, base=1}, + hlexists={args=1, base=1}, hostname={}, - iconv={args=3}, - indent={args=1}, + iconv={args=3, base=1}, + indent={args=1, base=1}, index={args={2, 4}, base=1}, - input={args={1, 3}}, - inputdialog={args={1, 3}}, - inputlist={args=1}, + input={args={1, 3}, base=1}, + inputdialog={args={1, 3}, base=1}, + inputlist={args=1, base=1}, inputrestore={}, inputsave={}, - inputsecret={args={1, 2}}, + inputsecret={args={1, 2}, base=1}, insert={args={2, 3}, base=1}, interrupt={args=0}, invert={args=1, base=1}, - isdirectory={args=1}, + isdirectory={args=1, base=1}, isinf={args=1, base=1}, - islocked={args=1}, + islocked={args=1, base=1}, isnan={args=1, base=1}, id={args=1}, items={args=1, base=1}, diff --git a/src/nvim/testdir/test_breakindent.vim b/src/nvim/testdir/test_breakindent.vim index 97b570e64f..277050876e 100644 --- a/src/nvim/testdir/test_breakindent.vim +++ b/src/nvim/testdir/test_breakindent.vim @@ -418,8 +418,8 @@ endfunc func Test_breakindent11() " test strdisplaywidth() call s:test_windows('setl cpo-=n sbr=>> nu nuw=4 nolist briopt= ts=4') - let text=getline(2) - let width = strlen(text[1:])+indent(2)+strlen(&sbr)*3 " text wraps 3 times + let text = getline(2) + let width = strlen(text[1:]) + indent(2) + strlen(&sbr) * 3 " text wraps 3 times call assert_equal(width, strdisplaywidth(text)) call s:close_windows('set sbr=') endfunc @@ -431,7 +431,7 @@ func Test_breakindent11_vartabs() " test strdisplaywidth() call s:test_windows('setl cpo-=n sbr=>> nu nuw=4 nolist briopt= ts=4 vts=4') let text = getline(2) - let width = strlen(text[1:])+indent(2)+strlen(&sbr)*3 " text wraps 3 times + let width = strlen(text[1:]) + 2->indent() + strlen(&sbr) * 3 " text wraps 3 times call assert_equal(width, strdisplaywidth(text)) call s:close_windows('set sbr= vts&') endfunc diff --git a/src/nvim/testdir/test_functions.vim b/src/nvim/testdir/test_functions.vim index e3a80be6d5..90732549de 100644 --- a/src/nvim/testdir/test_functions.vim +++ b/src/nvim/testdir/test_functions.vim @@ -1127,7 +1127,7 @@ endfunc func Test_hlexists() call assert_equal(0, hlexists('does_not_exist')) - " call assert_equal(0, hlexists('Number')) + " call assert_equal(0, 'Number'->hlexists()) call assert_equal(0, highlight_exists('does_not_exist')) " call assert_equal(0, highlight_exists('Number')) syntax on @@ -1160,7 +1160,7 @@ endfunc func Test_inputlist() call feedkeys(":let c = inputlist(['Select color:', '1. red', '2. green', '3. blue'])\1\", 'tx') call assert_equal(1, c) - call feedkeys(":let c = inputlist(['Select color:', '1. red', '2. green', '3. blue'])\2\", 'tx') + call feedkeys(":let c = ['Select color:', '1. red', '2. green', '3. blue']->inputlist()\2\", 'tx') call assert_equal(2, c) call feedkeys(":let c = inputlist(['Select color:', '1. red', '2. green', '3. blue'])\3\", 'tx') call assert_equal(3, c) @@ -1413,7 +1413,7 @@ func Test_reg_executing_and_recording() let g:regs = [] func TestFunc() abort let g:regs += [reg_executing()] - let g:typed = input('?') + let g:typed = '?'->input() let g:regs += [reg_executing()] endfunc call feedkeys("@qy\", 'xt') @@ -1429,6 +1429,25 @@ func Test_reg_executing_and_recording() unlet s:reg_stat endfunc +func Test_inputsecret() + map W :call TestFunc() + let @q = "W" + let g:typed1 = '' + let g:typed2 = '' + let g:regs = [] + func TestFunc() abort + let g:typed1 = '?'->inputsecret() + let g:typed2 = inputsecret('password: ') + endfunc + call feedkeys("@qsomething\else\", 'xt') + call assert_equal("something", g:typed1) + call assert_equal("else", g:typed2) + delfunc TestFunc + unmap W + unlet g:typed1 + unlet g:typed2 +endfunc + func Test_getchar() call feedkeys('a', '') call assert_equal(char2nr('a'), getchar()) diff --git a/src/nvim/testdir/test_getcwd.vim b/src/nvim/testdir/test_getcwd.vim index ca098781e4..b9343b1daa 100644 --- a/src/nvim/testdir/test_getcwd.vim +++ b/src/nvim/testdir/test_getcwd.vim @@ -17,7 +17,7 @@ func GetCwdInfo(win, tab) let lflag = haslocaldir(a:win) else let dirname = fnamemodify(getcwd(a:win, a:tab), mod) - let lflag = haslocaldir(a:win, a:tab) + let lflag = a:win->haslocaldir(a:tab) endif return bufname . ' ' . dirname . ' ' . lflag endfunc diff --git a/src/nvim/testdir/test_history.vim b/src/nvim/testdir/test_history.vim index 16aad9889e..2f0dc2dae1 100644 --- a/src/nvim/testdir/test_history.vim +++ b/src/nvim/testdir/test_history.vim @@ -13,7 +13,7 @@ function History_Tests(hist) call assert_equal(-1, histnr(a:hist)) call assert_equal('', histget(a:hist)) - call assert_true(histadd(a:hist, 'ls')) + call assert_true('ls'->histadd(a:hist)) call assert_true(histadd(a:hist, 'buffers')) call assert_equal('buffers', histget(a:hist)) call assert_equal('ls', histget(a:hist, -2)) @@ -22,14 +22,14 @@ function History_Tests(hist) call assert_equal('', histget(a:hist, -5)) call assert_equal(2, histnr(a:hist)) call assert_true(histdel(a:hist, 2)) - call assert_false(histdel(a:hist, 7)) + call assert_false(a:hist->histdel(7)) call assert_equal(1, histnr(a:hist)) call assert_equal('ls', histget(a:hist, -1)) call assert_true(histadd(a:hist, 'buffers')) call assert_true(histadd(a:hist, 'ls')) - call assert_equal('ls', histget(a:hist, -1)) - call assert_equal(4, histnr(a:hist)) + call assert_equal('ls', a:hist->histget(-1)) + call assert_equal(4, a:hist->histnr()) let a=execute('history ' . a:hist) call assert_match("^\n # \\S* history\n 3 buffers\n> 4 ls$", a) diff --git a/src/nvim/testdir/test_listdict.vim b/src/nvim/testdir/test_listdict.vim index ae035fa519..f6c404d390 100644 --- a/src/nvim/testdir/test_listdict.vim +++ b/src/nvim/testdir/test_listdict.vim @@ -573,7 +573,7 @@ func Test_lockvar_script_autoload() set rtp+=./sautest lockvar g:footest#x unlockvar g:footest#x - call assert_equal(-1, islocked('g:footest#x')) + call assert_equal(-1, 'g:footest#x'->islocked()) call assert_equal(0, exists('g:footest#x')) call assert_equal(1, g:footest#x) let &rtp = old_rtp diff --git a/src/nvim/testdir/test_syn_attr.vim b/src/nvim/testdir/test_syn_attr.vim index 353054fec8..fa0b08fde5 100644 --- a/src/nvim/testdir/test_syn_attr.vim +++ b/src/nvim/testdir/test_syn_attr.vim @@ -8,7 +8,7 @@ func Test_missing_attr() call assert_equal('1', synIDattr(hlID("Mine"), "inverse", 'cterm')) hi Mine cterm=standout gui=undercurl call assert_equal('1', synIDattr(hlID("Mine"), "standout", 'cterm')) - call assert_equal('1', synIDattr(hlID("Mine"), "undercurl", 'gui')) + call assert_equal('1', synIDattr("Mine"->hlID(), "undercurl", 'gui')) hi Mine gui=strikethrough call assert_equal('1', synIDattr(hlID("Mine"), "strikethrough", 'gui')) hi Mine cterm=NONE gui=NONE diff --git a/src/nvim/testdir/test_true_false.vim b/src/nvim/testdir/test_true_false.vim index 315ba188cb..f3c7fff4a6 100644 --- a/src/nvim/testdir/test_true_false.vim +++ b/src/nvim/testdir/test_true_false.vim @@ -104,7 +104,7 @@ func Test_true_false_arg() call Try_arg_true_false('maparg("asdf", "i", %v%)', "", "asdff") call Try_arg_true_false('FilterMapArg(maparg("asdf", "i", 1, %v%))', "asdff", {'rhs': 'asdff'}) - call Try_arg_true_false('hasmapto("asdf", "i", %v%)', 0, 1) + call Try_arg_true_false('"asdf"->hasmapto("i", %v%)', 0, 1) new colored call setline(1, '') diff --git a/test/functional/legacy/delete_spec.lua b/test/functional/legacy/delete_spec.lua index b4ed8ff136..141d9583e6 100644 --- a/test/functional/legacy/delete_spec.lua +++ b/test/functional/legacy/delete_spec.lua @@ -39,7 +39,7 @@ describe('Test for delete()', function() eq(eval("['a', 'b']"), eval("readfile('Xdir1/Xfile')")) eq(1, eval("isdirectory('Xdir1/subdir')")) eq(eval("['a', 'b']"), eval("readfile('Xdir1/subdir/Xfile')")) - eq(1, eval("isdirectory('Xdir1/empty')")) + eq(1, eval("'Xdir1/empty'->isdirectory()")) eq(0, eval("delete('Xdir1', 'rf')")) eq(0, eval("isdirectory('Xdir1')")) eq(-1, eval("delete('Xdir1', 'd')")) From 86593beaa40035a10a664d3147327a01f4885cb7 Mon Sep 17 00:00:00 2001 From: Sean Dewar Date: Tue, 31 Aug 2021 23:49:43 +0100 Subject: [PATCH 6/9] feat(eval/method): partially port v8.1.1954 Does not include listener_*() functions. js_*() functions are N/A. json_encode() and json_decode() didn't include tests; add some anyway (to json_functions_spec.lua). test_lua.vim isn't included yet, so add tests to luaeval_spec.lua. --- runtime/doc/eval.txt | 31 ++++++++++++++++++- src/nvim/eval.lua | 18 +++++------ src/nvim/testdir/test_arglist.vim | 2 +- src/nvim/testdir/test_functions.vim | 10 +++--- src/nvim/testdir/test_lispwords.vim | 3 ++ src/nvim/testdir/test_utf8.vim | 2 +- test/functional/lua/luaeval_spec.lua | 7 +++-- .../vimscript/json_functions_spec.lua | 8 +++-- 8 files changed, 58 insertions(+), 23 deletions(-) diff --git a/runtime/doc/eval.txt b/runtime/doc/eval.txt index f998c5750a..9f8cad7af1 100644 --- a/runtime/doc/eval.txt +++ b/runtime/doc/eval.txt @@ -1204,7 +1204,7 @@ next method: > mylist->filter(filterexpr)->map(mapexpr)->sort()->join() < Example of using a lambda: > - GetPercentage->{x -> x * 100}()->printf('%d%%') + GetPercentage()->{x -> x * 100}()->printf('%d%%') < When using -> the |expr7| operators will be applied first, thus: > -1.234->string() @@ -6384,6 +6384,9 @@ json_decode({expr}) *json_decode()* recommended and the only one required to be supported. Non-UTF-8 characters are an error. + Can also be used as a |method|: > + ReadObject()->json_decode() + json_encode({expr}) *json_encode()* Convert {expr} into a JSON string. Accepts |msgpack-special-dict| as the input. Will not convert @@ -6396,6 +6399,9 @@ json_encode({expr}) *json_encode()* or special escapes like "\t", other are dumped as-is. |Blob|s are converted to arrays of the individual bytes. + Can also be used as a |method|: > + GetObject()->json_encode() + keys({dict}) *keys()* Return a |List| with all the keys of {dict}. The |List| is in arbitrary order. Also see |items()| and |values()|. @@ -6459,6 +6465,10 @@ libcall({libname}, {funcname}, {argument}) object code must be compiled as position-independent ('PIC'). Examples: > :echo libcall("libc.so", "getenv", "HOME") + +< Can also be used as a |method|, where the base is passed as + the argument to the called function: > + GetValue()->libcall("libc.so", "getenv") < *libcallnr()* libcallnr({libname}, {funcname}, {argument}) @@ -6468,6 +6478,10 @@ libcallnr({libname}, {funcname}, {argument}) :echo libcallnr("/usr/lib/libc.so", "getpid", "") :call libcallnr("libc.so", "printf", "Hello World!\n") :call libcallnr("libc.so", "sleep", 10) +< + Can also be used as a |method|, where the base is passed as + the argument to the called function: > + GetValue()->libcallnr("libc.so", "printf") < *line()* line({expr}) The result is a Number, which is the line number of the file @@ -6493,6 +6507,9 @@ line({expr}) The result is a Number, which is the line number of the file line(".") line number of the cursor line("'t") line number of mark t line("'" . marker) line number of mark marker +< + Can also be used as a |method|: > + GetValue()->line() line2byte({lnum}) *line2byte()* Return the byte count from the start of the buffer for line @@ -6507,6 +6524,9 @@ line2byte({lnum}) *line2byte()* |getline()|. When {lnum} is invalid -1 is returned. Also see |byte2line()|, |go| and |:goto|. + Can also be used as a |method|: > + GetLnum()->line2byte() + lispindent({lnum}) *lispindent()* Get the amount of indent for line {lnum} according the lisp indenting rules, as with 'lisp'. @@ -6514,6 +6534,9 @@ lispindent({lnum}) *lispindent()* relevant. {lnum} is used just like in |getline()|. When {lnum} is invalid, -1 is returned. + Can also be used as a |method|: > + GetLnum()->lispindent() + list2str({list} [, {utf8}]) *list2str()* Convert each number in {list} to a character string can concatenate them all. Examples: > @@ -6528,6 +6551,9 @@ list2str({list} [, {utf8}]) *list2str()* With utf-8 composing characters work as expected: > list2str([97, 769]) returns "á" < + Can also be used as a |method|: > + GetList()->list2str() + localtime() *localtime()* Return the current time, measured as seconds since 1st Jan 1970. See also |strftime()|, |strptime()| and |getftime()|. @@ -6562,6 +6588,9 @@ luaeval({expr}[, {expr}]) Evaluate Lua expression {expr} and return its result converted to Vim data structures. See |lua-eval| for more details. + Can also be used as a |method|: > + GetExpr()->luaeval() + map({expr1}, {expr2}) *map()* {expr1} must be a |List|, |Blob| or |Dictionary|. Replace each item in {expr1} with the result of evaluating diff --git a/src/nvim/eval.lua b/src/nvim/eval.lua index f600b4ce06..572e32e5a7 100644 --- a/src/nvim/eval.lua +++ b/src/nvim/eval.lua @@ -220,21 +220,21 @@ return { jobstop={args=1}, jobwait={args={1, 2}}, join={args={1, 2}, base=1}, - json_decode={args=1}, - json_encode={args=1}, + json_decode={args=1, base=1}, + json_encode={args=1, base=1}, keys={args=1, base=1}, last_buffer_nr={}, -- obsolete len={args=1, base=1}, - libcall={args=3}, - libcallnr={args=3}, - line={args={1, 2}}, - line2byte={args=1}, - lispindent={args=1}, - list2str={args={1, 2}}, + libcall={args=3, base=3}, + libcallnr={args=3, base=3}, + line={args={1, 2}, base=1}, + line2byte={args=1, base=1}, + lispindent={args=1, base=1}, + list2str={args={1, 2}, base=1}, localtime={}, log={args=1, base=1, func="float_op_wrapper", data="&log"}, log10={args=1, base=1, func="float_op_wrapper", data="&log10"}, - luaeval={args={1, 2}}, + luaeval={args={1, 2}, base=1}, map={args=2, base=1}, maparg={args={1, 4}}, mapcheck={args={1, 3}}, diff --git a/src/nvim/testdir/test_arglist.vim b/src/nvim/testdir/test_arglist.vim index 01d8f32893..8fd60d6a5a 100644 --- a/src/nvim/testdir/test_arglist.vim +++ b/src/nvim/testdir/test_arglist.vim @@ -88,7 +88,7 @@ func Test_argadd_empty_curbuf() argadd Xargadd call assert_equal(curbuf, bufnr('%')) call assert_equal('', bufname('%')) - call assert_equal(1, line('$')) + call assert_equal(1, '$'->line()) rew call assert_notequal(curbuf, '%'->bufnr()) call assert_equal('Xargadd', '%'->bufname()) diff --git a/src/nvim/testdir/test_functions.vim b/src/nvim/testdir/test_functions.vim index 90732549de..02e01497f9 100644 --- a/src/nvim/testdir/test_functions.vim +++ b/src/nvim/testdir/test_functions.vim @@ -905,7 +905,7 @@ func Test_byte2line_line2byte() call assert_equal([-1, -1, 1, 1, 2, 2, 2, 3, 3, -1], \ map(range(-1, 8), 'v:val->byte2line()')) call assert_equal([-1, -1, 1, 3, 6, 8, -1], - \ map(range(-1, 5), 'line2byte(v:val)')) + \ map(range(-1, 5), 'v:val->line2byte()')) set fileformat=dos call assert_equal([-1, -1, 1, 1, 1, 2, 2, 2, 2, 3, 3, 3, -1], @@ -1505,17 +1505,17 @@ func Test_libcall_libcallnr() endif if has('win32') - call assert_equal($USERPROFILE, libcall(libc, 'getenv', 'USERPROFILE')) + call assert_equal($USERPROFILE, 'USERPROFILE'->libcall(libc, 'getenv')) else - call assert_equal($HOME, libcall(libc, 'getenv', 'HOME')) + call assert_equal($HOME, 'HOME'->libcall(libc, 'getenv')) endif " If function returns NULL, libcall() should return an empty string. call assert_equal('', libcall(libc, 'getenv', 'X_ENV_DOES_NOT_EXIT')) " Test libcallnr() with string and integer argument. - call assert_equal(4, libcallnr(libc, 'strlen', 'abcd')) - call assert_equal(char2nr('A'), libcallnr(libc, 'toupper', char2nr('a'))) + call assert_equal(4, 'abcd'->libcallnr(libc, 'strlen')) + call assert_equal(char2nr('A'), char2nr('a')->libcallnr(libc, 'toupper')) call assert_fails("call libcall(libc, 'Xdoesnotexist_', '')", 'E364:') call assert_fails("call libcallnr(libc, 'Xdoesnotexist_', '')", 'E364:') diff --git a/src/nvim/testdir/test_lispwords.vim b/src/nvim/testdir/test_lispwords.vim index 4c05504cf1..aa5a738bdf 100644 --- a/src/nvim/testdir/test_lispwords.vim +++ b/src/nvim/testdir/test_lispwords.vim @@ -43,6 +43,9 @@ func Test_lisp_indent() \ ',@body', \ '(princ "")))' \ ]) + call assert_equal(7, lispindent(2)) + call assert_equal(5, 6->lispindent()) + set lisp set lispwords& let save_copt = &cpoptions diff --git a/src/nvim/testdir/test_utf8.vim b/src/nvim/testdir/test_utf8.vim index 735efac36d..da72da087f 100644 --- a/src/nvim/testdir/test_utf8.vim +++ b/src/nvim/testdir/test_utf8.vim @@ -111,7 +111,7 @@ func Test_list2str_str2list_utf8() let s = "\u304b\u3099\u3044" let l = [0x304b, 0x3099, 0x3044] call assert_equal(l, str2list(s, 1)) - call assert_equal(s, list2str(l, 1)) + call assert_equal(s, l->list2str(1)) if &enc ==# 'utf-8' call assert_equal(str2list(s), str2list(s, 1)) call assert_equal(list2str(l), list2str(l, 1)) diff --git a/test/functional/lua/luaeval_spec.lua b/test/functional/lua/luaeval_spec.lua index 255e99032f..0675ec9abd 100644 --- a/test/functional/lua/luaeval_spec.lua +++ b/test/functional/lua/luaeval_spec.lua @@ -86,14 +86,15 @@ describe('luaeval()', function() -- meaningful later. it('correctly evaluates scalars', function() + -- Also test method call (->) syntax eq(1, funcs.luaeval('1')) - eq(0, eval('type(luaeval("1"))')) + eq(0, eval('"1"->luaeval()->type()')) eq(1.5, funcs.luaeval('1.5')) - eq(5, eval('type(luaeval("1.5"))')) + eq(5, eval('"1.5"->luaeval()->type()')) eq("test", funcs.luaeval('"test"')) - eq(1, eval('type(luaeval("\'test\'"))')) + eq(1, eval('"\'test\'"->luaeval()->type()')) eq('', funcs.luaeval('""')) eq('\000', funcs.luaeval([['\0']])) diff --git a/test/functional/vimscript/json_functions_spec.lua b/test/functional/vimscript/json_functions_spec.lua index c3b607b544..5d1597f53d 100644 --- a/test/functional/vimscript/json_functions_spec.lua +++ b/test/functional/vimscript/json_functions_spec.lua @@ -168,7 +168,8 @@ describe('json_decode() function', function() end) it('parses floating-point numbers', function() - eq('100000.0', eval('string(json_decode("100000.0"))')) + -- Also test method call (->) syntax + eq('100000.0', eval('"100000.0"->json_decode()->string()')) eq(100000.5, funcs.json_decode('100000.5')) eq(-100000.5, funcs.json_decode('-100000.5')) eq(-100000.5e50, funcs.json_decode('-100000.5e50')) @@ -549,11 +550,12 @@ describe('json_encode() function', function() end) it('dumps floats', function() - eq('0.0', eval('json_encode(0.0)')) + -- Also test method call (->) syntax + eq('0.0', eval('0.0->json_encode()')) eq('10.5', funcs.json_encode(10.5)) eq('-10.5', funcs.json_encode(-10.5)) eq('-1.0e-5', funcs.json_encode(-1e-5)) - eq('1.0e50', eval('json_encode(1.0e50)')) + eq('1.0e50', eval('1.0e50->json_encode()')) end) it('fails to dump NaN and infinite values', function() From d23d37b212d7b47ae1f729de5e0ea46b456ad2e5 Mon Sep 17 00:00:00 2001 From: Sean Dewar Date: Wed, 1 Sep 2021 12:02:56 +0100 Subject: [PATCH 7/9] vim-patch:8.1.1961: more functions can be used as a method Problem: More functions can be used as a method. Solution: Allow more functions to be used as a method. Add a test for mapcheck(). https://github.com/vim/vim/commit/a1449836334355b1fb00cd1bf083e7d353f6c4d7 mzeval() (if_mzscheme) is N/A. --- runtime/doc/eval.txt | 38 ++++++++++++++++++++++++++ src/nvim/eval.lua | 26 +++++++++--------- src/nvim/testdir/test_functions.vim | 14 +++++----- src/nvim/testdir/test_getcwd.vim | 2 +- src/nvim/testdir/test_maparg.vim | 42 ++++++++++++++++++++++++++++- src/nvim/testdir/test_match.vim | 8 +++--- 6 files changed, 104 insertions(+), 26 deletions(-) diff --git a/runtime/doc/eval.txt b/runtime/doc/eval.txt index 9f8cad7af1..3253fc649f 100644 --- a/runtime/doc/eval.txt +++ b/runtime/doc/eval.txt @@ -6698,6 +6698,8 @@ maparg({name} [, {mode} [, {abbr} [, {dict}]]]) *maparg()* mapped, and have it do the original mapping too. Sketch: > exe 'nnoremap ==' . maparg('', 'n') +< Can also be used as a |method|: > + GetKey()->maparg('n') mapcheck({name} [, {mode} [, {abbr}]]) *mapcheck()* Check if there is a mapping that matches with {name} in mode @@ -6732,6 +6734,9 @@ mapcheck({name} [, {mode} [, {abbr}]]) *mapcheck()* < This avoids adding the "_vv" mapping when there already is a mapping for "_v" or for "_vvv". + Can also be used as a |method|: > + GetKey()->mapcheck('n') + match({expr}, {pat} [, {start} [, {count}]]) *match()* When {expr} is a |List| then this returns the index of the first item where {pat} matches. Each item is used as a @@ -6794,6 +6799,9 @@ match({expr}, {pat} [, {start} [, {count}]]) *match()* zero matches at the start instead of a number of matches further down in the text. + Can also be used as a |method|: > + GetList()->match('word') +< *matchadd()* *E798* *E799* *E801* *E957* matchadd({group}, {pattern}[, {priority}[, {id} [, {dict}]]]) Defines a pattern to be highlighted in the current window (a @@ -6849,6 +6857,9 @@ matchadd({group}, {pattern}[, {priority}[, {id} [, {dict}]]]) available from |getmatches()|. All matches can be deleted in one operation by |clearmatches()|. + Can also be used as a |method|: > + GetGroup()->matchadd('TODO') +< *matchaddpos()* matchaddpos({group}, {pos} [, {priority} [, {id} [, {dict}]]]) Same as |matchadd()|, but requires a list of positions {pos} @@ -6887,6 +6898,9 @@ matchaddpos({group}, {pos} [, {priority} [, {id} [, {dict}]]]) < Matches added by |matchaddpos()| are returned by |getmatches()|. + Can also be used as a |method|: > + GetGroup()->matchaddpos([23, 11]) + matcharg({nr}) *matcharg()* Selects the {nr} match item, as set with a |:match|, |:2match| or |:3match| command. @@ -6899,6 +6913,9 @@ matcharg({nr}) *matcharg()* Highlighting matches using the |:match| commands are limited to three matches. |matchadd()| does not have this limitation. + Can also be used as a |method|: > + GetMatch()->matcharg() + matchdelete({id} [, {win}]) *matchdelete()* *E802* *E803* Deletes a match with ID {id} previously defined by |matchadd()| or one of the |:match| commands. Returns 0 if successful, @@ -6907,6 +6924,9 @@ matchdelete({id} [, {win}]) *matchdelete()* *E802* *E803* If {win} is specified, use the window with this number or window ID instead of the current window. + Can also be used as a |method|: > + GetMatch()->matchdelete() + matchend({expr}, {pat} [, {start} [, {count}]]) *matchend()* Same as |match()|, but return the index of first character after the match. Example: > @@ -6926,6 +6946,9 @@ matchend({expr}, {pat} [, {start} [, {count}]]) *matchend()* < result is "-1". When {expr} is a |List| the result is equal to |match()|. + Can also be used as a |method|: > + GetText()->matchend('word') + matchlist({expr}, {pat} [, {start} [, {count}]]) *matchlist()* Same as |match()|, but return a |List|. The first item in the list is the matched string, same as what matchstr() would @@ -6936,6 +6959,9 @@ matchlist({expr}, {pat} [, {start} [, {count}]]) *matchlist()* < Results in: ['acd', 'a', '', 'c', 'd', '', '', '', '', ''] When there is no match an empty list is returned. + Can also be used as a |method|: > + GetList()->matchlist('word') + matchstr({expr}, {pat} [, {start} [, {count}]]) *matchstr()* Same as |match()|, but return the matched string. Example: > :echo matchstr("testing", "ing") @@ -6949,6 +6975,9 @@ matchstr({expr}, {pat} [, {start} [, {count}]]) *matchstr()* When {expr} is a |List| then the matching item is returned. The type isn't changed, it's not necessarily a String. + Can also be used as a |method|: > + GetText()->matchstr('word') + matchstrpos({expr}, {pat} [, {start} [, {count}]]) *matchstrpos()* Same as |matchstr()|, but return the matched string, the start position and the end position of the match. Example: > @@ -6967,6 +6996,9 @@ matchstrpos({expr}, {pat} [, {start} [, {count}]]) *matchstrpos()* < result is ["x", 1, 2, 3]. The type isn't changed, it's not necessarily a String. + Can also be used as a |method|: > + GetText()->matchstrpos('word') + *max()* max({expr}) Return the maximum value of all items in {expr}. {expr} can be a |List| or a |Dictionary|. For a Dictionary, @@ -7057,6 +7089,9 @@ mkdir({name} [, {path} [, {prot}]]) successful or FALSE if the directory creation failed or partly failed. + Can also be used as a |method|: > + GetName()->mkdir() +< *mode()* mode([expr]) Return a string that indicates the current mode. If [expr] is supplied and it evaluates to a non-zero Number or @@ -7106,6 +7141,9 @@ mode([expr]) Return a string that indicates the current mode. the leading character(s). Also see |visualmode()|. + Can also be used as a |method|: > + DoFull()->mode() + msgpackdump({list} [, {type}]) *msgpackdump()* Convert a list of VimL objects to msgpack. Returned value is a |readfile()|-style list. When {type} contains "B", a |Blob| is diff --git a/src/nvim/eval.lua b/src/nvim/eval.lua index 572e32e5a7..854bfd5f61 100644 --- a/src/nvim/eval.lua +++ b/src/nvim/eval.lua @@ -236,22 +236,22 @@ return { log10={args=1, base=1, func="float_op_wrapper", data="&log10"}, luaeval={args={1, 2}, base=1}, map={args=2, base=1}, - maparg={args={1, 4}}, - mapcheck={args={1, 3}}, - match={args={2, 4}}, - matchadd={args={2, 5}}, - matchaddpos={args={2, 5}}, - matcharg={args=1}, - matchdelete={args={1, 2}}, - matchend={args={2, 4}}, - matchlist={args={2, 4}}, - matchstr={args={2, 4}}, - matchstrpos={args={2,4}}, + maparg={args={1, 4}, base=1}, + mapcheck={args={1, 3}, base=1}, + match={args={2, 4}, base=1}, + matchadd={args={2, 5}, base=1}, + matchaddpos={args={2, 5}, base=1}, + matcharg={args=1, base=1}, + matchdelete={args={1, 2}, base=1}, + matchend={args={2, 4}, base=1}, + matchlist={args={2, 4}, base=1}, + matchstr={args={2, 4}, base=1}, + matchstrpos={args={2,4}, base=1}, max={args=1, base=1}, menu_get={args={1, 2}}, min={args=1, base=1}, - mkdir={args={1, 3}}, - mode={args={0, 1}}, + mkdir={args={1, 3}, base=1}, + mode={args={0, 1}, base=1}, msgpackdump={args={1, 2}}, msgpackparse={args=1}, nextnonblank={args=1}, diff --git a/src/nvim/testdir/test_functions.vim b/src/nvim/testdir/test_functions.vim index 02e01497f9..d4da8dde40 100644 --- a/src/nvim/testdir/test_functions.vim +++ b/src/nvim/testdir/test_functions.vim @@ -658,8 +658,8 @@ func Test_mode() exe "normal gRabc\\\\u" call assert_equal('R-Rvc', g:current_modes) - call assert_equal('n', mode(0)) - call assert_equal('n', mode(1)) + call assert_equal('n', 0->mode()) + call assert_equal('n', 1->mode()) " i_CTRL-O exe "normal i\:call Save_mode()\\" @@ -815,7 +815,7 @@ endfunc func Test_match_func() call assert_equal(4, match('testing', 'ing')) - call assert_equal(4, match('testing', 'ing', 2)) + call assert_equal(4, 'testing'->match('ing', 2)) call assert_equal(-1, match('testing', 'ing', 5)) call assert_equal(-1, match('testing', 'ing', 8)) call assert_equal(1, match(['vim', 'testing', 'execute'], 'ing')) @@ -824,7 +824,7 @@ endfunc func Test_matchend() call assert_equal(7, matchend('testing', 'ing')) - call assert_equal(7, matchend('testing', 'ing', 2)) + call assert_equal(7, 'testing'->matchend('ing', 2)) call assert_equal(-1, matchend('testing', 'ing', 5)) call assert_equal(-1, matchend('testing', 'ing', 8)) call assert_equal(match(['vim', 'testing', 'execute'], 'ing'), matchend(['vim', 'testing', 'execute'], 'ing')) @@ -833,13 +833,13 @@ endfunc func Test_matchlist() call assert_equal(['acd', 'a', '', 'c', 'd', '', '', '', '', ''], matchlist('acd', '\(a\)\?\(b\)\?\(c\)\?\(.*\)')) - call assert_equal(['d', '', '', '', 'd', '', '', '', '', ''], matchlist('acd', '\(a\)\?\(b\)\?\(c\)\?\(.*\)', 2)) + call assert_equal(['d', '', '', '', 'd', '', '', '', '', ''], 'acd'->matchlist('\(a\)\?\(b\)\?\(c\)\?\(.*\)', 2)) call assert_equal([], matchlist('acd', '\(a\)\?\(b\)\?\(c\)\?\(.*\)', 4)) endfunc func Test_matchstr() call assert_equal('ing', matchstr('testing', 'ing')) - call assert_equal('ing', matchstr('testing', 'ing', 2)) + call assert_equal('ing', 'testing'->matchstr('ing', 2)) call assert_equal('', matchstr('testing', 'ing', 5)) call assert_equal('', matchstr('testing', 'ing', 8)) call assert_equal('testing', matchstr(['vim', 'testing', 'execute'], 'ing')) @@ -848,7 +848,7 @@ endfunc func Test_matchstrpos() call assert_equal(['ing', 4, 7], matchstrpos('testing', 'ing')) - call assert_equal(['ing', 4, 7], matchstrpos('testing', 'ing', 2)) + call assert_equal(['ing', 4, 7], 'testing'->matchstrpos('ing', 2)) call assert_equal(['', -1, -1], matchstrpos('testing', 'ing', 5)) call assert_equal(['', -1, -1], matchstrpos('testing', 'ing', 8)) call assert_equal(['ing', 1, 4, 7], matchstrpos(['vim', 'testing', 'execute'], 'ing')) diff --git a/src/nvim/testdir/test_getcwd.vim b/src/nvim/testdir/test_getcwd.vim index b9343b1daa..2ff396b641 100644 --- a/src/nvim/testdir/test_getcwd.vim +++ b/src/nvim/testdir/test_getcwd.vim @@ -35,7 +35,7 @@ function SetUp() " we start from a clean state. call delete("Xtopdir", "rf") new - call mkdir('Xtopdir') + eval 'Xtopdir'->mkdir() cd Xtopdir let g:topdir = getcwd() call mkdir('Xdir1') diff --git a/src/nvim/testdir/test_maparg.vim b/src/nvim/testdir/test_maparg.vim index 238d2f900d..5b082198cf 100644 --- a/src/nvim/testdir/test_maparg.vim +++ b/src/nvim/testdir/test_maparg.vim @@ -1,5 +1,6 @@ " Tests for maparg(). " Also test utf8 map with a 0x80 byte. +" Also test mapcheck() function s:SID() return str2nr(matchstr(expand(''), '\zs\d\+\ze_SID$')) @@ -22,7 +23,7 @@ function Test_maparg() call assert_equal({'silent': 1, 'noremap': 1, 'script': 1, 'lhs': 'bar', 'mode': 'v', \ 'nowait': 0, 'expr': 1, 'sid': sid, 'lnum': lnum + 2, \ 'rhs': 'isbar', 'buffer': 1}, - \ maparg('bar', '', 0, 1)) + \ 'bar'->maparg('', 0, 1)) let lnum = expand('') map foo bar call assert_equal({'silent': 0, 'noremap': 0, 'script': 0, 'lhs': 'foo', 'mode': ' ', @@ -51,6 +52,45 @@ function Test_maparg() unmap abc endfunction +func Test_mapcheck() + call assert_equal('', mapcheck('a')) + call assert_equal('', mapcheck('abc')) + call assert_equal('', mapcheck('ax')) + call assert_equal('', mapcheck('b')) + + map a something + call assert_equal('something', mapcheck('a')) + call assert_equal('something', mapcheck('a', 'n')) + call assert_equal('', mapcheck('a', 'c')) + call assert_equal('', mapcheck('a', 'i')) + call assert_equal('something', 'abc'->mapcheck()) + call assert_equal('something', 'ax'->mapcheck()) + call assert_equal('', mapcheck('b')) + unmap a + + map ab foobar + call assert_equal('foobar', mapcheck('a')) + call assert_equal('foobar', mapcheck('abc')) + call assert_equal('', mapcheck('ax')) + call assert_equal('', mapcheck('b')) + unmap ab + + map abc barfoo + call assert_equal('barfoo', mapcheck('a')) + call assert_equal('barfoo', mapcheck('a', 'n', 0)) + call assert_equal('', mapcheck('a', 'n', 1)) + call assert_equal('barfoo', mapcheck('abc')) + call assert_equal('', mapcheck('ax')) + call assert_equal('', mapcheck('b')) + unmap abc + + abbr ab abbrev + call assert_equal('abbrev', mapcheck('a', 'i', 1)) + call assert_equal('', mapcheck('a', 'n', 1)) + call assert_equal('', mapcheck('a', 'i', 0)) + unabbr ab +endfunc + function Test_range_map() new " Outside of the range, minimum diff --git a/src/nvim/testdir/test_match.vim b/src/nvim/testdir/test_match.vim index 505a052a19..70271aa32f 100644 --- a/src/nvim/testdir/test_match.vim +++ b/src/nvim/testdir/test_match.vim @@ -14,7 +14,7 @@ function Test_match() 2match MyGroup2 /FIXME/ 3match MyGroup3 /XXX/ call assert_equal(['MyGroup1', 'TODO'], matcharg(1)) - call assert_equal(['MyGroup2', 'FIXME'], matcharg(2)) + call assert_equal(['MyGroup2', 'FIXME'], 2->matcharg()) call assert_equal(['MyGroup3', 'XXX'], matcharg(3)) " --- Check that "matcharg()" returns an empty list if the argument is not 1, @@ -43,7 +43,7 @@ function Test_match() " --- Check that "matchdelete()" deletes the matches defined in the previous " --- test correctly. call matchdelete(m1) - call matchdelete(m2) + eval m2->matchdelete() call matchdelete(m3) call assert_equal([], getmatches()) @@ -55,7 +55,7 @@ function Test_match() " --- Check that "clearmatches()" clears all matches defined by ":match" and " --- "matchadd()". let m1 = matchadd("MyGroup1", "TODO") - let m2 = matchadd("MyGroup2", "FIXME", 42) + let m2 = "MyGroup2"->matchadd("FIXME", 42) let m3 = matchadd("MyGroup3", "XXX", 60, 17) match MyGroup1 /COFFEE/ 2match MyGroup2 /HUMPPA/ @@ -117,7 +117,7 @@ function Test_match() call clearmatches() call setline(1, 'abcdΣabcdef') - call matchaddpos("MyGroup1", [[1, 4, 2], [1, 9, 2]]) + eval "MyGroup1"->matchaddpos([[1, 4, 2], [1, 9, 2]]) 1 redraw! let v1 = screenattr(1, 1) From c5583df3c081e485b521570891dbdd16cd952a85 Mon Sep 17 00:00:00 2001 From: Sean Dewar Date: Wed, 1 Sep 2021 12:28:16 +0100 Subject: [PATCH 8/9] vim-patch:8.1.1984: more functions can be used as methods Problem: More functions can be used as methods. Solution: Make various functions usable as a method. https://github.com/vim/vim/commit/3f4f3d8e7e6fc0494d00cfb75669a554c8e67c8b test_prompt_buffer.vim already had all the changes, except Test_prompt_garbage_collect(). --- runtime/doc/eval.txt | 32 +++++++++++++++++++++++++ src/nvim/eval.lua | 22 ++++++++--------- src/nvim/testdir/test_functions.vim | 14 +++++------ src/nvim/testdir/test_perl.vim | 2 +- src/nvim/testdir/test_prompt_buffer.vim | 7 ++---- src/nvim/testdir/test_python2.vim | 2 +- src/nvim/testdir/test_python3.vim | 2 +- src/nvim/testdir/test_pyx2.vim | 2 +- 8 files changed, 56 insertions(+), 27 deletions(-) diff --git a/runtime/doc/eval.txt b/runtime/doc/eval.txt index 3253fc649f..1878913311 100644 --- a/runtime/doc/eval.txt +++ b/runtime/doc/eval.txt @@ -7246,6 +7246,9 @@ nextnonblank({lnum}) *nextnonblank()* {lnum} is used like with |getline()|. See also |prevnonblank()|. + Can also be used as a |method|: > + GetLnum()->nextnonblank() + nr2char({expr} [, {utf8}]) *nr2char()* Return a string with a single character, which has the number value {expr}. Examples: > @@ -7260,6 +7263,9 @@ nr2char({expr} [, {utf8}]) *nr2char()* characters. nr2char(0) is a real NUL and terminates the string, thus results in an empty string. + Can also be used as a |method|: > + GetNumber()->nr2char() + nvim_...({...}) *E5555* *nvim_...()* *eval-api* Call nvim |api| functions. The type checking of arguments will be stricter than for most other builtins. For instance, @@ -7288,6 +7294,9 @@ pathshorten({path}) *pathshorten()* < ~/.c/n/a/file1.vim ~ It doesn't matter if the path exists or not. + Can also be used as a |method|: > + GetDirectories()->pathshorten() + perleval({expr}) *perleval()* Evaluate |perl| expression {expr} and return its result converted to Vim data structures. @@ -7303,6 +7312,9 @@ perleval({expr}) *perleval()* :echo perleval('[1 .. 4]') < [1, 2, 3, 4] + Can also be used as a |method|: > + GetExpr()->perleval() + pow({x}, {y}) *pow()* Return the power of {x} to the exponent {y} as a |Float|. {x} and {y} must evaluate to a |Float| or a |Number|. @@ -7326,6 +7338,8 @@ prevnonblank({lnum}) *prevnonblank()* {lnum} is used like with |getline()|. Also see |nextnonblank()|. + Can also be used as a |method|: > + GetLnum()->prevnonblank() printf({fmt}, {expr1} ...) *printf()* Return a String with {fmt}, where "%" items are replaced by @@ -7558,6 +7572,9 @@ prompt_setcallback({buf}, {expr}) *prompt_setcallback()* endif endfunc +< Can also be used as a |method|: > + GetBuffer()->prompt_setcallback(callback) + prompt_setinterrupt({buf}, {expr}) *prompt_setinterrupt()* Set a callback for buffer {buf} to {expr}. When {expr} is an empty string the callback is removed. This has only effect if @@ -7567,12 +7584,18 @@ prompt_setinterrupt({buf}, {expr}) *prompt_setinterrupt()* mode. Without setting a callback Vim will exit Insert mode, as in any buffer. + Can also be used as a |method|: > + GetBuffer()->prompt_setinterrupt(callback) + prompt_setprompt({buf}, {text}) *prompt_setprompt()* Set prompt for buffer {buf} to {text}. You most likely want {text} to end in a space. The result is only visible if {buf} has 'buftype' set to "prompt". Example: > call prompt_setprompt(bufnr(''), 'command: ') +< + Can also be used as a |method|: > + GetBuffer()->prompt_setprompt('command: ') pum_getpos() *pum_getpos()* If the popup menu (see |ins-completion-menu|) is not visible, @@ -7603,6 +7626,9 @@ py3eval({expr}) *py3eval()* Dictionaries are represented as Vim |Dictionary| type with keys converted to strings. + Can also be used as a |method|: > + GetExpr()->py3eval() +< *E858* *E859* pyeval({expr}) *pyeval()* Evaluate Python expression {expr} and return its result @@ -7613,12 +7639,18 @@ pyeval({expr}) *pyeval()* Dictionaries are represented as Vim |Dictionary| type, non-string keys result in error. + Can also be used as a |method|: > + GetExpr()->pyeval() + pyxeval({expr}) *pyxeval()* Evaluate Python expression {expr} and return its result converted to Vim data structures. Uses Python 2 or 3, see |python_x| and 'pyxversion'. See also: |pyeval()|, |py3eval()| + Can also be used as a |method|: > + GetExpr()->pyxeval() +< *E726* *E727* range({expr} [, {max} [, {stride}]]) *range()* Returns a |List| with Numbers: diff --git a/src/nvim/eval.lua b/src/nvim/eval.lua index 854bfd5f61..741b8547fe 100644 --- a/src/nvim/eval.lua +++ b/src/nvim/eval.lua @@ -254,23 +254,23 @@ return { mode={args={0, 1}, base=1}, msgpackdump={args={1, 2}}, msgpackparse={args=1}, - nextnonblank={args=1}, - nr2char={args={1, 2}}, + nextnonblank={args=1, base=1}, + nr2char={args={1, 2}, base=1}, ['or']={args=2, base=1}, - pathshorten={args=1}, + pathshorten={args=1, base=1}, pow={args=2, base=1}, - prevnonblank={args=1}, + prevnonblank={args=1, base=1}, printf={args=varargs(1), base=2}, prompt_getprompt={args=1}, - prompt_setcallback={args={2, 2}}, - prompt_setinterrupt={args={2, 2}}, - prompt_setprompt={args={2, 2}}, + prompt_setcallback={args={2, 2}, base=1}, + prompt_setinterrupt={args={2, 2}, base=1}, + prompt_setprompt={args={2, 2}, base=1}, pum_getpos={}, pumvisible={}, - py3eval={args=1}, - pyeval={args=1}, - pyxeval={args=1}, - perleval={args=1}, + py3eval={args=1, base=1}, + pyeval={args=1, base=1}, + pyxeval={args=1, base=1}, + perleval={args=1, base=1}, range={args={1, 3}}, readdir={args={1, 2}}, readfile={args={1, 3}}, diff --git a/src/nvim/testdir/test_functions.vim b/src/nvim/testdir/test_functions.vim index d4da8dde40..c08b43736b 100644 --- a/src/nvim/testdir/test_functions.vim +++ b/src/nvim/testdir/test_functions.vim @@ -360,10 +360,10 @@ endfunc func Test_pathshorten() call assert_equal('', pathshorten('')) call assert_equal('foo', pathshorten('foo')) - call assert_equal('/foo', pathshorten('/foo')) + call assert_equal('/foo', '/foo'->pathshorten()) call assert_equal('f/', pathshorten('foo/')) call assert_equal('f/bar', pathshorten('foo/bar')) - call assert_equal('f/b/foobar', pathshorten('foo/bar/foobar')) + call assert_equal('f/b/foobar', 'foo/bar/foobar'->pathshorten()) call assert_equal('/f/b/foobar', pathshorten('/foo/bar/foobar')) call assert_equal('.f/bar', pathshorten('.foo/bar')) call assert_equal('~f/bar', pathshorten('~foo/bar')) @@ -869,21 +869,21 @@ Test call assert_equal(0, nextnonblank(-1)) call assert_equal(0, nextnonblank(0)) call assert_equal(1, nextnonblank(1)) - call assert_equal(4, nextnonblank(2)) + call assert_equal(4, 2->nextnonblank()) call assert_equal(4, nextnonblank(3)) call assert_equal(4, nextnonblank(4)) call assert_equal(6, nextnonblank(5)) call assert_equal(6, nextnonblank(6)) call assert_equal(7, nextnonblank(7)) - call assert_equal(0, nextnonblank(8)) + call assert_equal(0, 8->nextnonblank()) call assert_equal(0, prevnonblank(-1)) call assert_equal(0, prevnonblank(0)) - call assert_equal(1, prevnonblank(1)) + call assert_equal(1, 1->prevnonblank()) call assert_equal(1, prevnonblank(2)) call assert_equal(1, prevnonblank(3)) call assert_equal(4, prevnonblank(4)) - call assert_equal(4, prevnonblank(5)) + call assert_equal(4, 5->prevnonblank()) call assert_equal(6, prevnonblank(6)) call assert_equal(7, prevnonblank(7)) call assert_equal(0, prevnonblank(8)) @@ -1292,7 +1292,7 @@ func Test_trim() call assert_fails('call trim(" vim ", " ", -1)', 'E475:') call assert_fails('call trim(" vim ", " ", 3)', 'E475:') - let chars = join(map(range(1, 0x20) + [0xa0], {n -> nr2char(n)}), '') + let chars = join(map(range(1, 0x20) + [0xa0], {n -> n->nr2char()}), '') call assert_equal("x", trim(chars . "x" . chars)) endfunc diff --git a/src/nvim/testdir/test_perl.vim b/src/nvim/testdir/test_perl.vim index 872194a804..b911a982f9 100644 --- a/src/nvim/testdir/test_perl.vim +++ b/src/nvim/testdir/test_perl.vim @@ -32,7 +32,7 @@ endfunc funct Test_VIM_Blob() call assert_equal('0z', perleval('VIM::Blob("")')) - call assert_equal('0z31326162', perleval('VIM::Blob("12ab")')) + call assert_equal('0z31326162', 'VIM::Blob("12ab")'->perleval()) call assert_equal('0z00010203', perleval('VIM::Blob("\x00\x01\x02\x03")')) call assert_equal('0z8081FEFF', perleval('VIM::Blob("\x80\x81\xfe\xff")')) endfunc diff --git a/src/nvim/testdir/test_prompt_buffer.vim b/src/nvim/testdir/test_prompt_buffer.vim index 6fc5850be3..3da46eb1a6 100644 --- a/src/nvim/testdir/test_prompt_buffer.vim +++ b/src/nvim/testdir/test_prompt_buffer.vim @@ -110,11 +110,8 @@ func Test_prompt_garbage_collect() new set buftype=prompt - " Nvim doesn't support method call syntax yet. - " eval bufnr('')->prompt_setcallback(function('MyPromptCallback', [{}])) - " eval bufnr('')->prompt_setinterrupt(function('MyPromptInterrupt', [{}])) - eval prompt_setcallback(bufnr(''), function('MyPromptCallback', [{}])) - eval prompt_setinterrupt(bufnr(''), function('MyPromptInterrupt', [{}])) + eval bufnr('')->prompt_setcallback(function('MyPromptCallback', [{}])) + eval bufnr('')->prompt_setinterrupt(function('MyPromptInterrupt', [{}])) call test_garbagecollect_now() " Must not crash call feedkeys("\\", 'xt') diff --git a/src/nvim/testdir/test_python2.vim b/src/nvim/testdir/test_python2.vim index 5895ac85a8..ae8bc57c7f 100644 --- a/src/nvim/testdir/test_python2.vim +++ b/src/nvim/testdir/test_python2.vim @@ -59,7 +59,7 @@ func Test_vim_function() try py f = vim.Function('\x80\xfdR' + vim.eval('s:foo()')) - call assert_equal(name, pyeval('f.name')) + call assert_equal(name, 'f.name'->pyeval()) catch call assert_false(v:exception) endtry diff --git a/src/nvim/testdir/test_python3.vim b/src/nvim/testdir/test_python3.vim index 637648817c..54da3d2eba 100644 --- a/src/nvim/testdir/test_python3.vim +++ b/src/nvim/testdir/test_python3.vim @@ -59,7 +59,7 @@ func Test_vim_function() try py3 f = vim.Function(b'\x80\xfdR' + vim.eval('s:foo()').encode()) - call assert_equal(name, py3eval('f.name')) + call assert_equal(name, 'f.name'->py3eval()) catch call assert_false(v:exception) endtry diff --git a/src/nvim/testdir/test_pyx2.vim b/src/nvim/testdir/test_pyx2.vim index 10ff3b6e58..b6ed80f842 100644 --- a/src/nvim/testdir/test_pyx2.vim +++ b/src/nvim/testdir/test_pyx2.vim @@ -35,7 +35,7 @@ endfunc func Test_pyxeval() pyx import sys - call assert_match(s:py2pattern, split(pyxeval('sys.version'))[0]) + call assert_match(s:py2pattern, split('sys.version'->pyxeval())[0]) endfunc From a8504638cd2497b3bdd0daf27dcc50903e1e2bb9 Mon Sep 17 00:00:00 2001 From: Sean Dewar Date: Wed, 1 Sep 2021 13:40:58 +0100 Subject: [PATCH 9/9] feat(eval/method): partially port v8.1.1987 Cannot be fully ported as the remote_*() functions from +clientserver are not yet ported. Include the test changes anyway. line()'s optional winid argument was already ported. (Wasn't added in this patch; this just adds documentation) --- runtime/doc/eval.txt | 40 +++++++++++++++++++++++--- src/nvim/eval.lua | 18 ++++++------ src/nvim/testdir/test_clientserver.vim | 12 ++++---- src/nvim/testdir/test_functions.vim | 6 ++-- src/nvim/testdir/test_reltime.vim | 6 ++-- src/nvim/testdir/test_rename.vim | 2 +- 6 files changed, 58 insertions(+), 26 deletions(-) diff --git a/runtime/doc/eval.txt b/runtime/doc/eval.txt index 1878913311..8305cbf0d5 100644 --- a/runtime/doc/eval.txt +++ b/runtime/doc/eval.txt @@ -2505,7 +2505,7 @@ keys({dict}) List keys in {dict} len({expr}) Number the length of {expr} libcall({lib}, {func}, {arg}) String call {func} in library {lib} with {arg} libcallnr({lib}, {func}, {arg}) Number idem, but return a Number -line({expr}) Number line nr of cursor, last line or mark +line({expr} [, {winid}]) Number line nr of cursor, last line or mark line2byte({lnum}) Number byte count of line {lnum} lispindent({lnum}) Number Lisp indent for line {lnum} list2str({list} [, {utf8}]) String turn numbers in {list} into a String @@ -5780,7 +5780,9 @@ hasmapto({what} [, {mode} [, {abbr}]]) *hasmapto()* If no matching mapping is found FALSE is returned. The following characters are recognized in {mode}: n Normal mode - v Visual mode + v Visual and Select mode + x Visual mode + s Select mode o Operator-pending mode i Insert mode l Language-Argument ("r", "f", "t", etc.) @@ -6483,8 +6485,8 @@ libcallnr({libname}, {funcname}, {argument}) the argument to the called function: > GetValue()->libcallnr("libc.so", "printf") < - *line()* -line({expr}) The result is a Number, which is the line number of the file +line({expr} [, {winid}]) *line()* + The result is a Number, which is the line number of the file position given with {expr}. The {expr} argument is a string. The accepted positions are: . the cursor position @@ -6503,8 +6505,11 @@ line({expr}) The result is a Number, which is the line number of the file then applies to another buffer. To get the column number use |col()|. To get both use |getpos()|. + With the optional {winid} argument the values are obtained for + that window instead of the current window. Examples: > line(".") line number of the cursor + line(".", winid) idem, in window "winid" line("'t") line number of mark t line("'" . marker) line number of mark marker < @@ -7669,6 +7674,9 @@ range({expr} [, {max} [, {stride}]]) *range()* range(2, -2, -1) " [2, 1, 0, -1, -2] range(0) " [] range(2, 0) " error! +< + Can also be used as a |method|: > + GetExpr()->range() < *readdir()* readdir({directory} [, {expr}]) @@ -7696,6 +7704,9 @@ readdir({directory} [, {expr}]) \ {x : s:tree(a:dir . '/' . x)} : x})} endfunction echo s:tree(".") +< + Can also be used as a |method|: > + GetDirName()->readdir() < *readfile()* readfile({fname} [, {type} [, {max}]]) @@ -7730,6 +7741,9 @@ readfile({fname} [, {type} [, {max}]]) the result is an empty list. Also see |writefile()|. + Can also be used as a |method|: > + GetFileName()->readfile() + reg_executing() *reg_executing()* Returns the single letter name of the register being executed. Returns an empty string when no register is being executed. @@ -7757,6 +7771,9 @@ reltime([{start} [, {end}]]) *reltime()* The {start} and {end} arguments must be values returned by reltime(). + Can also be used as a |method|: > + GetStart()->reltime() +< Note: |localtime()| returns the current (non-relative) time. reltimefloat({time}) *reltimefloat()* @@ -7770,6 +7787,9 @@ reltimefloat({time}) *reltimefloat()* Also see |profiling|. If there is an error an empty string is returned + Can also be used as a |method|: > + reltime(start)->reltimefloat() + reltimestr({time}) *reltimestr()* Return a String that represents the time value of {time}. This is the number of seconds, a dot and the number of @@ -7784,6 +7804,9 @@ reltimestr({time}) *reltimestr()* < Also see |profiling|. If there is an error an empty string is returned + Can also be used as a |method|: > + reltime(start)->reltimestr() +< *remote_expr()* *E449* remote_expr({server}, {string} [, {idvar} [, {timeout}]]) Send the {string} to {server}. The string is sent as an @@ -7916,6 +7939,9 @@ rename({from}, {to}) *rename()* NOTE: If {to} exists it is overwritten without warning. This function is not available in the |sandbox|. + Can also be used as a |method|: > + GetOldName()->rename(newname) + repeat({expr}, {count}) *repeat()* Repeat {expr} {count} times and return the concatenated result. Example: > @@ -7942,6 +7968,9 @@ resolve({filename}) *resolve()* *E655* current directory (provided the result is still a relative path name) and also keeps a trailing path separator. + Can also be used as a |method|: > + GetName()->resolve() +< *reverse()* reverse({object}) Reverse the order of items in {object} in-place. @@ -7996,6 +8025,9 @@ rubyeval({expr}) *rubyeval()* Other objects are represented as strings resulted from their "Object#to_s" method. + Can also be used as a |method|: > + GetRubyExpr()->rubyeval() + screenattr({row}, {col}) *screenattr()* Like |screenchar()|, but return the attribute. This is a rather arbitrary number that can only be used to compare to the diff --git a/src/nvim/eval.lua b/src/nvim/eval.lua index 741b8547fe..70aa2bb1f8 100644 --- a/src/nvim/eval.lua +++ b/src/nvim/eval.lua @@ -271,25 +271,25 @@ return { pyeval={args=1, base=1}, pyxeval={args=1, base=1}, perleval={args=1, base=1}, - range={args={1, 3}}, - readdir={args={1, 2}}, - readfile={args={1, 3}}, + range={args={1, 3}, base=1}, + readdir={args={1, 2}, base=1}, + readfile={args={1, 3}, base=1}, reg_executing={}, reg_recording={}, - reltime={args={0, 2}}, - reltimefloat={args=1}, - reltimestr={args=1}, + reltime={args={0, 2}, base=1}, + reltimefloat={args=1, base=1}, + reltimestr={args=1, base=1}, remove={args={2, 3}, base=1}, - rename={args=2}, + rename={args=2, base=1}, ['repeat']={args=2, base=1}, - resolve={args=1}, + resolve={args=1, base=1}, reverse={args=1, base=1}, round={args=1, base=1, func="float_op_wrapper", data="&round"}, rpcnotify={args=varargs(2)}, rpcrequest={args=varargs(2)}, rpcstart={args={1, 2}}, rpcstop={args=1}, - rubyeval={args=1}, + rubyeval={args=1, base=1}, screenattr={args=2}, screenchar={args=2}, screenchars={args=2}, diff --git a/src/nvim/testdir/test_clientserver.vim b/src/nvim/testdir/test_clientserver.vim index 53704bd094..f3db472b03 100644 --- a/src/nvim/testdir/test_clientserver.vim +++ b/src/nvim/testdir/test_clientserver.vim @@ -34,7 +34,7 @@ func Test_client_server() " When using valgrind it takes much longer. call WaitForAssert({-> assert_match(name, serverlist())}) - call remote_foreground(name) + eval name->remote_foreground() call remote_send(name, ":let testvar = 'yes'\") call WaitFor('remote_expr("' . name . '", "exists(\"testvar\") ? testvar : \"\"", "", 1) == "yes"') @@ -53,7 +53,7 @@ func Test_client_server() endif " Wait for the server to be up and answering requests. sleep 100m - call WaitForAssert({-> assert_true(remote_expr(name, "v:version", "", 1) != "")}) + call WaitForAssert({-> assert_true(name->remote_expr("v:version", "", 1) != "")}) call remote_send(name, ":let testvar = 'maybe'\") call WaitForAssert({-> assert_equal('maybe', remote_expr(name, "testvar", "", 2))}) @@ -72,7 +72,7 @@ func Test_client_server() " Expression evaluated locally. if v:servername == '' - call remote_startserver('MYSELF') + eval 'MYSELF'->remote_startserver() " May get MYSELF1 when running the test again. call assert_match('MYSELF', v:servername) endif @@ -80,11 +80,11 @@ func Test_client_server() call assert_equal('myself', remote_expr(v:servername, 'testvar')) call remote_send(name, ":call server2client(expand(''), 'got it')\", 'g:myserverid') - call assert_equal('got it', remote_read(g:myserverid, 2)) + call assert_equal('got it', g:myserverid->remote_read(2)) call remote_send(name, ":call server2client(expand(''), 'another')\", 'g:myserverid') let peek_result = 'nothing' - let r = remote_peek(g:myserverid, 'peek_result') + let r = g:myserverid->remote_peek('peek_result') " unpredictable whether the result is already available. if r > 0 call assert_equal('another', peek_result) @@ -98,7 +98,7 @@ func Test_client_server() call assert_equal('another', g:peek_result) call assert_equal('another', remote_read(g:myserverid, 2)) - call remote_send(name, ":qa!\") + eval name->remote_send(":qa!\") try call WaitForAssert({-> assert_equal("dead", job_status(job))}) finally diff --git a/src/nvim/testdir/test_functions.vim b/src/nvim/testdir/test_functions.vim index c08b43736b..a80c3e9bf2 100644 --- a/src/nvim/testdir/test_functions.vim +++ b/src/nvim/testdir/test_functions.vim @@ -295,7 +295,7 @@ func Test_resolve_unix() call delete('Xlink') silent !ln -s -f Xlink2/ Xlink1 - call assert_equal('Xlink2', resolve('Xlink1')) + call assert_equal('Xlink2', 'Xlink1'->resolve()) call assert_equal('Xlink2/', resolve('Xlink1/')) call delete('Xlink1') @@ -1306,7 +1306,7 @@ func Test_func_range_with_edit() " is invalid in that buffer. call writefile(['just one line'], 'Xfuncrange2') new - call setline(1, range(10)) + call setline(1, 10->range()) write Xfuncrange1 call assert_fails('5,8call EditAnotherFile()', 'E16:') @@ -1578,7 +1578,7 @@ func Test_readdir() call assert_equal(['bar.txt', 'dir', 'foo.txt'], sort(files)) " Only results containing "f" - let files = readdir('Xdir', { x -> stridx(x, 'f') !=- 1 }) + let files = 'Xdir'->readdir({ x -> stridx(x, 'f') !=- 1 }) call assert_equal(['foo.txt'], sort(files)) " Only .txt files diff --git a/src/nvim/testdir/test_reltime.vim b/src/nvim/testdir/test_reltime.vim index 2ef2fbba23..37b9e783c6 100644 --- a/src/nvim/testdir/test_reltime.vim +++ b/src/nvim/testdir/test_reltime.vim @@ -8,11 +8,11 @@ func Test_reltime() let now = reltime() sleep 10m let later = reltime() - let elapsed = reltime(now) + let elapsed = now->reltime() call assert_true(reltimestr(elapsed) =~ '0\.0') - call assert_true(reltimestr(elapsed) != '0.0') + call assert_true(elapsed->reltimestr() != '0.0') call assert_true(reltimefloat(elapsed) < 0.1) - call assert_true(reltimefloat(elapsed) > 0.0) + call assert_true(elapsed->reltimefloat() > 0.0) let same = reltime(now, now) call assert_equal('0.000', split(reltimestr(same))[0][:4]) diff --git a/src/nvim/testdir/test_rename.vim b/src/nvim/testdir/test_rename.vim index 2311caf790..3887fcfabf 100644 --- a/src/nvim/testdir/test_rename.vim +++ b/src/nvim/testdir/test_rename.vim @@ -25,7 +25,7 @@ func Test_rename_file_ignore_case() set fileignorecase call writefile(['foo'], 'Xrename') - call assert_equal(0, rename('Xrename', 'XRENAME')) + call assert_equal(0, 'Xrename'->rename('XRENAME')) call assert_equal(['foo'], readfile('XRENAME'))