Pyodbc can't find FreeTDS driver

centos7, freetds, pyodbc, python, sql-server

Solution

To build on @FlipperPA's answer, it's not obvious how pyodbc "finds" the FreeTDS driver. If you have this error:

pyodbc.Error: ('01000', "[01000] [unixODBC][Driver Manager]Can't open lib 'FreeTDS' : file not found (0) (SQLDriverConnect)")

There can be other possible causes, including an incorrect environment. Here's what I discovered:

pyodbc is a wrapper around unixODBC, which isn't documented, but you need to install the `unixODBC` devel packages before you can `pip install pyodbc`. pyodbc passes the connection string directly to unixODBC.

unixODBC needs to load a shared library containing the ODBC database driver, for example `libtdsodbc.so` for FreeTDS. You can set the `DRIVER` parameter in the connect string to one of two things:

- Either the direct path to the shared library file (e.g. `/usr/local/lib/libtdsodbc.so`)

- Or the name of a config section in `odbcinst.ini`, which contains a `Driver = ...` setting that points to the shared library file

The first way is guaranteed to find the shared library, and a good way to check whether you have environment issues, but the second way is preferred and more portable. See here for more details:

This ini file simply lists all installed drivers. It is located in /etc/odbcinst.ini. The syntax is simple; a name followed by a property which tells us the drivers file name. For example;

[Sybase 11] 
Comment = Super Duper Sybase Server 
Driver =  /usr/lib/libsybase.so.11 
Setup = /usr/lib/libsybaseS.so.11 
FileUsage = 1

The Driver file name (ie `/usr/lib/libsybase.so.11`) should be unique. The friendly name (ie `Sybase 11`) must also be unique.

However, this can only work if unixODBC can find your `odbcinst.ini` file. It appears to search for it:

- in your home directory with a modified name, `.odbcinst.ini`

- In the directory pointed to by the `ODBCSYSINI` environment variable, if set.

- Otherwise, in `/etc`.

For FreeTDS it should contain something like this:

[FreeTDS]
Description = For example, my database server name or FreeTDS version
Driver = /usr/local/lib/libtdsodbc.so

Only then can you use `DRIVER=FreeTDS` in a connect string and expect it to work (and not get the above error).

You might also want to use the `ldd` command (on Linux) to check that all of the library's dependencies are satisfied, and can be found and loaded by the dynamic library loader, `ld.so`:

ldd /usr/local/lib/libtdsodbc.so
ldd: warning: you do not have execution permission for `/usr/local/lib/libtdsodbc.so'
        linux-vdso.so.1 =>  (0x00007ffe145fe000)
        libodbcinst.so.2 => /lib64/libodbcinst.so.2 (0x00007f81f9dfd000)
        libdl.so.2 => /lib64/libdl.so.2 (0x00007f81f9bf8000)
        libpthread.so.0 => /lib64/libpthread.so.0 (0x00007f81f99dc000)
        libc.so.6 => /lib64/libc.so.6 (0x00007f81f961b000)
        libltdl.so.7 => /usr/local/lib/libltdl.so.7 (0x00007f81f940f000)
        /lib64/ld-linux-x86-64.so.2 (0x00007f81fa2ac000)

If you are still stuck, you might want to start over from scratch by following this or this answer.

Problem

I am on a Centos 7 Linux machine trying to connect to an SQL database through pyodbc. I learned that you need to setup the DSN and you do that by installing the freetds driver and doing something like: ``` import pyodbc cnxn = pyodbc.connect('DRIVER={FreeTDS};SERVER=example;DATABASE=TEST;') ``` Unfortunately when I do that I get an error saying the driver FreeTDS can't be found. I have ran: ``` $ ./configure $ make $ make install ``` It seemed to have installed it but I get the same error. Can someone please send me a link to a working example

Original source

Related problems