Когда я смотрю это odbcinst -j это показывает

unixODBC 2.2.14
DRIVERS............: /etc/unixODBC/odbcinst.ini
SYSTEM DATA SOURCES: /etc/unixODBC/odbc.ini
FILE DATA SOURCES..: /etc/unixODBC/ODBCDataSources
USER DATA SOURCES..: /etc/unixODBC/odbc.ini
SQLULEN Size.......: 8
SQLLEN Size........: 8
SQLSETPOSIROW Size.: 8

Но там нет места /etc/unixODBC/odbcinst.ini. Фактическое местоположение /etc/odbcinst.ini, поэтому мне нужно изменить местоположение. Как мне это сделать?

Я пытаюсь запустить ниже скрипт

import pyodbc 
cnxn = pyodbc.connect('DRIVER={SQLServer};SERVER=10.10.10.1;DATABASE=ABC;UID=username;PWD=password')
cursor = cnxn.cursor()

Но это показывает следующую ошибку

 pyodbc.Error: ('IM002', '[IM002] [unixODBC][Driver Manager]Data source name not found, and no default driver specified (0) (SQLDriverConnect)')

И я добавил информацию о файле odbc.in и odbcinst.ini следующим образом

cat odbc.ini
[SQLServer]
Description     = ODBC for MSSQL
Driver          = /usr/lib/x86_64-linux-gnu/odbc/libodbcmyS.so
Servername      = 
Database        = 
UID             = 
Port            = 1433

cat /etc/odbcinst.ini
[SQLServer]
Description     = ODBC for MSSQL
Driver          = /usr/lib/x86_64-linux-gnu/odbc/libodbcmyS.so
Setup           = /usr/lib/x86_64-linux-gnu/odbc/libmyodbc.so
UsageCount      = 1
FileUsage       = 1

Я надеюсь, что проблема в odbcinst -j, когда я показываю это, он отображает неправильный путь. Не знаю как починить.?

12
mkHun 11 Янв 2017 в 10:43

3 ответа

Лучший ответ

Похоже, путь по умолчанию установлен неправильно.
Я почти уверен, что вы уже делаете это, как указано в разных местах, но я хочу напомнить, что вы должны установить правильные переменные среды, как описано в следующих ссылках:
http://www.raosoft.com/ezsurvey/help/2007/odbc_in_unix.html http://gemfirexd.docs.pivotal.io /1.3.0/userguide/developers_guide/topics/odbc/install_config_odbc.html
Это означает, что в вашем случае вы можете добавить пару строк в ваш .bashrc или .bash_profile или аналогичный файл, чтобы программа указывала на правильные места каждый раз, когда вы открываете свою оболочку.
Строки для добавления будут тогда:

export ODBCINI=/etc/odbc.ini
export ODBCSYSINI=/etc

Если посмотреть на исходный код пакета unixODBC-2.2.14-p2 , то при вызове odbcinst -j он пройдет через следующую ветку в коде

case 'j':
    PrintConfigInfo();
    exit(0);

И PrintConfigInfo() будет печатать кучу информации, особенно то, что вы видите

void PrintConfigInfo()
{
    char szFileName[ODBC_FILENAME_MAX+1];
        char b1[ 256 ], b2[ 256 ];

    printf( "unixODBC " VERSION "\n" );

    *szFileName = '\0';
    sprintf( szFileName, "%s/odbcinst.ini", odbcinst_system_file_path( b1 ), odbcinst_system_file_name( b2 ));
    printf( "DRIVERS............: %s\n", szFileName );

    *szFileName = '\0';
    _odbcinst_SystemINI( szFileName, FALSE );
    printf( "SYSTEM DATA SOURCES: %s\n", szFileName );

    *szFileName = '\0';
    _odbcinst_FileINI( szFileName );
    printf( "FILE DATA SOURCES..: %s\n", szFileName );

    *szFileName = '\0';
    _odbcinst_UserINI( szFileName, FALSE );
    printf( "USER DATA SOURCES..: %s\n", szFileName );

    printf( "SQLULEN Size.......: %d\n", sizeof( SQLULEN ));
    printf( "SQLLEN Size........: %d\n", sizeof( SQLLEN ));
    printf( "SQLSETPOSIROW Size.: %d\n", sizeof( SQLSETPOSIROW ));
}  

