Only the "ycm:ident" value of the ft= argument in the YcmCompleter
command is working. This value forces the use of the identifier
completer which serve no purpose because this completer doesn't define
commands. Ignore completely the ft= argument and move the logic to the
Python layer.
When the client sends a request to the server, if an extra conf file is found
that is not already white/blacklisted, the server stops processing the request
and tells the client that an unknown extra conf file has been found. The client
then asks the user if that file should be loaded or not. Depending on the
user's answer, the client sends a request to the server to load or ignore the
extra conf file. Finally, the server loads the file or adds it to the
blacklist. However, the initial request was not processed by the server and
should be sent again.
This implements an asynchronous message system using a long-poll request
to the server.
The server provides an endpoint /receive_messages which blocks until
either a timeout occurs or we receive a batch of asynchronous messages.
We send this request asynchronously and poll it 4 times a second to see
if we have received any messages.
The messages may either be simply for display (such as startup progress)
or diagnostics, which override the diagnostics returned by
OnFileReqdyToParse.
In the former case, we simply display the message, accepting that this
might be overwritten by any other message (indeed, requiring this), and
for the latter we fan out diagnostics to any open buffer for the file in
question.
Unfortunately, Vim has bugs related to timers when there is something
displayed (such as a "confirm" prompt or other), so we suspend
background timers when doing subcommands to avoid vim bugs. NOTE: This
requires a new version of Vim (detected by the presence of the
particular functions used).
Reduce the time spent to build the request when there are a lot of buffers by:
- using the options property on the buffer object to get the mod variable
instead of evaluating getbufvar;
- not computing the buffer filepath if the buffer is not modified;
- passing the number of the unloaded buffer instead of its filepath on the
BufferUnload event. Getting the Python buffer object from its number is
easier than from its filepath.
Do not call user's completion function if the start column is after the current
column or if there are no candidates. This avoids keeping the user in
completion mode even if there is no completion menu.
When sending keys to Vim, they are by default added to the end of the typeahead
buffer. If there are already keys in the buffer, they will be processed first
and may change the state that our keys combination was sent for (e.g.
<C-X><C-U><C-P> in normal mode instead of insert mode or <C-e> outside of
completion mode). We avoid that by inserting the keys at the start of the
typeahead buffer.
Bring fully asynchronous completion by polling for completions with a timer
then calling completefunc once the completions are ready. Use the start column
returned by the server in completefunc. Immediately display the last completion
on the TextChangedI event to prevent the popup menu disappearing while waiting
for the completions. Handle the TextChangedI event not being triggered while
the completion menu is open by closing the menu when inserting a character
through the InsertCharPre event, and when deleting a character on the <BS> and
<C-h> keys.
Use the timers feature to display diagnostics asynchronously instead of waiting
for an autocommand to trigger.
Increase Vim version requirement to 7.4.1578.
Drop the CursorHold and CursorHoldI autocommands.
Parse buffer on the TextChanged autocommand instead of CursorMoved.
[READY] Improve reparse requirement on BufEnter event
When opening a file, Vim triggers the `BufRead` event then the `BufEnter` one. By setting the `s:previous_allowed_buffer_number` variable in `s:AllowedToCompleteInBuffer`, we avoid a reparse on `BufEnter` after parsing the buffer on `BufRead`. This reduces the number of `BufferVisit` and `FileReadyToParse` requests sent to the server by one when opening a file.
<!-- Reviewable:start -->
---
This change is [<img src="https://reviewable.io/review_button.svg" height="34" align="absmiddle" alt="Reviewable"/>](https://reviewable.io/reviews/valloric/youcompleteme/2644)
<!-- Reviewable:end -->
Considering that a buffer won't be parsed if no filetype is set and that it's
already parsed if the filetype is set when reading a buffer, there is no point
in parsing a buffer on the BufRead event.
When both versions are available, we prefer Python 3 over Python 2:
- faster startup (no monkey-patching from python-future);
- better Windows support (e.g. temporary paths are not returned in all
lowercase);
- Python 2 support will eventually be dropped.
[READY] Rely on connect timeout instead of checking that the server is alive
Currently, we always check that the ycmd process is up (with the `IsServerAlive` method) before sending a request. Without this check, each request could block Vim until a `NewConnectionError` exception is raised if the server crashed. This is the case on Windows where it takes ~1s before the exception is raised which makes Vim unusable. However, even with this check, Vim may still be blocked in the following cases:
- the server crashes just after the check but before sending the request;
- the server is up but unresponsive (e.g. its port is closed).
To avoid both cases, we instead use [the connect timeout parameter from Requests](http://docs.python-requests.org/en/master/user/advanced/?highlight=connect%20timeout#timeouts) and set it to a duration sufficiently short (10 ms) that the blocking can't be noticed by the user. Since the server is supposed to run locally (this is what YCM is designed for), 10ms is largely enough to establish a connection.
The `IsServerAlive` check is removed almost everywhere except in `OnFileReadyToParse` because we still want to notify the user if the server crashed.
This change makes it possible to not have to [wait for the server to be healthy before sending asynchronous requests](https://github.com/Valloric/YouCompleteMe/blob/master/python/ycm/client/base_request.py#L137-L138). This will dramatically improve startup time (see issue #2085) and fixes#2071. Next PR once this one is merged.
<!-- Reviewable:start -->
---
This change is [<img src="https://reviewable.io/review_button.svg" height="34" align="absmiddle" alt="Reviewable"/>](https://reviewable.io/reviews/valloric/youcompleteme/2514)
<!-- Reviewable:end -->
Vim automatically adds a space between strings when concatenating them
without the dot operator. This is not obvious so we always use the dot
operator.
Minor coding style changes when writing statements on multiple lines to
be more consistent.
Send the request as the unloaded buffer instead of the current buffer
for the BufferUnload event notification. This fixes the issue where
the filetype of the current buffer is not the same as the unloaded
buffer one, making the ycmd server uses the wrong completer when
handling the request.