1" Test for user functions. 2" Also test an <expr> mapping calling a function. 3" Also test that a builtin function cannot be replaced. 4" Also test for regression when calling arbitrary expression. 5 6func Table(title, ...) 7 let ret = a:title 8 let idx = 1 9 while idx <= a:0 10 exe "let ret = ret . a:" . idx 11 let idx = idx + 1 12 endwhile 13 return ret 14endfunc 15 16func Compute(n1, n2, divname) 17 if a:n2 == 0 18 return "fail" 19 endif 20 exe "let g:" . a:divname . " = ". a:n1 / a:n2 21 return "ok" 22endfunc 23 24func Expr1() 25 silent! normal! v 26 return "111" 27endfunc 28 29func Expr2() 30 call search('XX', 'b') 31 return "222" 32endfunc 33 34func ListItem() 35 let g:counter += 1 36 return g:counter . '. ' 37endfunc 38 39func ListReset() 40 let g:counter = 0 41 return '' 42endfunc 43 44func FuncWithRef(a) 45 unlet g:FuncRef 46 return a:a 47endfunc 48 49func Test_user_func() 50 let g:FuncRef = function("FuncWithRef") 51 let g:counter = 0 52 inoremap <expr> ( ListItem() 53 inoremap <expr> [ ListReset() 54 imap <expr> + Expr1() 55 imap <expr> * Expr2() 56 let g:retval = "nop" 57 58 call assert_equal('xxx4asdf', Table("xxx", 4, "asdf")) 59 call assert_equal('fail', Compute(45, 0, "retval")) 60 call assert_equal('nop', g:retval) 61 call assert_equal('ok', Compute(45, 5, "retval")) 62 call assert_equal(9, g:retval) 63 call assert_equal(333, g:FuncRef(333)) 64 65 let g:retval = "nop" 66 call assert_equal('xxx4asdf', "xxx"->Table(4, "asdf")) 67 call assert_equal('fail', 45->Compute(0, "retval")) 68 call assert_equal('nop', g:retval) 69 call assert_equal('ok', 45->Compute(5, "retval")) 70 call assert_equal(9, g:retval) 71 " call assert_equal(333, 333->g:FuncRef()) 72 73 enew 74 75 normal oXX+-XX 76 call assert_equal('XX111-XX', getline('.')) 77 normal o---*--- 78 call assert_equal('---222---', getline('.')) 79 normal o(one 80 call assert_equal('1. one', getline('.')) 81 normal o(two 82 call assert_equal('2. two', getline('.')) 83 normal o[(one again 84 call assert_equal('1. one again', getline('.')) 85 86 call assert_equal(3, max([1, 2, 3])) 87 call assert_fails("call extend(g:, {'max': function('min')})", 'E704') 88 call assert_equal(3, max([1, 2, 3])) 89 90 " Try to overwrite an user defined function with a function reference 91 call assert_fails("let Expr1 = function('min')", 'E705:') 92 93 " Regression: the first line below used to throw ?E110: Missing ')'? 94 " Second is here just to prove that this line is correct when not skipping 95 " rhs of &&. 96 call assert_equal(0, (0 && (function('tr'))(1, 2, 3))) 97 call assert_equal(1, (1 && (function('tr'))(1, 2, 3))) 98 99 delfunc Table 100 delfunc Compute 101 delfunc Expr1 102 delfunc Expr2 103 delfunc ListItem 104 delfunc ListReset 105 unlet g:retval g:counter 106 enew! 107endfunc 108 109func Log(val, base = 10) 110 return log(a:val) / log(a:base) 111endfunc 112 113func Args(mandatory, optional = v:null, ...) 114 return deepcopy(a:) 115endfunc 116 117func Args2(a = 1, b = 2, c = 3) 118 return deepcopy(a:) 119endfunc 120 121func MakeBadFunc() 122 func s:fcn(a, b=1, c) 123 endfunc 124endfunc 125 126func Test_default_arg() 127 if has('float') 128 call assert_equal(1.0, Log(10)) 129 call assert_equal(log(10), Log(10, exp(1))) 130 call assert_fails("call Log(1,2,3)", 'E118') 131 endif 132 133 let res = Args(1) 134 call assert_equal(res.mandatory, 1) 135 call assert_equal(res.optional, v:null) 136 call assert_equal(res['0'], 0) 137 138 let res = Args(1,2) 139 call assert_equal(res.mandatory, 1) 140 call assert_equal(res.optional, 2) 141 call assert_equal(res['0'], 0) 142 143 let res = Args(1,2,3) 144 call assert_equal(res.mandatory, 1) 145 call assert_equal(res.optional, 2) 146 call assert_equal(res['0'], 1) 147 148 call assert_fails("call MakeBadFunc()", 'E989') 149 call assert_fails("fu F(a=1 ,) | endf", 'E475') 150 151 let d = Args2(7, v:none, 9) 152 call assert_equal([7, 2, 9], [d.a, d.b, d.c]) 153 154 call assert_equal("\n" 155 \ .. " function Args2(a = 1, b = 2, c = 3)\n" 156 \ .. "1 return deepcopy(a:)\n" 157 \ .. " endfunction", 158 \ execute('func Args2')) 159endfunc 160 161func s:addFoo(lead) 162 return a:lead .. 'foo' 163endfunc 164 165func Test_user_method() 166 eval 'bar'->s:addFoo()->assert_equal('barfoo') 167endfunc 168 169func Test_failed_call_in_try() 170 try | call UnknownFunc() | catch | endtry 171endfunc 172