Pani Pani - 9 months ago 132
Python Question

vim - Youcomplete me unable to find an appropriate Python library

I have followed the instructions from here https://github.com/Valloric/YouCompleteMe
and have installed both:

Cmake

sudo apt-get install build-essential cmake


and Python Headers
sudo apt-get install python-dev python3-dev


Then I
cd ~/.vim/bundle/YouCompleteMe
and runned:
./install.py --clang-completer
I got:

Searching Python 2.7 libraries...
ERROR: unable to find an appropriate Python library.


I then tried
python3 install.py --clang-completer

but still got:

Searching Python 3.4 libraries...
ERROR: unable to find an appropriate Python library.


Does anybody have an idea of what is going on?
Thanks

Answer Source

The script isn't finding the path to your python libraries. You might want to make sure you have setuptools installed before you do the following:

The error you're seeing is probably being returned by function FindPythonLibrariesOnLinux() on line 149 in ~/.vim/bundle/YouCompleteMe/third_party/ycmd/build.py

You can run just the part of script that's causing you problems by creating a file called youcompletemetest.py and fill it with the following code:

import sys
import os.path as p
import subprocess
import re

NO_PYTHON_LIBRARY_ERROR = 'ERROR: unable to find an appropriate Python library.'
PY_MAJOR, PY_MINOR = sys.version_info[ 0 : 2 ]
LIBRARY_LDCONFIG_REGEX = re.compile(
'(?P<library>\S+) \(.*\) => (?P<path>\S+)' )

if not ( ( PY_MAJOR == 2 and PY_MINOR >= 6 ) or
            ( PY_MAJOR == 3 and PY_MINOR >= 3 ) or
            PY_MAJOR > 3 ):
    sys.exit( 'ycmd requires Python >= 2.6 or >= 3.3; '
            'your version of Python is ' + sys.version )

def GetPythonNameOnUnix():
    python_name = 'python' + str( PY_MAJOR ) + '.' + str( PY_MINOR )
    # Python 3 has an 'm' suffix on Unix platforms, for instance libpython3.3m.so.
    if PY_MAJOR == 3:
        python_name += 'm' 
    return python_name


def GetStandardPythonLocationsOnUnix( prefix, name ): 
    return ( '{0}/lib/lib{1}'.format( prefix, name ),
            '{0}/include/{1}'.format( prefix, name ) )


def CheckOutput( *popen_args, **kwargs ):
    process = subprocess.Popen( stdout=subprocess.PIPE, *popen_args, **kwargs )
    output, unused_err = process.communicate()
    retcode = process.poll()
    if retcode:
        command = kwargs.get( 'args' )
        if command is None:
            command = popen_args[ 0 ]
        error = subprocess.CalledProcessError( retcode, command )
        error.output = output
        raise error
    return output


def FindPythonLibrariesOnLinux():
    python_name = GetPythonNameOnUnix()
    python_library_root, python_include = GetStandardPythonLocationsOnUnix(
        sys.exec_prefix, python_name )

    python_library = python_library_root + '.so'
    if p.isfile( python_library ):
        return python_library, python_include

    python_library = python_library_root + '.a'
    if p.isfile( python_library ):
        sys.exit( NO_DYNAMIC_PYTHON_ERROR.format( library = python_library,
                                                flag = '--enable-shared' ) )

    # On some distributions (Ubuntu for instance), the Python system library is
    # not installed in its default path: /usr/lib. We use the ldconfig tool to
    # find it.
    python_library = 'lib' + python_name + '.so'
    ldconfig_output = CheckOutput( [ 'ldconfig', '-p' ] ).strip().decode( 'utf8' )
    for line in ldconfig_output.splitlines():
        match = LIBRARY_LDCONFIG_REGEX.search( line )
        if match and match.group( 'library' ) == python_library:
            return match.group( 'path' ), python_include

    sys.exit( NO_PYTHON_LIBRARY_ERROR )

print "\n".join(FindPythonLibrariesOnLinux());

You can run that file with:

python youcompletemetest.py 

For me that will output

/usr/lib/x86_64-linux-gnu/libpython2.7.so

/usr/include/python2.7

But for you it's not able to locate python. If you know where python is installed you can find that path and replace the entire content of the function called FindPythonLibrariesOnLinux() with an array that contains the locations of your python libraries.

So open the source file:

vi ~/.vim/bundle/YouCompleteMe/third_party/ycmd/build.py

Find the function that's not's working: /^def\sFindPythonLibrariesOnLinux

Change that function so it only returns the full path to your python libraries (the following in my case):

def FindPythonLibrariesOnLinux():
    return ["/usr/lib/x86_64-linux-gnu/libpython2.7.so","/usr/include/python2.7"]

Now you will be able to continue with the installation:

./install.py --clang-completer