blob: 08855005c5b7f9b22cc5b02ce131d6cbe3b7fb29 [file] [log] [blame]
Bram Moolenaard7ece102016-02-02 23:23:02 +01001" Test for channel functions.
2scriptencoding utf-8
3
Bram Moolenaare2469252016-02-04 10:54:34 +01004if !has('channel')
5 finish
6endif
7
8" This test requires the Python command to run the test server.
Bram Moolenaara8343c12016-02-04 22:09:48 +01009" This most likely only works on Unix and Windows.
Bram Moolenaara0f9cd12016-02-03 20:13:24 +010010if has('unix')
Bram Moolenaar835dc632016-02-07 14:27:38 +010011 " We also need the job feature or the pkill command to make sure the server
12 " can be stopped.
13 if !(executable('python') && (has('job') || executable('pkill')))
Bram Moolenaara0f9cd12016-02-03 20:13:24 +010014 finish
15 endif
Bram Moolenaarb6a77372016-02-15 22:55:28 +010016 let s:python = 'python'
Bram Moolenaara8343c12016-02-04 22:09:48 +010017elseif has('win32')
Bram Moolenaarb6a77372016-02-15 22:55:28 +010018 " Use Python Launcher for Windows (py.exe) if available.
19 if executable('py.exe')
20 let s:python = 'py.exe'
21 elseif executable('python.exe')
22 let s:python = 'python.exe'
23 else
Bram Moolenaara0f9cd12016-02-03 20:13:24 +010024 finish
25 endif
26else
Bram Moolenaard6a8d482016-02-10 20:32:20 +010027 " Can't run this test.
Bram Moolenaard7ece102016-02-02 23:23:02 +010028 finish
29endif
30
Bram Moolenaare74e8e72016-02-16 22:01:30 +010031let s:chopt = {}
Bram Moolenaar3b05b132016-02-03 23:25:07 +010032
Bram Moolenaard6a8d482016-02-10 20:32:20 +010033" Run "testfunc" after sarting the server and stop the server afterwards.
Bram Moolenaar81661fb2016-02-18 22:23:34 +010034func s:run_server(testfunc, ...)
Bram Moolenaarfcb1e3d2016-02-03 21:32:46 +010035 " The Python program writes the port number in Xportnr.
36 call delete("Xportnr")
37
Bram Moolenaar81661fb2016-02-18 22:23:34 +010038 if a:0 == 1
39 let arg = ' ' . a:1
40 else
41 let arg = ''
42 endif
43 let cmd = s:python . " test_channel.py" . arg
44
Bram Moolenaard6a8d482016-02-10 20:32:20 +010045 try
46 if has('job')
Bram Moolenaar65edff82016-02-21 16:40:11 +010047 let s:job = job_start(cmd, {"stoponexit": "hup"})
48 call job_setoptions(s:job, {"stoponexit": "kill"})
Bram Moolenaard6a8d482016-02-10 20:32:20 +010049 elseif has('win32')
Bram Moolenaar81661fb2016-02-18 22:23:34 +010050 exe 'silent !start cmd /c start "test_channel" ' . cmd
Bram Moolenaard6a8d482016-02-10 20:32:20 +010051 else
Bram Moolenaar81661fb2016-02-18 22:23:34 +010052 exe 'silent !' . cmd . '&'
Bram Moolenaard7ece102016-02-02 23:23:02 +010053 endif
Bram Moolenaard7ece102016-02-02 23:23:02 +010054
Bram Moolenaard6a8d482016-02-10 20:32:20 +010055 " Wait for up to 2 seconds for the port number to be there.
56 let cnt = 20
57 let l = []
58 while cnt > 0
59 try
60 let l = readfile("Xportnr")
61 catch
62 endtry
63 if len(l) >= 1
64 break
65 endif
66 sleep 100m
67 let cnt -= 1
68 endwhile
69 call delete("Xportnr")
70
71 if len(l) == 0
72 " Can't make the connection, give up.
73 call assert_false(1, "Can't start test_channel.py")
74 return -1
75 endif
76 let port = l[0]
77
78 call call(function(a:testfunc), [port])
79 catch
80 call assert_false(1, "Caught exception: " . v:exception)
81 finally
Bram Moolenaara0f9cd12016-02-03 20:13:24 +010082 call s:kill_server()
Bram Moolenaard6a8d482016-02-10 20:32:20 +010083 endtry
Bram Moolenaarfcb1e3d2016-02-03 21:32:46 +010084endfunc
85
86func s:kill_server()
Bram Moolenaar835dc632016-02-07 14:27:38 +010087 if has('job')
Bram Moolenaard6a8d482016-02-10 20:32:20 +010088 if exists('s:job')
89 call job_stop(s:job)
90 unlet s:job
91 endif
Bram Moolenaar835dc632016-02-07 14:27:38 +010092 elseif has('win32')
Bram Moolenaarb6a77372016-02-15 22:55:28 +010093 call system('taskkill /IM ' . s:python . ' /T /F /FI "WINDOWTITLE eq test_channel"')
Bram Moolenaarfcb1e3d2016-02-03 21:32:46 +010094 else
Bram Moolenaar608a8912016-02-03 22:39:51 +010095 call system("pkill -f test_channel.py")
Bram Moolenaarfcb1e3d2016-02-03 21:32:46 +010096 endif
97endfunc
98
Bram Moolenaara07fec92016-02-05 21:04:08 +010099let s:responseMsg = ''
100func s:RequestHandler(handle, msg)
101 let s:responseHandle = a:handle
102 let s:responseMsg = a:msg
103endfunc
104
Bram Moolenaard6a8d482016-02-10 20:32:20 +0100105func s:communicate(port)
106 let handle = ch_open('localhost:' . a:port, s:chopt)
Bram Moolenaar77073442016-02-13 23:23:53 +0100107 if ch_status(handle) == "fail"
Bram Moolenaard6a8d482016-02-10 20:32:20 +0100108 call assert_false(1, "Can't open channel")
Bram Moolenaarfcb1e3d2016-02-03 21:32:46 +0100109 return
110 endif
Bram Moolenaar839fd112016-03-06 21:34:03 +0100111 if has('job')
112 " check that no job is handled correctly
113 call assert_equal('no process', string(ch_getjob(handle)))
114 endif
Bram Moolenaard7ece102016-02-02 23:23:02 +0100115
116 " Simple string request and reply.
Bram Moolenaar8b1862a2016-02-27 19:21:24 +0100117 call assert_equal('got it', ch_evalexpr(handle, 'hello!'))
Bram Moolenaard7ece102016-02-02 23:23:02 +0100118
119 " Request that triggers sending two ex commands. These will usually be
120 " handled before getting the response, but it's not guaranteed, thus wait a
121 " tiny bit for the commands to get executed.
Bram Moolenaar8b1862a2016-02-27 19:21:24 +0100122 call assert_equal('ok', ch_evalexpr(handle, 'make change'))
Bram Moolenaard7ece102016-02-02 23:23:02 +0100123 sleep 10m
124 call assert_equal('added1', getline(line('$') - 1))
125 call assert_equal('added2', getline('$'))
126
Bram Moolenaarda94fdf2016-03-03 18:09:10 +0100127 call assert_equal('ok', ch_evalexpr(handle, 'do normal', {'timeout': 100}))
Bram Moolenaarf4160862016-02-05 23:09:12 +0100128 sleep 10m
129 call assert_equal('added more', getline('$'))
130
Bram Moolenaara07fec92016-02-05 21:04:08 +0100131 " Send a request with a specific handler.
Bram Moolenaar910b8aa2016-02-16 21:03:07 +0100132 call ch_sendexpr(handle, 'hello!', {'callback': 's:RequestHandler'})
Bram Moolenaara07fec92016-02-05 21:04:08 +0100133 sleep 10m
Bram Moolenaar77073442016-02-13 23:23:53 +0100134 if !exists('s:responseHandle')
135 call assert_false(1, 's:responseHandle was not set')
136 else
137 call assert_equal(handle, s:responseHandle)
Bram Moolenaar9186a272016-02-23 19:34:01 +0100138 unlet s:responseHandle
Bram Moolenaar77073442016-02-13 23:23:53 +0100139 endif
Bram Moolenaara07fec92016-02-05 21:04:08 +0100140 call assert_equal('got it', s:responseMsg)
141
Bram Moolenaarb6a4fee2016-02-11 20:48:34 +0100142 let s:responseMsg = ''
Bram Moolenaar910b8aa2016-02-16 21:03:07 +0100143 call ch_sendexpr(handle, 'hello!', {'callback': function('s:RequestHandler')})
Bram Moolenaarb6a4fee2016-02-11 20:48:34 +0100144 sleep 10m
Bram Moolenaar77073442016-02-13 23:23:53 +0100145 if !exists('s:responseHandle')
146 call assert_false(1, 's:responseHandle was not set')
147 else
148 call assert_equal(handle, s:responseHandle)
Bram Moolenaar9186a272016-02-23 19:34:01 +0100149 unlet s:responseHandle
Bram Moolenaar77073442016-02-13 23:23:53 +0100150 endif
Bram Moolenaarb6a4fee2016-02-11 20:48:34 +0100151 call assert_equal('got it', s:responseMsg)
152
Bram Moolenaar38fd4bb2016-03-06 16:38:28 +0100153 " Collect garbage, tests that our handle isn't collected.
154 call garbagecollect()
155
Bram Moolenaar40ea1da2016-02-19 22:33:35 +0100156 " check setting options (without testing the effect)
157 call ch_setoptions(handle, {'callback': 's:NotUsed'})
Bram Moolenaar1f6ef662016-02-19 22:59:44 +0100158 call ch_setoptions(handle, {'timeout': 1111})
Bram Moolenaarb6b52522016-02-20 23:30:07 +0100159 call ch_setoptions(handle, {'mode': 'json'})
Bram Moolenaar40ea1da2016-02-19 22:33:35 +0100160 call assert_fails("call ch_setoptions(handle, {'waittime': 111})", "E475")
Bram Moolenaar0ba75a92016-02-19 23:21:26 +0100161 call ch_setoptions(handle, {'callback': ''})
Bram Moolenaar40ea1da2016-02-19 22:33:35 +0100162
Bram Moolenaarfcb1e3d2016-02-03 21:32:46 +0100163 " Send an eval request that works.
Bram Moolenaar8b1862a2016-02-27 19:21:24 +0100164 call assert_equal('ok', ch_evalexpr(handle, 'eval-works'))
Bram Moolenaara02b3212016-02-04 21:03:33 +0100165 sleep 10m
Bram Moolenaar8b1862a2016-02-27 19:21:24 +0100166 call assert_equal([-1, 'foo123'], ch_evalexpr(handle, 'eval-result'))
Bram Moolenaarfcb1e3d2016-02-03 21:32:46 +0100167
168 " Send an eval request that fails.
Bram Moolenaar8b1862a2016-02-27 19:21:24 +0100169 call assert_equal('ok', ch_evalexpr(handle, 'eval-fails'))
Bram Moolenaara02b3212016-02-04 21:03:33 +0100170 sleep 10m
Bram Moolenaar8b1862a2016-02-27 19:21:24 +0100171 call assert_equal([-2, 'ERROR'], ch_evalexpr(handle, 'eval-result'))
Bram Moolenaarfcb1e3d2016-02-03 21:32:46 +0100172
Bram Moolenaar55fab432016-02-07 16:53:13 +0100173 " Send an eval request that works but can't be encoded.
Bram Moolenaar8b1862a2016-02-27 19:21:24 +0100174 call assert_equal('ok', ch_evalexpr(handle, 'eval-error'))
Bram Moolenaar55fab432016-02-07 16:53:13 +0100175 sleep 10m
Bram Moolenaar8b1862a2016-02-27 19:21:24 +0100176 call assert_equal([-3, 'ERROR'], ch_evalexpr(handle, 'eval-result'))
Bram Moolenaar55fab432016-02-07 16:53:13 +0100177
Bram Moolenaar66624ff2016-02-03 23:59:43 +0100178 " Send a bad eval request. There will be no response.
Bram Moolenaar8b1862a2016-02-27 19:21:24 +0100179 call assert_equal('ok', ch_evalexpr(handle, 'eval-bad'))
Bram Moolenaara02b3212016-02-04 21:03:33 +0100180 sleep 10m
Bram Moolenaar8b1862a2016-02-27 19:21:24 +0100181 call assert_equal([-3, 'ERROR'], ch_evalexpr(handle, 'eval-result'))
Bram Moolenaar66624ff2016-02-03 23:59:43 +0100182
Bram Moolenaarf4160862016-02-05 23:09:12 +0100183 " Send an expr request
Bram Moolenaar8b1862a2016-02-27 19:21:24 +0100184 call assert_equal('ok', ch_evalexpr(handle, 'an expr'))
Bram Moolenaarf4160862016-02-05 23:09:12 +0100185 sleep 10m
186 call assert_equal('one', getline(line('$') - 2))
187 call assert_equal('two', getline(line('$') - 1))
188 call assert_equal('three', getline('$'))
189
190 " Request a redraw, we don't check for the effect.
Bram Moolenaar8b1862a2016-02-27 19:21:24 +0100191 call assert_equal('ok', ch_evalexpr(handle, 'redraw'))
192 call assert_equal('ok', ch_evalexpr(handle, 'redraw!'))
Bram Moolenaarf4160862016-02-05 23:09:12 +0100193
Bram Moolenaar8b1862a2016-02-27 19:21:24 +0100194 call assert_equal('ok', ch_evalexpr(handle, 'empty-request'))
Bram Moolenaarf4160862016-02-05 23:09:12 +0100195
Bram Moolenaar6f3a5442016-02-20 19:56:13 +0100196 " Reading while there is nothing available.
Bram Moolenaar9186a272016-02-23 19:34:01 +0100197 call assert_equal(v:none, ch_read(handle, {'timeout': 0}))
198 let start = reltime()
199 call assert_equal(v:none, ch_read(handle, {'timeout': 333}))
200 let elapsed = reltime(start)
201 call assert_true(reltimefloat(elapsed) > 0.3)
202 call assert_true(reltimefloat(elapsed) < 0.6)
Bram Moolenaar6f3a5442016-02-20 19:56:13 +0100203
204 " Send without waiting for a response, then wait for a response.
Bram Moolenaar8b1862a2016-02-27 19:21:24 +0100205 call ch_sendexpr(handle, 'wait a bit')
Bram Moolenaar6f3a5442016-02-20 19:56:13 +0100206 let resp = ch_read(handle)
207 call assert_equal(type([]), type(resp))
208 call assert_equal(type(11), type(resp[0]))
209 call assert_equal('waited', resp[1])
210
Bram Moolenaard7ece102016-02-02 23:23:02 +0100211 " make the server quit, can't check if this works, should not hang.
Bram Moolenaar8b1862a2016-02-27 19:21:24 +0100212 call ch_sendexpr(handle, '!quit!')
Bram Moolenaard6a8d482016-02-10 20:32:20 +0100213endfunc
Bram Moolenaard7ece102016-02-02 23:23:02 +0100214
Bram Moolenaard6a8d482016-02-10 20:32:20 +0100215func Test_communicate()
Bram Moolenaar81661fb2016-02-18 22:23:34 +0100216 call ch_log('Test_communicate()')
Bram Moolenaard6a8d482016-02-10 20:32:20 +0100217 call s:run_server('s:communicate')
Bram Moolenaard7ece102016-02-02 23:23:02 +0100218endfunc
Bram Moolenaarfcb1e3d2016-02-03 21:32:46 +0100219
Bram Moolenaar3b05b132016-02-03 23:25:07 +0100220" Test that we can open two channels.
Bram Moolenaard6a8d482016-02-10 20:32:20 +0100221func s:two_channels(port)
Bram Moolenaar39b21272016-02-10 23:28:21 +0100222 let handle = ch_open('localhost:' . a:port, s:chopt)
Bram Moolenaar77073442016-02-13 23:23:53 +0100223 if ch_status(handle) == "fail"
Bram Moolenaard6a8d482016-02-10 20:32:20 +0100224 call assert_false(1, "Can't open channel")
Bram Moolenaar3b05b132016-02-03 23:25:07 +0100225 return
226 endif
Bram Moolenaard6a8d482016-02-10 20:32:20 +0100227
Bram Moolenaar8b1862a2016-02-27 19:21:24 +0100228 call assert_equal('got it', ch_evalexpr(handle, 'hello!'))
Bram Moolenaar3b05b132016-02-03 23:25:07 +0100229
Bram Moolenaard6a8d482016-02-10 20:32:20 +0100230 let newhandle = ch_open('localhost:' . a:port, s:chopt)
Bram Moolenaar77073442016-02-13 23:23:53 +0100231 if ch_status(newhandle) == "fail"
Bram Moolenaard6a8d482016-02-10 20:32:20 +0100232 call assert_false(1, "Can't open second channel")
233 return
234 endif
Bram Moolenaar8b1862a2016-02-27 19:21:24 +0100235 call assert_equal('got it', ch_evalexpr(newhandle, 'hello!'))
236 call assert_equal('got it', ch_evalexpr(handle, 'hello!'))
Bram Moolenaar3b05b132016-02-03 23:25:07 +0100237
238 call ch_close(handle)
Bram Moolenaar8b1862a2016-02-27 19:21:24 +0100239 call assert_equal('got it', ch_evalexpr(newhandle, 'hello!'))
Bram Moolenaar3b05b132016-02-03 23:25:07 +0100240
Bram Moolenaard6a8d482016-02-10 20:32:20 +0100241 call ch_close(newhandle)
242endfunc
243
244func Test_two_channels()
Bram Moolenaar81661fb2016-02-18 22:23:34 +0100245 call ch_log('Test_two_channels()')
Bram Moolenaarbfa1ffc2016-02-13 18:40:30 +0100246 call s:run_server('s:two_channels')
Bram Moolenaar3b05b132016-02-03 23:25:07 +0100247endfunc
248
Bram Moolenaarfcb1e3d2016-02-03 21:32:46 +0100249" Test that a server crash is handled gracefully.
Bram Moolenaard6a8d482016-02-10 20:32:20 +0100250func s:server_crash(port)
251 let handle = ch_open('localhost:' . a:port, s:chopt)
Bram Moolenaar77073442016-02-13 23:23:53 +0100252 if ch_status(handle) == "fail"
Bram Moolenaard6a8d482016-02-10 20:32:20 +0100253 call assert_false(1, "Can't open channel")
Bram Moolenaarfcb1e3d2016-02-03 21:32:46 +0100254 return
255 endif
Bram Moolenaard6a8d482016-02-10 20:32:20 +0100256
Bram Moolenaar8b1862a2016-02-27 19:21:24 +0100257 call ch_evalexpr(handle, '!crash!')
Bram Moolenaarfcb1e3d2016-02-03 21:32:46 +0100258
Bram Moolenaarfcb1e3d2016-02-03 21:32:46 +0100259 sleep 10m
Bram Moolenaard6a8d482016-02-10 20:32:20 +0100260endfunc
261
262func Test_server_crash()
Bram Moolenaar81661fb2016-02-18 22:23:34 +0100263 call ch_log('Test_server_crash()')
Bram Moolenaarbfa1ffc2016-02-13 18:40:30 +0100264 call s:run_server('s:server_crash')
Bram Moolenaarfcb1e3d2016-02-03 21:32:46 +0100265endfunc
Bram Moolenaar7a84dbe2016-02-07 21:29:00 +0100266
Bram Moolenaard6547fc2016-03-03 19:35:02 +0100267"""""""""
268
Bram Moolenaarf6157282016-02-10 21:07:14 +0100269let s:reply = ""
270func s:Handler(chan, msg)
Bram Moolenaarb6a4fee2016-02-11 20:48:34 +0100271 unlet s:reply
Bram Moolenaarf6157282016-02-10 21:07:14 +0100272 let s:reply = a:msg
273endfunc
274
275func s:channel_handler(port)
Bram Moolenaarb6a4fee2016-02-11 20:48:34 +0100276 let handle = ch_open('localhost:' . a:port, s:chopt)
Bram Moolenaar77073442016-02-13 23:23:53 +0100277 if ch_status(handle) == "fail"
Bram Moolenaarf6157282016-02-10 21:07:14 +0100278 call assert_false(1, "Can't open channel")
279 return
280 endif
281
282 " Test that it works while waiting on a numbered message.
Bram Moolenaar8b1862a2016-02-27 19:21:24 +0100283 call assert_equal('ok', ch_evalexpr(handle, 'call me'))
Bram Moolenaarf6157282016-02-10 21:07:14 +0100284 sleep 10m
285 call assert_equal('we called you', s:reply)
286
287 " Test that it works while not waiting on a numbered message.
Bram Moolenaar8b1862a2016-02-27 19:21:24 +0100288 call ch_sendexpr(handle, 'call me again')
Bram Moolenaarf6157282016-02-10 21:07:14 +0100289 sleep 10m
290 call assert_equal('we did call you', s:reply)
291endfunc
292
293func Test_channel_handler()
Bram Moolenaar81661fb2016-02-18 22:23:34 +0100294 call ch_log('Test_channel_handler()')
Bram Moolenaarb6a4fee2016-02-11 20:48:34 +0100295 let s:chopt.callback = 's:Handler'
Bram Moolenaarf6157282016-02-10 21:07:14 +0100296 call s:run_server('s:channel_handler')
Bram Moolenaarb6a4fee2016-02-11 20:48:34 +0100297 let s:chopt.callback = function('s:Handler')
298 call s:run_server('s:channel_handler')
299 unlet s:chopt.callback
Bram Moolenaarf6157282016-02-10 21:07:14 +0100300endfunc
301
Bram Moolenaard6547fc2016-03-03 19:35:02 +0100302"""""""""
303
Bram Moolenaar5983ad02016-03-05 20:54:36 +0100304let s:ch_reply = ''
305func s:ChHandler(chan, msg)
306 unlet s:ch_reply
307 let s:ch_reply = a:msg
308endfunc
309
310let s:zero_reply = ''
311func s:OneHandler(chan, msg)
312 unlet s:zero_reply
313 let s:zero_reply = a:msg
314endfunc
315
316func s:channel_zero(port)
317 let handle = ch_open('localhost:' . a:port, s:chopt)
318 if ch_status(handle) == "fail"
319 call assert_false(1, "Can't open channel")
320 return
321 endif
322
323 " Check that eval works.
324 call assert_equal('got it', ch_evalexpr(handle, 'hello!'))
325
326 " Check that eval works if a zero id message is sent back.
327 let s:ch_reply = ''
328 call assert_equal('sent zero', ch_evalexpr(handle, 'send zero'))
329 sleep 10m
330 if s:has_handler
331 call assert_equal('zero index', s:ch_reply)
332 else
333 call assert_equal('', s:ch_reply)
334 endif
335
336 " Check that handler works if a zero id message is sent back.
337 let s:ch_reply = ''
338 let s:zero_reply = ''
339 call ch_sendexpr(handle, 'send zero', {'callback': 's:OneHandler'})
340 " Somehow the second message takes a bit of time.
341 for i in range(50)
342 if s:zero_reply == 'sent zero'
343 break
344 endif
345 sleep 10m
346 endfor
347 if s:has_handler
348 call assert_equal('zero index', s:ch_reply)
349 else
350 call assert_equal('', s:ch_reply)
351 endif
352 call assert_equal('sent zero', s:zero_reply)
353endfunc
354
355func Test_zero_reply()
356 call ch_log('Test_zero_reply()')
357 " Run with channel handler
358 let s:has_handler = 1
359 let s:chopt.callback = 's:ChHandler'
360 call s:run_server('s:channel_zero')
361 unlet s:chopt.callback
362
363 " Run without channel handler
364 let s:has_handler = 0
365 call s:run_server('s:channel_zero')
366endfunc
367
368"""""""""
369
Bram Moolenaard6547fc2016-03-03 19:35:02 +0100370let s:reply1 = ""
371func s:HandleRaw1(chan, msg)
372 unlet s:reply1
373 let s:reply1 = a:msg
374endfunc
375
376let s:reply2 = ""
377func s:HandleRaw2(chan, msg)
378 unlet s:reply2
379 let s:reply2 = a:msg
380endfunc
381
382let s:reply3 = ""
383func s:HandleRaw3(chan, msg)
384 unlet s:reply3
385 let s:reply3 = a:msg
386endfunc
387
388func s:raw_one_time_callback(port)
389 let handle = ch_open('localhost:' . a:port, s:chopt)
390 if ch_status(handle) == "fail"
391 call assert_false(1, "Can't open channel")
392 return
393 endif
394 call ch_setoptions(handle, {'mode': 'raw'})
395
396 " The message are sent raw, we do our own JSON strings here.
397 call ch_sendraw(handle, "[1, \"hello!\"]", {'callback': 's:HandleRaw1'})
Bram Moolenaar304563c2016-03-07 22:26:28 +0100398 for i in range(50)
399 sleep 10m
400 if s:reply1 != ''
401 break
402 endif
403 endfor
Bram Moolenaard6547fc2016-03-03 19:35:02 +0100404 call assert_equal("[1, \"got it\"]", s:reply1)
405 call ch_sendraw(handle, "[2, \"echo something\"]", {'callback': 's:HandleRaw2'})
406 call ch_sendraw(handle, "[3, \"wait a bit\"]", {'callback': 's:HandleRaw3'})
Bram Moolenaar304563c2016-03-07 22:26:28 +0100407 for i in range(50)
408 sleep 10m
409 if s:reply2 != ''
410 break
411 endif
412 endfor
Bram Moolenaard6547fc2016-03-03 19:35:02 +0100413 call assert_equal("[2, \"something\"]", s:reply2)
414 " wait for up to 500 msec for the 200 msec delayed reply
415 for i in range(50)
416 sleep 10m
417 if s:reply3 != ''
418 break
419 endif
420 endfor
421 call assert_equal("[3, \"waited\"]", s:reply3)
422endfunc
423
424func Test_raw_one_time_callback()
Bram Moolenaard6547fc2016-03-03 19:35:02 +0100425 call ch_log('Test_raw_one_time_callback()')
426 call s:run_server('s:raw_one_time_callback')
Bram Moolenaard6547fc2016-03-03 19:35:02 +0100427endfunc
428
429"""""""""
430
Bram Moolenaar7a84dbe2016-02-07 21:29:00 +0100431" Test that trying to connect to a non-existing port fails quickly.
432func Test_connect_waittime()
Bram Moolenaar81661fb2016-02-18 22:23:34 +0100433 call ch_log('Test_connect_waittime()')
Bram Moolenaar7a84dbe2016-02-07 21:29:00 +0100434 let start = reltime()
Bram Moolenaara4833262016-02-09 23:33:25 +0100435 let handle = ch_open('localhost:9876', s:chopt)
Bram Moolenaar81661fb2016-02-18 22:23:34 +0100436 if ch_status(handle) != "fail"
Bram Moolenaar7a84dbe2016-02-07 21:29:00 +0100437 " Oops, port does exists.
438 call ch_close(handle)
439 else
440 let elapsed = reltime(start)
Bram Moolenaar74f5e652016-02-07 21:44:49 +0100441 call assert_true(reltimefloat(elapsed) < 1.0)
Bram Moolenaar7a84dbe2016-02-07 21:29:00 +0100442 endif
443
Bram Moolenaar08298fa2016-02-21 13:01:53 +0100444 " We intend to use a socket that doesn't exist and wait for half a second
445 " before giving up. If the socket does exist it can fail in various ways.
446 " Check for "Connection reset by peer" to avoid flakyness.
Bram Moolenaar7a84dbe2016-02-07 21:29:00 +0100447 let start = reltime()
Bram Moolenaar08298fa2016-02-21 13:01:53 +0100448 try
449 let handle = ch_open('localhost:9867', {'waittime': 500})
450 if ch_status(handle) != "fail"
451 " Oops, port does exists.
452 call ch_close(handle)
453 else
454 " Failed connection should wait about 500 msec.
455 let elapsed = reltime(start)
456 call assert_true(reltimefloat(elapsed) > 0.3)
457 call assert_true(reltimefloat(elapsed) < 1.0)
458 endif
459 catch
460 if v:exception !~ 'Connection reset by peer'
461 call assert_false(1, "Caught exception: " . v:exception)
462 endif
463 endtry
Bram Moolenaar7a84dbe2016-02-07 21:29:00 +0100464endfunc
Bram Moolenaar6463ca22016-02-13 17:04:46 +0100465
Bram Moolenaard6547fc2016-03-03 19:35:02 +0100466"""""""""
467
Bram Moolenaar9a6e33a2016-02-16 19:25:12 +0100468func Test_raw_pipe()
469 if !has('job')
470 return
471 endif
Bram Moolenaar81661fb2016-02-18 22:23:34 +0100472 call ch_log('Test_raw_pipe()')
Bram Moolenaar9a6e33a2016-02-16 19:25:12 +0100473 let job = job_start(s:python . " test_channel_pipe.py", {'mode': 'raw'})
474 call assert_equal("run", job_status(job))
475 try
Bram Moolenaar151f6562016-03-07 21:19:38 +0100476 " For a change use the job where a channel is expected.
477 call ch_sendraw(job, "echo something\n")
478 let msg = ch_readraw(job)
Bram Moolenaar9a6e33a2016-02-16 19:25:12 +0100479 call assert_equal("something\n", substitute(msg, "\r", "", 'g'))
480
Bram Moolenaar151f6562016-03-07 21:19:38 +0100481 call ch_sendraw(job, "double this\n")
482 let msg = ch_readraw(job)
Bram Moolenaar9a6e33a2016-02-16 19:25:12 +0100483 call assert_equal("this\nAND this\n", substitute(msg, "\r", "", 'g'))
484
Bram Moolenaar151f6562016-03-07 21:19:38 +0100485 let reply = ch_evalraw(job, "quit\n", {'timeout': 100})
Bram Moolenaar9a6e33a2016-02-16 19:25:12 +0100486 call assert_equal("Goodbye!\n", substitute(reply, "\r", "", 'g'))
487 finally
488 call job_stop(job)
489 endtry
490endfunc
491
492func Test_nl_pipe()
Bram Moolenaard8070362016-02-15 21:56:54 +0100493 if !has('job')
Bram Moolenaar6463ca22016-02-13 17:04:46 +0100494 return
495 endif
Bram Moolenaar81661fb2016-02-18 22:23:34 +0100496 call ch_log('Test_nl_pipe()')
Bram Moolenaarb6a77372016-02-15 22:55:28 +0100497 let job = job_start(s:python . " test_channel_pipe.py")
Bram Moolenaar6463ca22016-02-13 17:04:46 +0100498 call assert_equal("run", job_status(job))
499 try
500 let handle = job_getchannel(job)
Bram Moolenaar8b1862a2016-02-27 19:21:24 +0100501 call ch_sendraw(handle, "echo something\n")
Bram Moolenaar9a6e33a2016-02-16 19:25:12 +0100502 call assert_equal("something", ch_readraw(handle))
503
Bram Moolenaarc25558b2016-03-03 21:02:23 +0100504 call ch_sendraw(handle, "echoerr wrong\n")
505 call assert_equal("wrong", ch_readraw(handle, {'part': 'err'}))
506
Bram Moolenaar8b1862a2016-02-27 19:21:24 +0100507 call ch_sendraw(handle, "double this\n")
Bram Moolenaar9a6e33a2016-02-16 19:25:12 +0100508 call assert_equal("this", ch_readraw(handle))
509 call assert_equal("AND this", ch_readraw(handle))
510
Bram Moolenaar8b1862a2016-02-27 19:21:24 +0100511 let reply = ch_evalraw(handle, "quit\n")
Bram Moolenaar9a6e33a2016-02-16 19:25:12 +0100512 call assert_equal("Goodbye!", reply)
Bram Moolenaar6463ca22016-02-13 17:04:46 +0100513 finally
514 call job_stop(job)
515 endtry
516endfunc
Bram Moolenaar3bece9f2016-02-15 20:39:46 +0100517
Bram Moolenaarc25558b2016-03-03 21:02:23 +0100518func Test_nl_err_to_out_pipe()
519 if !has('job')
520 return
521 endif
522 call ch_log('Test_nl_err_to_out_pipe()')
523 let job = job_start(s:python . " test_channel_pipe.py", {'err-io': 'out'})
524 call assert_equal("run", job_status(job))
525 try
526 let handle = job_getchannel(job)
527 call ch_sendraw(handle, "echo something\n")
528 call assert_equal("something", ch_readraw(handle))
529
530 call ch_sendraw(handle, "echoerr wrong\n")
531 call assert_equal("wrong", ch_readraw(handle))
532 finally
533 call job_stop(job)
534 endtry
535endfunc
536
Bram Moolenaarb69fccf2016-03-06 23:06:25 +0100537func Test_nl_read_file()
538 if !has('job')
539 return
540 endif
Bram Moolenaarb69fccf2016-03-06 23:06:25 +0100541 call ch_log('Test_nl_read_file()')
542 call writefile(['echo something', 'echoerr wrong', 'double this'], 'Xinput')
543 let job = job_start(s:python . " test_channel_pipe.py",
544 \ {'in-io': 'file', 'in-name': 'Xinput'})
545 call assert_equal("run", job_status(job))
546 try
547 let handle = job_getchannel(job)
548 call assert_equal("something", ch_readraw(handle))
549 call assert_equal("wrong", ch_readraw(handle, {'part': 'err'}))
550 call assert_equal("this", ch_readraw(handle))
551 call assert_equal("AND this", ch_readraw(handle))
552 finally
553 call job_stop(job)
554 call delete('Xinput')
555 endtry
556endfunc
557
Bram Moolenaare98d1212016-03-08 15:37:41 +0100558func Test_nl_write_out_file()
559 if !has('job')
560 return
561 endif
562 " TODO: make this work for MS-Windows
563 if !has('unix')
564 return
565 endif
566 call ch_log('Test_nl_write_out_file()')
567 let job = job_start(s:python . " test_channel_pipe.py",
568 \ {'out-io': 'file', 'out-name': 'Xoutput'})
569 call assert_equal("run", job_status(job))
570 try
571 let handle = job_getchannel(job)
572 call ch_sendraw(handle, "echo line one\n")
573 call ch_sendraw(handle, "echo line two\n")
574 call ch_sendraw(handle, "double this\n")
575 for i in range(50)
576 sleep 10m
577 if len(readfile('Xoutput')) > 2
578 break
579 endif
580 endfor
581 call assert_equal(['line one', 'line two', 'this', 'AND this'], readfile('Xoutput'))
582 finally
583 call job_stop(job)
584 call delete('Xoutput')
585 endtry
586endfunc
587
588func Test_nl_write_err_file()
589 if !has('job')
590 return
591 endif
592 " TODO: make this work for MS-Windows
593 if !has('unix')
594 return
595 endif
596 call ch_log('Test_nl_write_err_file()')
597 let job = job_start(s:python . " test_channel_pipe.py",
598 \ {'err-io': 'file', 'err-name': 'Xoutput'})
599 call assert_equal("run", job_status(job))
600 try
601 let handle = job_getchannel(job)
602 call ch_sendraw(handle, "echoerr line one\n")
603 call ch_sendraw(handle, "echoerr line two\n")
604 call ch_sendraw(handle, "doubleerr this\n")
605 for i in range(50)
606 sleep 10m
607 if len(readfile('Xoutput')) > 2
608 break
609 endif
610 endfor
611 call assert_equal(['line one', 'line two', 'this', 'AND this'], readfile('Xoutput'))
612 finally
613 call job_stop(job)
614 call delete('Xoutput')
615 endtry
616endfunc
617
618func Test_nl_write_both_file()
619 if !has('job')
620 return
621 endif
622 " TODO: make this work for MS-Windows
623 if !has('unix')
624 return
625 endif
626 call ch_log('Test_nl_write_both_file()')
627 let job = job_start(s:python . " test_channel_pipe.py",
628 \ {'out-io': 'file', 'out-name': 'Xoutput', 'err-io': 'out'})
629 call assert_equal("run", job_status(job))
630 try
631 let handle = job_getchannel(job)
632 call ch_sendraw(handle, "echoerr line one\n")
633 call ch_sendraw(handle, "echo line two\n")
634 call ch_sendraw(handle, "double this\n")
635 call ch_sendraw(handle, "doubleerr that\n")
636 for i in range(50)
637 sleep 10m
638 if len(readfile('Xoutput')) > 5
639 break
640 endif
641 endfor
642 call assert_equal(['line one', 'line two', 'this', 'AND this', 'that', 'AND that'], readfile('Xoutput'))
643 finally
644 call job_stop(job)
645 call delete('Xoutput')
646 endtry
647endfunc
648
Bram Moolenaar8b1862a2016-02-27 19:21:24 +0100649func Test_pipe_to_buffer()
650 if !has('job')
651 return
652 endif
653 call ch_log('Test_pipe_to_buffer()')
654 let job = job_start(s:python . " test_channel_pipe.py",
655 \ {'out-io': 'buffer', 'out-name': 'pipe-output'})
656 call assert_equal("run", job_status(job))
657 try
658 let handle = job_getchannel(job)
659 call ch_sendraw(handle, "echo line one\n")
660 call ch_sendraw(handle, "echo line two\n")
661 call ch_sendraw(handle, "double this\n")
662 call ch_sendraw(handle, "quit\n")
663 sp pipe-output
664 for i in range(100)
665 sleep 10m
666 if line('$') >= 6
667 break
668 endif
669 endfor
670 call assert_equal(['Reading from channel output...', 'line one', 'line two', 'this', 'AND this', 'Goodbye!'], getline(1, '$'))
671 bwipe!
672 finally
673 call job_stop(job)
674 endtry
675endfunc
676
Bram Moolenaar014069a2016-03-03 22:51:40 +0100677func Test_pipe_from_buffer()
678 if !has('job')
679 return
680 endif
Bram Moolenaar014069a2016-03-03 22:51:40 +0100681 call ch_log('Test_pipe_from_buffer()')
682
683 sp pipe-input
684 call setline(1, ['echo one', 'echo two', 'echo three'])
685
686 let job = job_start(s:python . " test_channel_pipe.py",
687 \ {'in-io': 'buffer', 'in-name': 'pipe-input'})
688 call assert_equal("run", job_status(job))
689 try
690 let handle = job_getchannel(job)
691 call assert_equal('one', ch_read(handle))
692 call assert_equal('two', ch_read(handle))
693 call assert_equal('three', ch_read(handle))
694 bwipe!
695 finally
696 call job_stop(job)
697 endtry
Bram Moolenaar014069a2016-03-03 22:51:40 +0100698endfunc
699
Bram Moolenaarc7f0ebc2016-02-27 21:10:09 +0100700func Test_pipe_to_nameless_buffer()
701 if !has('job')
702 return
703 endif
704 call ch_log('Test_pipe_to_nameless_buffer()')
705 let job = job_start(s:python . " test_channel_pipe.py",
706 \ {'out-io': 'buffer'})
707 call assert_equal("run", job_status(job))
708 try
709 let handle = job_getchannel(job)
710 call ch_sendraw(handle, "echo line one\n")
711 call ch_sendraw(handle, "echo line two\n")
712 exe ch_getbufnr(handle, "out") . 'sbuf'
713 for i in range(100)
714 sleep 10m
715 if line('$') >= 3
716 break
717 endif
718 endfor
719 call assert_equal(['Reading from channel output...', 'line one', 'line two'], getline(1, '$'))
720 bwipe!
721 finally
722 call job_stop(job)
723 endtry
724endfunc
725
Bram Moolenaarcc7f8be2016-02-29 22:55:56 +0100726func Test_pipe_to_buffer_json()
727 if !has('job')
728 return
729 endif
730 call ch_log('Test_pipe_to_buffer_json()')
731 let job = job_start(s:python . " test_channel_pipe.py",
732 \ {'out-io': 'buffer', 'out-mode': 'json'})
733 call assert_equal("run", job_status(job))
734 try
735 let handle = job_getchannel(job)
736 call ch_sendraw(handle, "echo [0, \"hello\"]\n")
737 call ch_sendraw(handle, "echo [-2, 12.34]\n")
738 exe ch_getbufnr(handle, "out") . 'sbuf'
739 for i in range(100)
740 sleep 10m
741 if line('$') >= 3
742 break
743 endif
744 endfor
745 call assert_equal(['Reading from channel output...', '[0,"hello"]', '[-2,12.34]'], getline(1, '$'))
746 bwipe!
747 finally
748 call job_stop(job)
749 endtry
750endfunc
751
Bram Moolenaar3f39f642016-03-06 21:35:57 +0100752" Wait a little while for the last line, minus "offset", to equal "line".
753func Wait_for_last_line(line, offset)
754 for i in range(100)
755 sleep 10m
756 if getline(line('$') - a:offset) == a:line
757 break
758 endif
759 endfor
760endfunc
761
762func Test_pipe_io_two_buffers()
763 if !has('job')
764 return
765 endif
766 call ch_log('Test_pipe_io_two_buffers()')
767
768 " Create two buffers, one to read from and one to write to.
769 split pipe-output
770 set buftype=nofile
771 split pipe-input
772 set buftype=nofile
773
774 let job = job_start(s:python . " test_channel_pipe.py",
775 \ {'in-io': 'buffer', 'in-name': 'pipe-input', 'in-top': 0,
776 \ 'out-io': 'buffer', 'out-name': 'pipe-output'})
777 call assert_equal("run", job_status(job))
778 try
779 exe "normal Gaecho hello\<CR>"
780 exe bufwinnr('pipe-output') . "wincmd w"
781 call Wait_for_last_line('hello', 0)
782 call assert_equal('hello', getline('$'))
783
784 exe bufwinnr('pipe-input') . "wincmd w"
785 exe "normal Gadouble this\<CR>"
786 exe bufwinnr('pipe-output') . "wincmd w"
787 call Wait_for_last_line('AND this', 0)
788 call assert_equal('this', getline(line('$') - 1))
789 call assert_equal('AND this', getline('$'))
790
791 bwipe!
792 exe bufwinnr('pipe-input') . "wincmd w"
793 bwipe!
794 finally
795 call job_stop(job)
796 endtry
797endfunc
798
799func Test_pipe_io_one_buffer()
800 if !has('job')
801 return
802 endif
803 call ch_log('Test_pipe_io_one_buffer()')
804
805 " Create one buffer to read from and to write to.
806 split pipe-io
807 set buftype=nofile
808
809 let job = job_start(s:python . " test_channel_pipe.py",
810 \ {'in-io': 'buffer', 'in-name': 'pipe-io', 'in-top': 0,
811 \ 'out-io': 'buffer', 'out-name': 'pipe-io'})
812 call assert_equal("run", job_status(job))
813 try
814 exe "normal Goecho hello\<CR>"
815 call Wait_for_last_line('hello', 1)
816 call assert_equal('hello', getline(line('$') - 1))
817
818 exe "normal Gadouble this\<CR>"
819 call Wait_for_last_line('AND this', 1)
820 call assert_equal('this', getline(line('$') - 2))
821 call assert_equal('AND this', getline(line('$') - 1))
822
823 bwipe!
824 finally
825 call job_stop(job)
826 endtry
827endfunc
828
Bram Moolenaard46ae142016-02-16 13:33:52 +0100829""""""""""
830
Bram Moolenaar3bece9f2016-02-15 20:39:46 +0100831let s:unletResponse = ''
832func s:UnletHandler(handle, msg)
833 let s:unletResponse = a:msg
834 unlet s:channelfd
835endfunc
836
837" Test that "unlet handle" in a handler doesn't crash Vim.
838func s:unlet_handle(port)
839 let s:channelfd = ch_open('localhost:' . a:port, s:chopt)
Bram Moolenaar910b8aa2016-02-16 21:03:07 +0100840 call ch_sendexpr(s:channelfd, "test", {'callback': function('s:UnletHandler')})
Bram Moolenaar3bece9f2016-02-15 20:39:46 +0100841 sleep 10m
842 call assert_equal('what?', s:unletResponse)
843endfunc
844
845func Test_unlet_handle()
Bram Moolenaar81661fb2016-02-18 22:23:34 +0100846 call ch_log('Test_unlet_handle()')
Bram Moolenaar3bece9f2016-02-15 20:39:46 +0100847 call s:run_server('s:unlet_handle')
848endfunc
Bram Moolenaar5cefd402016-02-16 12:44:26 +0100849
Bram Moolenaard46ae142016-02-16 13:33:52 +0100850""""""""""
851
852let s:unletResponse = ''
853func s:CloseHandler(handle, msg)
854 let s:unletResponse = a:msg
855 call ch_close(s:channelfd)
856endfunc
857
858" Test that "unlet handle" in a handler doesn't crash Vim.
859func s:close_handle(port)
860 let s:channelfd = ch_open('localhost:' . a:port, s:chopt)
Bram Moolenaar910b8aa2016-02-16 21:03:07 +0100861 call ch_sendexpr(s:channelfd, "test", {'callback': function('s:CloseHandler')})
Bram Moolenaard46ae142016-02-16 13:33:52 +0100862 sleep 10m
863 call assert_equal('what?', s:unletResponse)
864endfunc
865
866func Test_close_handle()
Bram Moolenaar81661fb2016-02-18 22:23:34 +0100867 call ch_log('Test_close_handle()')
Bram Moolenaard46ae142016-02-16 13:33:52 +0100868 call s:run_server('s:close_handle')
869endfunc
870
871""""""""""
872
Bram Moolenaar5cefd402016-02-16 12:44:26 +0100873func Test_open_fail()
Bram Moolenaar81661fb2016-02-18 22:23:34 +0100874 call ch_log('Test_open_fail()')
Bram Moolenaar5cefd402016-02-16 12:44:26 +0100875 silent! let ch = ch_open("noserver")
876 echo ch
877 let d = ch
878endfunc
Bram Moolenaar81661fb2016-02-18 22:23:34 +0100879
880""""""""""
881
882func s:open_delay(port)
883 " Wait up to a second for the port to open.
884 let s:chopt.waittime = 1000
885 let channel = ch_open('localhost:' . a:port, s:chopt)
886 unlet s:chopt.waittime
887 if ch_status(channel) == "fail"
888 call assert_false(1, "Can't open channel")
889 return
890 endif
Bram Moolenaar8b1862a2016-02-27 19:21:24 +0100891 call assert_equal('got it', ch_evalexpr(channel, 'hello!'))
Bram Moolenaar81661fb2016-02-18 22:23:34 +0100892 call ch_close(channel)
893endfunc
894
895func Test_open_delay()
896 call ch_log('Test_open_delay()')
897 " The server will wait half a second before creating the port.
898 call s:run_server('s:open_delay', 'delay')
899endfunc
Bram Moolenaarece61b02016-02-20 21:39:05 +0100900
901"""""""""
902
903function MyFunction(a,b,c)
904 let s:call_ret = [a:a, a:b, a:c]
905endfunc
906
907function s:test_call(port)
908 let handle = ch_open('localhost:' . a:port, s:chopt)
909 if ch_status(handle) == "fail"
910 call assert_false(1, "Can't open channel")
911 return
912 endif
913
Bram Moolenaar8b1862a2016-02-27 19:21:24 +0100914 call assert_equal('ok', ch_evalexpr(handle, 'call-func'))
Bram Moolenaarece61b02016-02-20 21:39:05 +0100915 sleep 20m
916 call assert_equal([1, 2, 3], s:call_ret)
917endfunc
918
919func Test_call()
920 call ch_log('Test_call()')
921 call s:run_server('s:test_call')
922endfunc
Bram Moolenaaree1cffc2016-02-21 19:14:41 +0100923
924"""""""""
925
Bram Moolenaar4e221c92016-02-23 13:20:22 +0100926let s:job_exit_ret = 'not yet'
Bram Moolenaaree1cffc2016-02-21 19:14:41 +0100927function MyExitCb(job, status)
Bram Moolenaar4e221c92016-02-23 13:20:22 +0100928 let s:job_exit_ret = 'done'
Bram Moolenaaree1cffc2016-02-21 19:14:41 +0100929endfunc
930
931function s:test_exit_callback(port)
932 call job_setoptions(s:job, {'exit-cb': 'MyExitCb'})
933 let s:exit_job = s:job
934endfunc
935
936func Test_exit_callback()
937 if has('job')
Bram Moolenaar9730f742016-02-28 19:50:51 +0100938 call ch_log('Test_exit_callback()')
Bram Moolenaaree1cffc2016-02-21 19:14:41 +0100939 call s:run_server('s:test_exit_callback')
940
Bram Moolenaar9730f742016-02-28 19:50:51 +0100941 " wait up to a second for the job to exit
942 for i in range(100)
943 if s:job_exit_ret == 'done'
944 break
945 endif
946 sleep 10m
947 " calling job_status() triggers the callback
948 call job_status(s:exit_job)
949 endfor
Bram Moolenaaree1cffc2016-02-21 19:14:41 +0100950
Bram Moolenaar4e221c92016-02-23 13:20:22 +0100951 call assert_equal('done', s:job_exit_ret)
Bram Moolenaar9730f742016-02-28 19:50:51 +0100952 unlet s:exit_job
Bram Moolenaaree1cffc2016-02-21 19:14:41 +0100953 endif
954endfunc
Bram Moolenaar4e221c92016-02-23 13:20:22 +0100955
956"""""""""
957
958let s:ch_close_ret = 'alive'
959function MyCloseCb(ch)
960 let s:ch_close_ret = 'closed'
961endfunc
962
963function s:test_close_callback(port)
964 let handle = ch_open('localhost:' . a:port, s:chopt)
965 if ch_status(handle) == "fail"
966 call assert_false(1, "Can't open channel")
967 return
968 endif
969 call ch_setoptions(handle, {'close-cb': 'MyCloseCb'})
970
Bram Moolenaar8b1862a2016-02-27 19:21:24 +0100971 call assert_equal('', ch_evalexpr(handle, 'close me'))
Bram Moolenaar4e221c92016-02-23 13:20:22 +0100972 sleep 20m
973 call assert_equal('closed', s:ch_close_ret)
974endfunc
975
976func Test_close_callback()
977 call ch_log('Test_close_callback()')
978 call s:run_server('s:test_close_callback')
979endfunc
980
Bram Moolenaar9730f742016-02-28 19:50:51 +0100981" Uncomment this to see what happens, output is in src/testdir/channellog.
982" call ch_logfile('channellog', 'w')