Теперь давайте рассмотрим одно из утверждений print, чтобы понять, откуда оно получает путь, например, возьмем строку

printf( "SYSTEM DATA SOURCES: %s\n", szFileName );

Где szFileName устанавливается следующим вызовом:

_odbcinst_SystemINI( szFileName, FALSE );  

Который определен в файле odbcinst/_odbcinst_SystemINI.c:

BOOL _odbcinst_SystemINI( char *pszFileName, BOOL bVerify )
{
        FILE                    *hFile;
        char                    b1[ 256 ];

    sprintf( pszFileName, "%s/odbc.ini", odbcinst_system_file_path( b1 ));

        if ( bVerify )
        {
        /* try opening for read */
                hFile = uo_fopen( pszFileName, "r" );
                if ( hFile )
                        uo_fclose( hFile );
                else
        {
            /* does not exist so try creating it */
            hFile = uo_fopen( pszFileName, "w" );
            if ( hFile )
                uo_fclose( hFile );
            else
                return FALSE;
        }
        }

        return TRUE;
}

Где он устанавливает строку для печати в следующей строке

sprintf( pszFileName, "%s/odbc.ini", odbcinst_system_file_path( b1 ));

Чтобы понять, как odbcinst_system_file_path( b1 ) устанавливает этот путь, мы смотрим на источник, и каждый находит

  char *odbcinst_system_file_path( char *buffer )
{
    char *path;
    static char save_path[ 512 ];
    static int saved = 0;

    if ( saved ) {
            return save_path;
    }

    if (( path = getenv( "ODBCSYSINI" ))) {
                strcpy( buffer, path );
        strcpy( save_path, buffer );
        saved = 1;
        return buffer;
        }
#ifdef SYSTEM_FILE_PATH
    else {
        strcpy( save_path, SYSTEM_FILE_PATH );
        saved = 1;
        return SYSTEM_FILE_PATH;
        }
#else
    else {
        strcpy( save_path, "/etc" );
        saved = 1;
        return "/etc";
        }
#endif
}

Который, как вы можете видеть, читает переменную среды через getenv( "ODBCSYSINI" ). Аналогично для других. Теперь исходный код имеет другую ветвь, но в конечном итоге делает то же самое, используя настраиваемые функции.

6
fedepad 24 Янв 2017 в 21:39

Я считаю, что корень ошибки, которую вы получаете, заключается в том, что определение DRIVER вашего .odbc.ini не указывает на имя драйвера вашего odbcinst.ini.

Это должно быть что-то вроде этого:

cat odbc.ini
[SQLServer]
Description     = ODBC for MSSQL
Driver          = DRIVER_ISSUE
Servername      = 
Database        = 
UID             = 
Port            = 1433

cat /etc/odbcinst.ini
[DRIVER_ISSUE]
Description     = ODBC for MSSQL
Driver          = /usr/lib/x86_64-linux-gnu/odbc/libodbcmyS.so
Setup           = /usr/lib/x86_64-linux-gnu/odbc/libmyodbc.so
UsageCount      = 1
FileUsage       = 1

Кроме того, я считаю, что ваш драйвер (libodbcmyS.so) НЕ подходит для SQL-сервера. (Примечание: этот ответ зависит от символической ссылки, которую вы уже добавили.)

1
gregory 25 Янв 2017 в 04:33

Попробуйте это, если вы не сбросили свой odbcinst.ini

cnx = pyodbc.connect(server=servername, database = DBname, user=Username,
                           tds_version='7.3',password=Password,port=portno,
                           driver='/usr/local/lib/libtdsodbc.so')
0
Rahul Banerjee 8 Ноя 2019 в 19:29