1" Test commands that are not compiled in a :def function
2
3source check.vim
4source vim9.vim
5source term_util.vim
6source view_util.vim
7
8def Test_vim9cmd()
9  var lines =<< trim END
10    vim9cmd var x = 123
11    let s:y = 'yes'
12    vim9c assert_equal(123, x)
13    vim9cm assert_equal('yes', y)
14  END
15  CheckScriptSuccess(lines)
16enddef
17
18def Test_edit_wildcards()
19  var filename = 'Xtest'
20  edit `=filename`
21  assert_equal('Xtest', bufname())
22
23  var filenr = 123
24  edit Xtest`=filenr`
25  assert_equal('Xtest123', bufname())
26
27  filenr = 77
28  edit `=filename``=filenr`
29  assert_equal('Xtest77', bufname())
30
31  edit X`=filename`xx`=filenr`yy
32  assert_equal('XXtestxx77yy', bufname())
33
34  CheckDefFailure(['edit `=xxx`'], 'E1001:')
35  CheckDefFailure(['edit `="foo"'], 'E1083:')
36enddef
37
38def Test_expand_alternate_file()
39  var lines =<< trim END
40    edit Xfileone
41    var bone = bufnr()
42    edit Xfiletwo
43    var btwo = bufnr()
44    edit Xfilethree
45    var bthree = bufnr()
46
47    edit #
48    assert_equal(bthree, bufnr())
49    edit %%
50    assert_equal(btwo, bufnr())
51    edit %% # comment
52    assert_equal(bthree, bufnr())
53    edit %%yy
54    assert_equal('Xfiletwoyy', bufname())
55
56    exe "edit %%" .. bone
57    assert_equal(bone, bufnr())
58    exe "edit %%" .. btwo .. "xx"
59    assert_equal('Xfiletwoxx', bufname())
60
61    next Xfileone Xfiletwo Xfilethree
62    assert_equal('Xfileone', argv(0))
63    assert_equal('Xfiletwo', argv(1))
64    assert_equal('Xfilethree', argv(2))
65    next %%%zz
66    assert_equal('Xfileone', argv(0))
67    assert_equal('Xfiletwo', argv(1))
68    assert_equal('Xfilethreezz', argv(2))
69
70    v:oldfiles = ['Xonefile', 'Xtwofile']
71    edit %%<1
72    assert_equal('Xonefile', bufname())
73    edit %%<2
74    assert_equal('Xtwofile', bufname())
75    assert_fails('edit %%<3', 'E684:')
76
77    edit Xfileone.vim
78    edit Xfiletwo
79    edit %%:r
80    assert_equal('Xfileone', bufname())
81
82    assert_false(bufexists('altfoo'))
83    edit altfoo
84    edit bar
85    assert_true(bufexists('altfoo'))
86    assert_true(buflisted('altfoo'))
87    bdel %%
88    assert_true(bufexists('altfoo'))
89    assert_false(buflisted('altfoo'))
90    bwipe! altfoo
91    bwipe! bar
92  END
93  CheckDefAndScriptSuccess(lines)
94enddef
95
96def Test_global_backtick_expansion()
97  new
98  setline(1, 'xx')
99  var name = 'foobar'
100  g/^xx/s/.*/`=name`
101  assert_equal('foobar', getline(1))
102  bwipe!
103enddef
104
105def Test_folddo_backtick_expansion()
106  new
107  var name = 'xxx'
108  folddoopen edit `=name`
109  assert_equal('xxx', bufname())
110  bwipe!
111
112  new
113  setline(1, ['one', 'two'])
114  set nomodified
115  :1,2fold
116  foldclose
117  folddoclose edit `=name`
118  assert_equal('xxx', bufname())
119  bwipe!
120enddef
121
122def Test_hardcopy_wildcards()
123  CheckUnix
124  CheckFeature postscript
125
126  var outfile = 'print'
127  hardcopy > X`=outfile`.ps
128  assert_true(filereadable('Xprint.ps'))
129
130  delete('Xprint.ps')
131enddef
132
133def Test_syn_include_wildcards()
134  writefile(['syn keyword Found found'], 'Xthemine.vim')
135  var save_rtp = &rtp
136  &rtp = '.'
137
138  var fname = 'mine'
139  syn include @Group Xthe`=fname`.vim
140  assert_match('Found.* contained found', execute('syn list Found'))
141
142  &rtp = save_rtp
143  delete('Xthemine.vim')
144enddef
145
146def Test_echo_linebreak()
147  var lines =<< trim END
148      vim9script
149      redir @a
150      echo 'one'
151            .. 'two'
152      redir END
153      assert_equal("\nonetwo", @a)
154  END
155  CheckScriptSuccess(lines)
156
157  lines =<< trim END
158      vim9script
159      redir @a
160      echo 11 +
161            77
162            - 22
163      redir END
164      assert_equal("\n66", @a)
165  END
166  CheckScriptSuccess(lines)
167enddef
168
169def Test_condition_types()
170  var lines =<< trim END
171      if 'text'
172      endif
173  END
174  CheckDefAndScriptFailure(lines, 'E1135:', 1)
175
176  lines =<< trim END
177      if [1]
178      endif
179  END
180  CheckDefFailure(lines, 'E1012:', 1)
181  CheckScriptFailure(['vim9script'] + lines, 'E745:', 2)
182
183  lines =<< trim END
184      g:cond = 'text'
185      if g:cond
186      endif
187  END
188  CheckDefExecAndScriptFailure(lines, 'E1135:', 2)
189
190  lines =<< trim END
191      g:cond = 0
192      if g:cond
193      elseif 'text'
194      endif
195  END
196  CheckDefFailure(lines, 'E1012:', 3)
197  CheckScriptFailure(['vim9script'] + lines, 'E1135:', 4)
198
199  lines =<< trim END
200      if g:cond
201      elseif [1]
202      endif
203  END
204  CheckDefFailure(lines, 'E1012:', 2)
205  CheckScriptFailure(['vim9script'] + lines, 'E745:', 3)
206
207  lines =<< trim END
208      g:cond = 'text'
209      if 0
210      elseif g:cond
211      endif
212  END
213  CheckDefExecAndScriptFailure(lines, 'E1135:', 3)
214
215  lines =<< trim END
216      while 'text'
217      endwhile
218  END
219  CheckDefFailure(lines, 'E1012:', 1)
220  CheckScriptFailure(['vim9script'] + lines, 'E1135:', 2)
221
222  lines =<< trim END
223      while [1]
224      endwhile
225  END
226  CheckDefFailure(lines, 'E1012:', 1)
227  CheckScriptFailure(['vim9script'] + lines, 'E745:', 2)
228
229  lines =<< trim END
230      g:cond = 'text'
231      while g:cond
232      endwhile
233  END
234  CheckDefExecAndScriptFailure(lines, 'E1135:', 2)
235enddef
236
237def Test_if_linebreak()
238  var lines =<< trim END
239      vim9script
240      if 1 &&
241            true
242            || 1
243        g:res = 42
244      endif
245      assert_equal(42, g:res)
246  END
247  CheckScriptSuccess(lines)
248  unlet g:res
249
250  lines =<< trim END
251      vim9script
252      if 1 &&
253            0
254        g:res = 0
255      elseif 0 ||
256              0
257              || 1
258        g:res = 12
259      endif
260      assert_equal(12, g:res)
261  END
262  CheckScriptSuccess(lines)
263  unlet g:res
264enddef
265
266def Test_while_linebreak()
267  var lines =<< trim END
268      vim9script
269      var nr = 0
270      while nr <
271              10 + 3
272            nr = nr
273                  + 4
274      endwhile
275      assert_equal(16, nr)
276  END
277  CheckScriptSuccess(lines)
278
279  lines =<< trim END
280      vim9script
281      var nr = 0
282      while nr
283            <
284              10
285              +
286              3
287            nr = nr
288                  +
289                  4
290      endwhile
291      assert_equal(16, nr)
292  END
293  CheckScriptSuccess(lines)
294enddef
295
296def Test_for_linebreak()
297  var lines =<< trim END
298      vim9script
299      var nr = 0
300      for x
301            in
302              [1, 2, 3, 4]
303          nr = nr + x
304      endfor
305      assert_equal(10, nr)
306  END
307  CheckScriptSuccess(lines)
308
309  lines =<< trim END
310      vim9script
311      var nr = 0
312      for x
313            in
314              [1, 2,
315                  3, 4
316                  ]
317          nr = nr
318                 +
319                  x
320      endfor
321      assert_equal(10, nr)
322  END
323  CheckScriptSuccess(lines)
324enddef
325
326def MethodAfterLinebreak(arg: string)
327  arg
328    ->setline(1)
329enddef
330
331def Test_method_call_linebreak()
332  var lines =<< trim END
333      vim9script
334      var res = []
335      func RetArg(
336            arg
337            )
338            let s:res = a:arg
339      endfunc
340      [1,
341          2,
342          3]->RetArg()
343      assert_equal([1, 2, 3], res)
344  END
345  CheckScriptSuccess(lines)
346
347  lines =<< trim END
348      new
349      var name = [1, 2]
350      name
351          ->copy()
352          ->setline(1)
353      assert_equal(['1', '2'], getline(1, 2))
354      bwipe!
355  END
356  CheckDefAndScriptSuccess(lines)
357
358  lines =<< trim END
359      new
360      def Foo(): string
361        return 'the text'
362      enddef
363      def Bar(F: func): string
364        return F()
365      enddef
366      def Test()
367        Foo  ->Bar()
368             ->setline(1)
369      enddef
370      Test()
371      assert_equal('the text', getline(1))
372      bwipe!
373  END
374  CheckDefAndScriptSuccess(lines)
375
376  lines =<< trim END
377      new
378      g:shortlist
379          ->copy()
380          ->setline(1)
381      assert_equal(['1', '2'], getline(1, 2))
382      bwipe!
383  END
384  g:shortlist = [1, 2]
385  CheckDefAndScriptSuccess(lines)
386  unlet g:shortlist
387
388  new
389  MethodAfterLinebreak('foobar')
390  assert_equal('foobar', getline(1))
391  bwipe!
392
393  lines =<< trim END
394      vim9script
395      def Foo(): string
396          return '# some text'
397      enddef
398
399      def Bar(F: func): string
400          return F()
401      enddef
402
403      Foo->Bar()
404         ->setline(1)
405  END
406  CheckScriptSuccess(lines)
407  assert_equal('# some text', getline(1))
408  bwipe!
409enddef
410
411def Test_method_call_whitespace()
412  var lines =<< trim END
413    new
414    var yank = 'text'
415    yank->setline(1)
416    yank  ->setline(2)
417    yank->  setline(3)
418    yank  ->  setline(4)
419    assert_equal(['text', 'text', 'text', 'text'], getline(1, 4))
420    bwipe!
421  END
422  CheckDefAndScriptSuccess(lines)
423enddef
424
425def Test_method_and_user_command()
426  var lines =<< trim END
427      vim9script
428      def Cmd()
429        g:didFunc = 1
430      enddef
431      command Cmd g:didCmd = 1
432      Cmd
433      assert_equal(1, g:didCmd)
434      Cmd()
435      assert_equal(1, g:didFunc)
436      unlet g:didFunc
437      unlet g:didCmd
438
439      def InDefFunc()
440        Cmd
441        assert_equal(1, g:didCmd)
442        Cmd()
443        assert_equal(1, g:didFunc)
444        unlet g:didFunc
445        unlet g:didCmd
446      enddef
447      InDefFunc()
448  END
449  CheckScriptSuccess(lines)
450enddef
451
452def Test_skipped_expr_linebreak()
453  if 0
454    var x = []
455               ->map(() => 0)
456  endif
457enddef
458
459def Test_dict_member()
460   var test: dict<list<number>> = {data: [3, 1, 2]}
461   test.data->sort()
462   assert_equal({data: [1, 2, 3]}, test)
463   test.data
464      ->reverse()
465   assert_equal({data: [3, 2, 1]}, test)
466
467  var lines =<< trim END
468      vim9script
469      var test: dict<list<number>> = {data: [3, 1, 2]}
470      test.data->sort()
471      assert_equal({data: [1, 2, 3]}, test)
472  END
473  CheckScriptSuccess(lines)
474enddef
475
476def Test_bar_after_command()
477  def RedrawAndEcho()
478    var x = 'did redraw'
479    redraw | echo x
480  enddef
481  RedrawAndEcho()
482  assert_match('did redraw', Screenline(&lines))
483
484  def CallAndEcho()
485    var x = 'did redraw'
486    reg_executing() | echo x
487  enddef
488  CallAndEcho()
489  assert_match('did redraw', Screenline(&lines))
490
491  if has('unix')
492    # bar in filter write command does not start new command
493    def WriteToShell()
494      new
495      setline(1, 'some text')
496      w !cat | cat > Xoutfile
497      bwipe!
498    enddef
499    WriteToShell()
500    assert_equal(['some text'], readfile('Xoutfile'))
501    delete('Xoutfile')
502
503    # bar in filter read command does not start new command
504    def ReadFromShell()
505      new
506      r! echo hello there | cat > Xoutfile
507      r !echo again | cat >> Xoutfile
508      bwipe!
509    enddef
510    ReadFromShell()
511    assert_equal(['hello there', 'again'], readfile('Xoutfile'))
512    delete('Xoutfile')
513  endif
514enddef
515
516def Test_filter_is_not_modifier()
517  var tags = [{a: 1, b: 2}, {x: 3, y: 4}]
518  filter(tags, ( _, v) => has_key(v, 'x') ? 1 : 0 )
519  assert_equal([{x: 3, y: 4}], tags)
520enddef
521
522def Test_command_modifier_filter()
523  var lines =<< trim END
524    final expected = "\nType Name Content\n  c  \"c   piyo"
525    @a = 'hoge'
526    @b = 'fuga'
527    @c = 'piyo'
528
529    assert_equal(execute('filter /piyo/ registers abc'), expected)
530  END
531  CheckDefAndScriptSuccess(lines)
532enddef
533
534def Test_win_command_modifiers()
535  assert_equal(1, winnr('$'))
536
537  set splitright
538  vsplit
539  assert_equal(2, winnr())
540  close
541  aboveleft vsplit
542  assert_equal(1, winnr())
543  close
544  set splitright&
545
546  vsplit
547  assert_equal(1, winnr())
548  close
549  belowright vsplit
550  assert_equal(2, winnr())
551  close
552  rightbelow vsplit
553  assert_equal(2, winnr())
554  close
555
556  if has('browse')
557    browse set
558    assert_equal('option-window', expand('%'))
559    close
560  endif
561
562  vsplit
563  botright split
564  assert_equal(3, winnr())
565  assert_equal(&columns, winwidth(0))
566  close
567  close
568
569  vsplit
570  topleft split
571  assert_equal(1, winnr())
572  assert_equal(&columns, winwidth(0))
573  close
574  close
575
576  gettabinfo()->len()->assert_equal(1)
577  tab split
578  gettabinfo()->len()->assert_equal(2)
579  tabclose
580
581  vertical new
582  assert_inrange(&columns / 2 - 2, &columns / 2 + 1, winwidth(0))
583  close
584enddef
585
586func Test_command_modifier_confirm()
587  CheckNotGui
588  CheckRunVimInTerminal
589
590  " Test for saving all the modified buffers
591  let lines =<< trim END
592    call setline(1, 'changed')
593    def Getout()
594      confirm write Xfile
595    enddef
596  END
597  call writefile(lines, 'Xconfirmscript')
598  call writefile(['empty'], 'Xfile')
599  let buf = RunVimInTerminal('-S Xconfirmscript', {'rows': 8})
600  call term_sendkeys(buf, ":call Getout()\n")
601  call WaitForAssert({-> assert_match('(Y)es, \[N\]o: ', term_getline(buf, 8))}, 1000)
602  call term_sendkeys(buf, "y")
603  call WaitForAssert({-> assert_match('(Y)es, \[N\]o: ', term_getline(buf, 8))}, 1000)
604  call term_sendkeys(buf, "\<CR>")
605  call TermWait(buf)
606  call StopVimInTerminal(buf)
607
608  call assert_equal(['changed'], readfile('Xfile'))
609  call delete('Xfile')
610  call delete('.Xfile.swp')  " in case Vim was killed
611  call delete('Xconfirmscript')
612endfunc
613
614def Test_command_modifiers_keep()
615  if has('unix')
616    def DoTest(addRflag: bool, keepMarks: bool, hasMarks: bool)
617      new
618      setline(1, ['one', 'two', 'three'])
619      normal 1Gma
620      normal 2Gmb
621      normal 3Gmc
622      if addRflag
623        set cpo+=R
624      else
625        set cpo-=R
626      endif
627      if keepMarks
628        keepmarks :%!cat
629      else
630        :%!cat
631      endif
632      if hasMarks
633        assert_equal(1, line("'a"))
634        assert_equal(2, line("'b"))
635        assert_equal(3, line("'c"))
636      else
637        assert_equal(0, line("'a"))
638        assert_equal(0, line("'b"))
639        assert_equal(0, line("'c"))
640      endif
641      quit!
642    enddef
643    DoTest(false, false, true)
644    DoTest(true, false, false)
645    DoTest(false, true, true)
646    DoTest(true, true, true)
647    set cpo&vim
648
649    new
650    setline(1, ['one', 'two', 'three', 'four'])
651    assert_equal(4, line("$"))
652    normal 1Gma
653    normal 2Gmb
654    normal 3Gmc
655    lockmarks :1,2!wc
656    # line is deleted, marks don't move
657    assert_equal(3, line("$"))
658    assert_equal('four', getline(3))
659    assert_equal(1, line("'a"))
660    assert_equal(2, line("'b"))
661    assert_equal(3, line("'c"))
662    quit!
663  endif
664
665  edit Xone
666  edit Xtwo
667  assert_equal('Xone', expand('#'))
668  keepalt edit Xthree
669  assert_equal('Xone', expand('#'))
670
671  normal /a*b*
672  assert_equal('a*b*', histget("search"))
673  keeppatterns normal /c*d*
674  assert_equal('a*b*', histget("search"))
675
676  new
677  setline(1, range(10))
678  :10
679  normal gg
680  assert_equal(10, getpos("''")[1])
681  keepjumps normal 5G
682  assert_equal(10, getpos("''")[1])
683  quit!
684enddef
685
686def Test_bar_line_continuation()
687  var lines =<< trim END
688      au BufNewFile Xfile g:readFile = 1
689          | g:readExtra = 2
690      g:readFile = 0
691      g:readExtra = 0
692      edit Xfile
693      assert_equal(1, g:readFile)
694      assert_equal(2, g:readExtra)
695      bwipe!
696      au! BufNewFile
697
698      au BufNewFile Xfile g:readFile = 1
699          | g:readExtra = 2
700          | g:readMore = 3
701      g:readFile = 0
702      g:readExtra = 0
703      g:readMore = 0
704      edit Xfile
705      assert_equal(1, g:readFile)
706      assert_equal(2, g:readExtra)
707      assert_equal(3, g:readMore)
708      bwipe!
709      au! BufNewFile
710      unlet g:readFile
711      unlet g:readExtra
712      unlet g:readMore
713  END
714  CheckDefAndScriptSuccess(lines)
715enddef
716
717def Test_command_modifier_other()
718  new Xsomefile
719  setline(1, 'changed')
720  var buf = bufnr()
721  hide edit Xotherfile
722  var info = getbufinfo(buf)
723  assert_equal(1, info[0].hidden)
724  assert_equal(1, info[0].changed)
725  edit Xsomefile
726  bwipe!
727
728  au BufNewFile Xfile g:readFile = 1
729  g:readFile = 0
730  edit Xfile
731  assert_equal(1, g:readFile)
732  bwipe!
733  g:readFile = 0
734  noautocmd edit Xfile
735  assert_equal(0, g:readFile)
736  au! BufNewFile
737  unlet g:readFile
738
739  noswapfile edit XnoSwap
740  assert_equal(false, &l:swapfile)
741  bwipe!
742
743  var caught = false
744  try
745    sandbox !ls
746  catch /E48:/
747    caught = true
748  endtry
749  assert_true(caught)
750
751  :8verbose g:verbose_now = &verbose
752  assert_equal(8, g:verbose_now)
753  unlet g:verbose_now
754enddef
755
756def EchoHere()
757  echomsg 'here'
758enddef
759def EchoThere()
760  unsilent echomsg 'there'
761enddef
762
763def Test_modifier_silent_unsilent()
764  echomsg 'last one'
765  silent echomsg "text"
766  assert_equal("\nlast one", execute(':1messages'))
767
768  silent! echoerr "error"
769
770  echomsg 'last one'
771  silent EchoHere()
772  assert_equal("\nlast one", execute(':1messages'))
773
774  silent EchoThere()
775  assert_equal("\nthere", execute(':1messages'))
776
777  try
778    silent eval [][0]
779  catch
780    echomsg "caught"
781  endtry
782  assert_equal("\ncaught", execute(':1messages'))
783enddef
784
785def Test_range_after_command_modifier()
786  CheckScriptFailure(['vim9script', 'silent keepjump 1d _'], 'E1050: Colon required before a range: 1d _', 2)
787  new
788  setline(1, 'xxx')
789  CheckScriptSuccess(['vim9script', 'silent keepjump :1d _'])
790  assert_equal('', getline(1))
791  bwipe!
792enddef
793
794def Test_silent_pattern()
795  new
796  silent! :/pat/put _
797  bwipe!
798enddef
799
800def Test_useless_command_modifier()
801  g:maybe = true
802  var lines =<< trim END
803      if g:maybe
804      silent endif
805  END
806  CheckDefAndScriptFailure(lines, 'E1176:', 2)
807
808  lines =<< trim END
809      for i in [0]
810      silent endfor
811  END
812  CheckDefAndScriptFailure(lines, 'E1176:', 2)
813
814  lines =<< trim END
815      while g:maybe
816      silent endwhile
817  END
818  CheckDefAndScriptFailure(lines, 'E1176:', 2)
819
820  lines =<< trim END
821      silent try
822      finally
823      endtry
824  END
825  CheckDefAndScriptFailure(lines, 'E1176:', 1)
826
827  lines =<< trim END
828      try
829      silent catch
830      endtry
831  END
832  CheckDefAndScriptFailure(lines, 'E1176:', 2)
833
834  lines =<< trim END
835      try
836      silent finally
837      endtry
838  END
839  CheckDefAndScriptFailure(lines, 'E1176:', 2)
840
841  lines =<< trim END
842      try
843      finally
844      silent endtry
845  END
846  CheckDefAndScriptFailure(lines, 'E1176:', 3)
847enddef
848
849def Test_eval_command()
850  var from = 3
851  var to = 5
852  g:val = 111
853  def Increment(nrs: list<number>)
854    for nr in nrs
855      g:val += nr
856    endfor
857  enddef
858  eval range(from, to)
859        ->Increment()
860  assert_equal(111 + 3 + 4 + 5, g:val)
861  unlet g:val
862
863  var lines =<< trim END
864    vim9script
865    g:caught = 'no'
866    try
867      eval 123 || 0
868    catch
869      g:caught = 'yes'
870    endtry
871    assert_equal('yes', g:caught)
872    unlet g:caught
873  END
874  CheckScriptSuccess(lines)
875enddef
876
877def Test_map_command()
878  var lines =<< trim END
879      nnoremap <F3> :echo 'hit F3 #'<CR>
880      assert_equal(":echo 'hit F3 #'<CR>", maparg("<F3>", "n"))
881  END
882  CheckDefSuccess(lines)
883  CheckScriptSuccess(['vim9script'] + lines)
884enddef
885
886def Test_normal_command()
887  new
888  setline(1, 'doesnotexist')
889  var caught = 0
890  try
891    exe "norm! \<C-]>"
892  catch /E433/
893    caught = 2
894  endtry
895  assert_equal(2, caught)
896
897  try
898    exe "norm! 3\<C-]>"
899  catch /E433/
900    caught = 3
901  endtry
902  assert_equal(3, caught)
903  bwipe!
904enddef
905
906def Test_put_command()
907  new
908  @p = 'ppp'
909  put p
910  assert_equal('ppp', getline(2))
911
912  put ='below'
913  assert_equal('below', getline(3))
914  put! ='above'
915  assert_equal('above', getline(3))
916  assert_equal('below', getline(4))
917
918  :2put =['a', 'b', 'c']
919  assert_equal(['ppp', 'a', 'b', 'c', 'above'], getline(2, 6))
920
921  # compute range at runtime
922  setline(1, range(1, 8))
923  @a = 'aaa'
924  :$-2put a
925  assert_equal('aaa', getline(7))
926
927  setline(1, range(1, 8))
928  :2
929  :+2put! a
930  assert_equal('aaa', getline(4))
931
932  []->mapnew(() => 0)
933  :$put ='end'
934  assert_equal('end', getline('$'))
935
936  bwipe!
937
938  CheckDefFailure(['put =xxx'], 'E1001:')
939enddef
940
941def Test_put_with_linebreak()
942  new
943  var lines =<< trim END
944    vim9script
945    pu =split('abc', '\zs')
946            ->join()
947  END
948  CheckScriptSuccess(lines)
949  getline(2)->assert_equal('a b c')
950  bwipe!
951enddef
952
953def Test_command_star_range()
954  new
955  setline(1, ['xxx foo xxx', 'xxx bar xxx', 'xxx foo xx bar'])
956  setpos("'<", [0, 1, 0, 0])
957  setpos("'>", [0, 3, 0, 0])
958  :*s/\(foo\|bar\)/baz/g
959  getline(1, 3)->assert_equal(['xxx baz xxx', 'xxx baz xxx', 'xxx baz xx baz'])
960
961  bwipe!
962enddef
963
964def Test_f_args()
965  var lines =<< trim END
966    vim9script
967
968    func SaveCmdArgs(...)
969      let g:args = a:000
970    endfunc
971
972    command -nargs=* TestFArgs call SaveCmdArgs(<f-args>)
973
974    TestFArgs
975    assert_equal([], g:args)
976
977    TestFArgs one two three
978    assert_equal(['one', 'two', 'three'], g:args)
979  END
980  CheckScriptSuccess(lines)
981enddef
982
983def Test_user_command_comment()
984  command -nargs=1 Comd echom <q-args>
985
986  var lines =<< trim END
987      vim9script
988      Comd # comment
989  END
990  CheckScriptSuccess(lines)
991
992  lines =<< trim END
993      vim9script
994      Comd# comment
995  END
996  CheckScriptFailure(lines, 'E1144:')
997  delcommand Comd
998
999  lines =<< trim END
1000      vim9script
1001      command Foo echo 'Foo'
1002      Foo3Bar
1003  END
1004  CheckScriptFailure(lines, 'E1144: Command "Foo" is not followed by white space: Foo3Bar')
1005
1006  delcommand Foo
1007enddef
1008
1009def Test_star_command()
1010  var lines =<< trim END
1011    vim9script
1012    @s = 'g:success = 8'
1013    set cpo+=*
1014    exe '*s'
1015    assert_equal(8, g:success)
1016    unlet g:success
1017    set cpo-=*
1018    assert_fails("exe '*s'", 'E1050:')
1019  END
1020  CheckScriptSuccess(lines)
1021enddef
1022
1023def Test_cmd_argument_without_colon()
1024  new Xfile
1025  setline(1, ['a', 'b', 'c', 'd'])
1026  write
1027  edit +3 %
1028  assert_equal(3, getcurpos()[1])
1029  edit +/a %
1030  assert_equal(1, getcurpos()[1])
1031  bwipe
1032  delete('Xfile')
1033enddef
1034
1035def Test_ambiguous_user_cmd()
1036  command Cmd1 eval 0
1037  command Cmd2 eval 0
1038  var lines =<< trim END
1039      Cmd
1040  END
1041  CheckDefAndScriptFailure(lines, 'E464:', 1)
1042  delcommand Cmd1
1043  delcommand Cmd2
1044enddef
1045
1046def Test_command_not_recognized()
1047  var lines =<< trim END
1048    d.key = 'asdf'
1049  END
1050  CheckDefFailure(lines, 'E1146:', 1)
1051
1052  lines =<< trim END
1053    d['key'] = 'asdf'
1054  END
1055  CheckDefFailure(lines, 'E1146:', 1)
1056enddef
1057
1058def Test_magic_not_used()
1059  new
1060  for cmd in ['set magic', 'set nomagic']
1061    exe cmd
1062    setline(1, 'aaa')
1063    s/.../bbb/
1064    assert_equal('bbb', getline(1))
1065  endfor
1066
1067  set magic
1068  setline(1, 'aaa')
1069  assert_fails('s/.\M../bbb/', 'E486:')
1070  assert_fails('snomagic/.../bbb/', 'E486:')
1071  assert_equal('aaa', getline(1))
1072
1073  bwipe!
1074enddef
1075
1076def Test_gdefault_not_used()
1077  new
1078  for cmd in ['set gdefault', 'set nogdefault']
1079    exe cmd
1080    setline(1, 'aaa')
1081    s/./b/
1082    assert_equal('baa', getline(1))
1083  endfor
1084
1085  set nogdefault
1086  bwipe!
1087enddef
1088
1089def g:SomeComplFunc(findstart: number, base: string): any
1090  if findstart
1091    return 0
1092  else
1093    return ['aaa', 'bbb']
1094  endif
1095enddef
1096
1097def Test_insert_complete()
1098  # this was running into an error with the matchparen hack
1099  new
1100  set completefunc=SomeComplFunc
1101  feedkeys("i\<c-x>\<c-u>\<Esc>", 'ntx')
1102  assert_equal('aaa', getline(1))
1103
1104  set completefunc=
1105  bwipe!
1106enddef
1107
1108def Test_wincmd()
1109  split
1110  var id1 = win_getid()
1111  if true
1112    try | wincmd w | catch | endtry
1113  endif
1114  assert_notequal(id1, win_getid())
1115  close
1116
1117  split
1118  var id = win_getid()
1119  split
1120  :2wincmd o
1121  assert_equal(id, win_getid())
1122  only
1123
1124  split
1125  split
1126  assert_equal(3, winnr('$'))
1127  :2wincmd c
1128  assert_equal(2, winnr('$'))
1129  only
1130
1131  split
1132  split
1133  assert_equal(3, winnr('$'))
1134  :2wincmd q
1135  assert_equal(2, winnr('$'))
1136  only
1137enddef
1138
1139def Test_windo_missing_endif()
1140  var lines =<< trim END
1141      windo if 1
1142  END
1143  CheckDefExecFailure(lines, 'E171:', 1)
1144enddef
1145
1146let s:theList = [1, 2, 3]
1147
1148def Test_lockvar()
1149  s:theList[1] = 22
1150  assert_equal([1, 22, 3], s:theList)
1151  lockvar s:theList
1152  assert_fails('theList[1] = 77', 'E741:')
1153  unlockvar s:theList
1154  s:theList[1] = 44
1155  assert_equal([1, 44, 3], s:theList)
1156
1157  var lines =<< trim END
1158      vim9script
1159      var theList = [1, 2, 3]
1160      def SetList()
1161        theList[1] = 22
1162        assert_equal([1, 22, 3], theList)
1163        lockvar theList
1164        theList[1] = 77
1165      enddef
1166      SetList()
1167  END
1168  CheckScriptFailure(lines, 'E1119', 4)
1169
1170  lines =<< trim END
1171      var theList = [1, 2, 3]
1172      lockvar theList
1173  END
1174  CheckDefFailure(lines, 'E1178', 2)
1175
1176  lines =<< trim END
1177      var theList = [1, 2, 3]
1178      unlockvar theList
1179  END
1180  CheckDefFailure(lines, 'E1178', 2)
1181enddef
1182
1183def Test_substitute_expr()
1184  var to = 'repl'
1185  new
1186  setline(1, 'one from two')
1187  s/from/\=to
1188  assert_equal('one repl two', getline(1))
1189
1190  setline(1, 'one from two')
1191  s/from/\=to .. '_x'
1192  assert_equal('one repl_x two', getline(1))
1193
1194  setline(1, 'one from two from three')
1195  var also = 'also'
1196  s/from/\=to .. '_' .. also/g#e
1197  assert_equal('one repl_also two repl_also three', getline(1))
1198
1199  setline(1, 'abc abc abc')
1200  for choice in [true, false]
1201    :1s/abc/\=choice ? 'yes' : 'no'/
1202  endfor
1203  assert_equal('yes no abc', getline(1))
1204
1205  bwipe!
1206
1207  CheckDefFailure(['s/from/\="x")/'], 'E488:')
1208  CheckDefFailure(['s/from/\="x"/9'], 'E488:')
1209
1210  # When calling a function the right instruction list needs to be restored.
1211  g:cond = true
1212  var lines =<< trim END
1213      vim9script
1214      def Foo()
1215          Bar([])
1216      enddef
1217      def Bar(l: list<number>)
1218        if g:cond
1219          s/^/\=Rep()/
1220          for n in l[:]
1221          endfor
1222        endif
1223      enddef
1224      def Rep(): string
1225          return 'rep'
1226      enddef
1227      new
1228      Foo()
1229      assert_equal('rep', getline(1))
1230      bwipe!
1231  END
1232  CheckScriptSuccess(lines)
1233  unlet g:cond
1234enddef
1235
1236def Test_redir_to_var()
1237  var result: string
1238  redir => result
1239    echo 'something'
1240  redir END
1241  assert_equal("\nsomething", result)
1242
1243  redir =>> result
1244    echo 'more'
1245  redir END
1246  assert_equal("\nsomething\nmore", result)
1247
1248  var d: dict<string>
1249  redir => d.redir
1250    echo 'dict'
1251  redir END
1252  assert_equal({redir: "\ndict"}, d)
1253
1254  var l = ['a', 'b', 'c']
1255  redir => l[1]
1256    echo 'list'
1257  redir END
1258  assert_equal(['a', "\nlist", 'c'], l)
1259
1260  var dl = {l: ['x']}
1261  redir => dl.l[0]
1262    echo 'dict-list'
1263  redir END
1264  assert_equal({l: ["\ndict-list"]}, dl)
1265
1266  redir =>> d.redir
1267    echo 'more'
1268  redir END
1269  assert_equal({redir: "\ndict\nmore"}, d)
1270
1271  var lines =<< trim END
1272    redir => notexist
1273  END
1274  CheckDefFailure(lines, 'E1089:')
1275
1276  lines =<< trim END
1277    var ls = 'asdf'
1278    redir => ls[1]
1279    redir END
1280  END
1281  CheckDefFailure(lines, 'E1141:')
1282enddef
1283
1284
1285" vim: ts=8 sw=2 sts=2 expandtab tw=80 fdm=marker
1286