From d7684470a240752a5e17938def324f4f1730584a Mon Sep 17 00:00:00 2001 From: Andrea Cedraro Date: Sat, 6 Jun 2015 17:03:48 +0200 Subject: [PATCH] Check the server end point for available completer Previously we were checking if the `hook.py` file existed for the given filetype. ycmd has an endpoint for checking if given a filetype a semantic completer is available. To avoid redundant requests we cache those requests for every filetype. A semantic engine cannot be added *after* the ycmd server is started so to avoid redundant requests we cache those requests for every filetype and we clear the cache at server setup, in this way if we issue a `YcmRestartServer` command the server will be setup again and if a semantic completer is available we can use it. Should fix #1284. --- .../ycm/client/completer_available_request.py | 48 +++++++++++++++++++ python/ycm/youcompleteme.py | 17 ++++++- 2 files changed, 63 insertions(+), 2 deletions(-) create mode 100644 python/ycm/client/completer_available_request.py diff --git a/python/ycm/client/completer_available_request.py b/python/ycm/client/completer_available_request.py new file mode 100644 index 00000000..3b12b6b2 --- /dev/null +++ b/python/ycm/client/completer_available_request.py @@ -0,0 +1,48 @@ +#!/usr/bin/env python +# +# Copyright (C) 2013 Google Inc. +# +# This file is part of YouCompleteMe. +# +# YouCompleteMe is free software: you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation, either version 3 of the License, or +# (at your option) any later version. +# +# YouCompleteMe is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with YouCompleteMe. If not, see . + +from ycm.client.base_request import ( BaseRequest, BuildRequestData, + HandleServerException ) + +class CompleterAvailableRequest( BaseRequest ): + def __init__( self, filetypes ): + super( CompleterAvailableRequest, self ).__init__() + self.filetypes = filetypes + self._response = None + + + def Start( self ): + request_data = BuildRequestData() + request_data.update( { 'filetypes': self.filetypes } ) + try: + self._response = self.PostDataToHandler( request_data, + 'semantic_completion_available' ) + except Exception as e: + HandleServerException( e ) + + + def Response( self ): + return self._response + + +def SendCompleterAvailableRequest( filetypes ): + request = CompleterAvailableRequest( filetypes ) + # This is a blocking call. + request.Start() + return request.Response() diff --git a/python/ycm/youcompleteme.py b/python/ycm/youcompleteme.py index 54da2cd7..ebc44941 100644 --- a/python/ycm/youcompleteme.py +++ b/python/ycm/youcompleteme.py @@ -30,9 +30,9 @@ from ycmd.request_wrap import RequestWrap from ycm.diagnostic_interface import DiagnosticInterface from ycm.omni_completer import OmniCompleter from ycm import syntax_parse -from ycmd.completers.completer_utils import FiletypeCompleterExistsForFiletype from ycm.client.ycmd_keepalive import YcmdKeepalive from ycm.client.base_request import BaseRequest, BuildRequestData +from ycm.client.completer_available_request import SendCompleterAvailableRequest from ycm.client.command_request import SendCommandRequest from ycm.client.completion_request import CompletionRequest from ycm.client.omni_completion_request import OmniCompletionRequest @@ -98,6 +98,7 @@ class YouCompleteMe( object ): self._ycmd_keepalive.Start() def _SetupServer( self ): + self._available_completers = {} server_port = utils.GetUnusedLocalhostPort() # The temp options file is deleted by ycmd during startup with tempfile.NamedTemporaryFile( delete = False ) as options_file: @@ -217,8 +218,20 @@ class YouCompleteMe( object ): return self._omnicomp + def FiletypeCompleterExistsForFiletype( self, filetype ): + try: + return self._available_completers[ filetype ] + except KeyError: + pass + + exists_completer = ( self.IsServerAlive() and + bool( SendCompleterAvailableRequest( filetype ) ) ) + self._available_completers[ filetype ] = exists_completer + return exists_completer + + def NativeFiletypeCompletionAvailable( self ): - return any( [ FiletypeCompleterExistsForFiletype( x ) for x in + return any( [ self.FiletypeCompleterExistsForFiletype( x ) for x in vimsupport.CurrentFiletypes() ] )