blob: e80439c361909cef70888a6cb39caf9769dd06d2 [file] [log] [blame]
Bram Moolenaarfb1f6262016-01-31 20:24:32 +01001*channel.txt* For Vim version 7.4. Last change: 2016 Jan 31
Bram Moolenaar3b5f9292016-01-28 22:37:01 +01002
3
4 VIM REFERENCE MANUAL by Bram Moolenaar
5
6
7 Inter-process communication *channel*
8
9DRAFT DRAFT DRAFT DRAFT DRAFT DRAFT DRAFT DRAFT DRAFT DRAFT
10
11Vim uses channels to communicate with other processes.
12A channel uses a socket. *socket-interface*
13
14Vim current supports up to 10 simultanious channels.
15The Netbeans interface also uses a channel. |netbeans|
16
171. Demo |channel-demo|
182. Opening a channel |channel-open|
193. Using a JSON channel |channel-use|
204. Vim commands |channel-commands|
215. Using a raw channel |channel-use|
226. Job control |job-control|
23
24{Vi does not have any of these features}
25{only available when compiled with the |+channel| feature}
26
27==============================================================================
281. Demo *channel-demo*
29
30This requires Python. The demo program can be found in
31$VIMRUNTIME/tools/demoserver.py
32Run it in one terminal. We will call this T1.
33
34Run Vim in another terminal. Connect to the demo server with: >
35 let handle = connect('localhost:8765', 'json')
36
37In T1 you should see:
38 === socket opened === ~
39
40You can now send a message to the server: >
41 echo sendexpr(handle, 'hello!')
42
43The message is received in T1 and a response is sent back to Vim.
44You can see the raw messages in T1. What Vim sends is:
45 [1,"hello!"] ~
46And the response is:
47 [1,"got it"] ~
48The number will increase every time you send a message.
49
50The server can send a command to Vim. Type this on T1 (literally, including
Bram Moolenaarfb1f6262016-01-31 20:24:32 +010051the quotes):
52 ["ex","echo 'hi there'"] ~
53And you should see the message in Vim. You can move the cursor a word forward:
54 ["normal","w"] ~
Bram Moolenaar3b5f9292016-01-28 22:37:01 +010055
56To handle asynchronous communication a callback needs to be used: >
57 func MyHandler(handle, msg)
58 echo "from the handler: " . a:msg
59 endfunc
60 call sendexpr(handle, 'hello!', "MyHandler")
61
62Instead of giving a callback with every send call, it can also be specified
63when opening the channel: >
64 call disconnect(handle)
65 let handle = connect('localhost:8765', 'json', "MyHandler")
66 call sendexpr(handle, 'hello!', 0)
67
68==============================================================================
692. Opening a channel *channel-open*
70
71To open a channel:
72 let handle = connect({address}, {mode}, {callback})
73
74{address} has the form "hostname:port". E.g., "localhost:8765".
75
76{mode} can be: *channel-mode*
77 "json" - Use JSON, see below; most convenient way
78 "raw" - Use raw messages
79
80 *channel-callback*
81{callback} is a function that is called when a message is received that is not
82handled otherwise. It gets two arguments: the channel handle and the received
83message. Example: >
84 func Handle(handle, msg)
85 echo 'Received: ' . a:msg
86 endfunc
87 let handle = connect("localhost:8765", 'json', "Handle")
88
89When {mode} is "json" the "msg" argument is the body of the received message,
90converted to Vim types.
91When {mode} is "raw" the "msg" argument is the whole message as a string.
92
93When {mode} is "json" the {callback} is optional. When omitted it is only
94possible to receive a message after sending one.
95
96The handler can be added or changed later: >
97 call sethandler(handle, {callback})
98When {callback} is empty (zero or an empty string) the handler is removed.
99
100Once done with the channel, disconnect it like this: >
101 call disconnect(handle)
102
Bram Moolenaarfb1f6262016-01-31 20:24:32 +0100103Currently up to 10 channels can be in use at the same time. *E897*
104
105When the channel can't be opened you will get an error message.
106*E898* *E899* *E900* *E901* *E902*
107
108If there is an error reading or writing a channel it will be closed.
109*E896* *E630* *E631*
110
Bram Moolenaar3b5f9292016-01-28 22:37:01 +0100111==============================================================================
1123. Using a JSON channel *channel-use*
113
114If {mode} is "json" then a message can be sent synchronously like this: >
115 let response = sendexpr(handle, {expr})
116This awaits a response from the other side.
117
118To send a message, without handling a response: >
119 call sendexpr(handle, {expr}, 0)
120
121To send a message and letting the response handled by a specific function,
122asynchronously: >
123 call sendexpr(handle, {expr}, {callback})
124
125The {expr} is converted to JSON and wrapped in an array. An example of the
126message that the receiver will get when {expr} is the string "hello":
127 [12,"hello"] ~
128
129The format of the JSON sent is:
130 [{number},{expr}]
131
132In which {number} is different every time. It must be used in the response
133(if any):
134
135 [{number},{response}]
136
137This way Vim knows which sent message matches with which received message and
138can call the right handler. Also when the messages arrive out of order.
139
140The sender must always send valid JSON to Vim. Vim can check for the end of
141the message by parsing the JSON. It will only accept the message if the end
142was received.
143
144When the process wants to send a message to Vim without first receiving a
145message, it must use the number zero:
146 [0,{response}]
147
148Then channel handler will then get {response} converted to Vim types. If the
149channel does not have a handler the message is dropped.
150
151On read error or disconnect() the string "DETACH" is sent, if still possible.
152The channel will then be inactive.
153
154==============================================================================
1554. Vim commands *channel-commands*
156
Bram Moolenaarfb1f6262016-01-31 20:24:32 +0100157PARTLY IMPLEMENTED: only "ex" and "normal" work
Bram Moolenaar3b5f9292016-01-28 22:37:01 +0100158
159With a "json" channel the process can send commands to Vim that will be
160handled by Vim internally, it does not require a handler for the channel.
161
Bram Moolenaarfb1f6262016-01-31 20:24:32 +0100162Possible commands are: *E903* *E904* *E905*
163 ["redraw" {forced}]
Bram Moolenaar3b5f9292016-01-28 22:37:01 +0100164 ["ex", {Ex command}]
165 ["normal", {Normal mode command}]
Bram Moolenaarfb1f6262016-01-31 20:24:32 +0100166 ["eval", {expression}, {number}]
Bram Moolenaar3b5f9292016-01-28 22:37:01 +0100167 ["expr", {expression}]
168
169With all of these: Be careful what these commands do! You can easily
170interfere with what the user is doing. To avoid trouble use |mode()| to check
171that the editor is in the expected state. E.g., to send keys that must be
Bram Moolenaarfb1f6262016-01-31 20:24:32 +0100172inserted as text, not executed as a command:
173 ["ex","if mode() == 'i' | call feedkeys('ClassName') | endif"] ~
174
175Errors in these commands are normally not reported to avoid them messing up
176the display. If you do want to see them, set the 'verbose' option to 3 or
177higher.
178
179
180Command "redraw" ~
181
182The other commands do not update the screen, so that you can send a sequence
183of commands without the cursor moving around. You must end with the "redraw"
184command to show any changed text and show the cursor where it belongs.
185
186The argument is normally an empty string:
187 ["redraw", ""] ~
188To first clear the screen pass "force":
189 ["redraw", "force"] ~
190
191
192Command "ex" ~
Bram Moolenaar3b5f9292016-01-28 22:37:01 +0100193
194The "ex" command is executed as any Ex command. There is no response for
Bram Moolenaarfb1f6262016-01-31 20:24:32 +0100195completion or error. You could use functions in an |autoload| script:
196 ["ex","call myscript#MyFunc(arg)"]
Bram Moolenaar3b5f9292016-01-28 22:37:01 +0100197
Bram Moolenaarfb1f6262016-01-31 20:24:32 +0100198You can also use "call |feedkeys()|" to insert any key sequence.
Bram Moolenaar3b5f9292016-01-28 22:37:01 +0100199
Bram Moolenaarfb1f6262016-01-31 20:24:32 +0100200
201Command "normal" ~
202
203The "normal" command is executed like with |:normal!|, commands are not
204mapped. Example to open the folds under the cursor:
205 ["normal" "zO"]
206
207
208Command "eval" ~
209
210The "eval" command an be used to get the result of an expression. For
211example, to get the number of lines in the current buffer:
212 ["eval","line('$')"] ~
213
214it will send back the result of the expression:
Bram Moolenaar3b5f9292016-01-28 22:37:01 +0100215 [{number}, {result}]
Bram Moolenaarfb1f6262016-01-31 20:24:32 +0100216Here {number} is the same as what was in the request. Use a negative number
217to avoid confusion with message that Vim sends.
Bram Moolenaar3b5f9292016-01-28 22:37:01 +0100218
Bram Moolenaarfb1f6262016-01-31 20:24:32 +0100219{result} is the result of the evaluation and is JSON encoded. If the
220evaluation fails it is the string "ERROR".
221
222
223Command "expr" ~
224
225The "expr" command is similar to "eval", but does not send back any response.
Bram Moolenaar3b5f9292016-01-28 22:37:01 +0100226Example:
Bram Moolenaarfb1f6262016-01-31 20:24:32 +0100227 ["expr","setline('$', ['one', 'two', 'three'])"] ~
Bram Moolenaar3b5f9292016-01-28 22:37:01 +0100228
229==============================================================================
2305. Using a raw channel *channel-raw*
231
232If {mode} is "raw" then a message can be send like this: >
233 let response = sendraw(handle, {string})
234The {string} is sent as-is. The response will be what can be read from the
235channel right away. Since Vim doesn't know how to recognize the end of the
236message you need to take care of it yourself.
237
238To send a message, without expecting a response: >
239 call sendraw(handle, {string}, 0)
240The process can send back a response, the channel handler will be called with
241it.
242
243To send a message and letting the response handled by a specific function,
244asynchronously: >
245 call sendraw(handle, {string}, {callback})
246
247This {string} can also be JSON, use |jsonencode()| to create it and
248|jsondecode()| to handle a received JSON message.
249
250==============================================================================
2516. Job control *job-control*
252
253NOT IMPLEMENTED YET
254
255To start another process: >
256 call startjob({command})
257
258This does not wait for {command} to exit.
259
260TODO:
261
262 let handle = startjob({command}, 's') # uses stdin/stdout
263 let handle = startjob({command}, '', {address}) # uses socket
264 let handle = startjob({command}, 'd', {address}) # start if connect fails
265
266
267 vim:tw=78:ts=8:ft=help:norl: