Chinaunix首页 | 论坛 | 博客
  • 博客访问: 57760
  • 博文数量: 16
  • 博客积分: 70
  • 博客等级: 民兵
  • 技术积分: 66
  • 用 户 组: 普通用户
  • 注册时间: 2012-08-07 09:54
文章分类
文章存档

2015年(11)

2014年(1)

2013年(2)

2012年(2)

我的朋友

分类: LINUX

2015-04-14 16:15:20

下载unixODBC, mysql-connector-odbc

 

安装unixODBC:

 

tar xzvf unixODBC-2.2.14.tar.gz

cd tar unixODBC-2.2.14

./configure --prefix=/code/unixODBC --enable-gui=no

make

make install

 

安装mysql-connector-odbc (libltdl required, )

 

tar xzvf mysql-connector-odbc-5.1.5r1144.tar.gz

cd mysql-connector-odbc-5.1.5r1144/

 

./configure --with-unixODBC=/code/unixODBC --with-mysql-path=/code/mysql --enable-gui=no

make
make install
odbc相关配置
cat /etc/odbcinst.ini
[mysql]
Description = MySQL driver.
Driver = /usr/local/lib/libmyodbc5-5.1.5.so
Setup = /code/unixODBC/lib/libodbcmyS.so
Socket = /tmp/mysql.sock
FileUsage = 1
 
 
cat /etc/odbc.ini
[mysql-test]
Description = MySQL test database
Trace = On
TraceFile = stderr
Driver = mysql
SERVER = localhost
USER = root
PASSWORD = mysql
PORT = 3306
DATABASE = test
socket = /tmp/mysql.sock
 
测试配置:
 
CMD /code/unixODBC/bin/isql mysql-test root mysql -v
  
连接成功:
+---------------------------------------+
| Connected! |
| |
| sql-statement |
| help [tablename] |
| quit |
| |
+---------------------------------------+

 

BTW,貌似安装运行库的时候还是不加prefix比较方便。

 

 

参考:

 

unix odbc:

 

 

http://blog.chinaunix.net/u1/58025/showart_470774.html

 

 

mysql odbc:

http://dev.mysql.com/doc/refman/5.1/en/connector-odbc-configuration-dsn-unix.html

 


四、 Linux/Unix下ODBC的编程:

 

1、使用unixODBC提供的ODBC API进行编程:

在进行编程之前,我们来看一下ODBC API中的常用数据类型与我们在C语言中使用的数据类型的对应关系:

类型标识符 ODBC数据类型 C数据类型

SQL_C_CHAR SQLCHAR * unsigned char *

SQL_C_SSHORT SQLSMALLINT short int

SQL_C_USHORT SQLUSMALLINT unsigned short int

SQL_C_SLONG SQLINTEGER long int

SQL_C_FLOAT SQLREAL float

SQL_C_DOUBLE SQLDOUBLE, SQLFLOAT double

SQL_C_BINARY SQLCHAR * unsigned char *

SQL_C_TYPE_DATE SQL_DATE_STRUCT struct tagDATE_STRUCT {SQLSMALLINT year; SQLUSMALLINT month; SQLUSMALLINT day; } DATE_STRUCT;

SQL_C_TYPE_TIME SQL_TIME_STRUCT struct tagTIME_STRUCT {SQLUSMALLINT hour; SQLUSMALLINT minute; SQLUSMALLINT second; } TIME_STRUCT;

 

我们这里使用的数据库名称为test(DSN),这个DSN使用的用户名是root,密码为空,表的名称是web,字段情况如下:

>

字段名 数据类型

id integer

name char(40)

size integer

 

第一:设定ODBC环境句柄并设置参数

首先我们需要声明一个ODBC环境句柄(SQLHENV),它可以用来获得有关的ODBC环境信息,我们需要调用SQLAllocHandle ( SQL_HANDLE_ENV, SQL_NULL_HANDLE, &V_OD_Env )来获得这个句柄,V_OD_Env就是要分配的SQLHENV类型的环境句柄。

分配好句柄之后,你给它需要设定所使用的ODBC版本,你可以调用SQLSetEnvAttr ( V_OD_Env, SQL_ATTR_ODBC_VERSION, (void*)SQL_OV_ODBC3, 0 ),SQL_ATTR_ODBC_VERSION是存放你定义的ODBC版本号的变量,SQL_OV_ODBC3则说明你的程序使用的是ODBC 3.0。

 

第二:设定连接句柄并设置超时参数

我们需要声明一个连接句柄(SQLHDBC),用来存放数据库连接信息的,调用SQLAllocHandle ( SQL_HANDLE_DBC, V_OD_Env, &V_OD_hdbc )获得连接句柄,V_OD_hdbc就是要分配的SQLHDBC类型的连接句柄。


 


分配好之后,我们可以调用SQLSetConnectAttr ( V_OD_hdbc, SQL_LOGIN_TIMEOUT, (SQLPOINTER *)5, 0 )来设定连接超时参数。

 

第三:连接数据库

调用SQLConnect ( V_OD_hdbc, (SQLCHAR*) "Test", SQL_NTS, (SQLCHAR*) "root", SQL_NTS, (SQLCHAR*) "", SQL_NTS )连接我前面提到的数据库,需要设定三个参数,就是数据库名称、用户名和密码(因为我的数据库密码为空,所以这里的密码也为空),后面的SQL_NTS的位置应该写入这些参数的长度,如果写的是SQL_NTS就是让SQLConnect来决定参数的长度。

 

第四:分配SQL语句的句柄并进行查询:

需要声明一个SQL语句的句柄(SQLHSTMT),用来存放SQL语句信息的,调用SQLAllocHandle ( SQL_HANDLE_STMT, V_OD_hdbc, &V_OD_hstmt )来获得这个句柄,V_OD_hstmt就是我们要分配的SQLHSTMT类型的SQL语句句柄。

 

我们的查询语句是:

 

SELECT name, id FROM web ORDER BY id

 

执行这条查询语句之后,查询结果可能有很多行,但每行只有两列,分别对应name和id,它们的数据类型为integer和char*,在ODBC中的数据类型标识符为SQL_C_ULONG和SQL_C_CHAR。我们需要先声明这样的两个变量来存贮查询结果:

 

SQLINTEGER V_OD_id;

char V_OD_buffer[200];

 

然后我们需要使用SQLBindCol函数把查询结果和我们定义的变量进行绑定:

 

SQLBindCol(V_OD_hstmt,1,SQL_C_CHAR, &V_OD_buffer,150,&V_OD_err);

SQLBindCol(V_OD_hstmt,2,SQL_C_ULONG,&V_OD_id,150,&V_OD_err);

 

这里的V_OD_err是用来存放错误信息编号的变量,类型也是SQLINTEGER。

接下来,我们调用SQLExecDirect来进行查询:

 

SQLExecDirect ( V_OD_hstmt, "SELECT dtname,iduser FROM web order by iduser", SQL_NTS );

 

我们可以用SQLNumResultCols ( V_OD_hstmt, &V_OD_colanz )来获得结果的列数,也可以用SQLRowCount( V_OD_hstmt, &V_OD_rowanz )来获得结果的条数,V_OD_colanz和V_OD_rowanz分别存储相应的结果,类型分别为SQLSMALLINT和SQLINTEGER。

在读取结果之前,我们需要调用SQLFetch ( V_OD_hstmt )语句,这个语句可以用来获得第一条结果也可以用来都下一条,有点像next的感觉。然后我们就可以在V_OD_id和V_OD_buffer里面获得每条记录的结果了。

 

第五:关于关闭连接和释放句柄

关闭数据库的连接,调用SQLDisconnect ( V_OD_hdbc )就可以了,但在关闭数据库之前需要先释放SQL语句的句柄,而且在关闭数据库之后应该释放连接句柄和ODBC环境句柄,语句如下(按正常的顺序):

 

SQLFreeHandle(SQL_HANDLE_STMT,V_OD_hstmt);

SQLDisconnect(V_OD_hdbc);

SQLFreeHandle(SQL_HANDLE_DBC,V_OD_hdbc);

SQLFreeHandle(SQL_HANDLE_ENV, V_OD_Env);

 

第六:关于上述情况中的错误信息处理

我们需要定义两个变量:

 

long V_OD_erg;

SQLINTEGER V_OD_err;

 

SQLAllocHandle、SQLSetEnvAttr、SQLSetConnectAttr、SQLConnect、SQLExecDirect、SQLNumResultCols和SQLRowCount的调用结果都可以用V_OD_erg来存储,V_OD_err可以获得SQLBindCol中的错误信息。

 

第七:获得本机的DSN信息

我们可以在声明SQLHENV句柄之后,使用SQLDataSources函数来获得本机的DSN信息。程序如下:

 

void OD_ListDSN(void)

{

char l_dsn[100],l_desc[100];

short int l_len1,l_len2,l_next;

 

l_next=SQL_FETCH_FIRST;

while( SQLDataSources(V_OD_Env,l_next,l_dsn, sizeof(l_dsn),

&l_len1, l_desc, sizeof(l_desc), &l_len2) == SQL_SUCCESS)

{

printf("Server=(%s) Beschreibung=(%s)

",l_dsn,l_desc);

l_next=SQL_FETCH_NEXT;

}

}

 

l_next变量是用来指定我们所要获得的DSN的类别:

SQL_FETCH_FIRST 设定SQLDataSources()函数找到第一个可用的数据源(可以是User DSN,也可以是Systerm DSN)

SQL_FETCH_FIRST_USER 设定SQLDataSources()函数找到第一个User DSN

SQL_FETCH_FIRST_SYSTEM 设定SQLDataSources()函数找到第一个System DSN

SQL_FETCH_NEXT 找到下一个数据源,至于数据源类型则要根据前面的定义

 

到这里,我们在Unix的C语言下面进行ODBC编程已经讲完,上述ODBC API需要引用以下几个头文件(这些文件已经安装到/usr/include下了):

 

#include

#include

#include

 

另外如果大家使用GTK进行编程,由于到目前为止GTK还没有加入专门处理数据库的部件,所以大家可以在GTK中调用上述的ODBC API即可。

 

这里附上例程供大家参考学习:

 

/* odbc.c

testing unixODBC

*/

#include
#include


#include "/home/lijian/sql.h"
#include "/home/lijian/sqlext.h"
#include "/home/lijian/sqltypes.h"


SQLHENV V_OD_Env; // Handle ODBC environment
long V_OD_erg; // result of functions
SQLHDBC V_OD_hdbc; // Handle connection
 
char V_OD_stat[10]; // Status SQL
SQLINTEGER V_OD_err,V_OD_rowanz,V_OD_id;
SQLSMALLINT V_OD_mlen,V_OD_colanz;
char V_OD_msg[200],V_OD_buffer[200];
 
int main(int argc,char *argv[])
{
    // 1. allocate Environment handle and register version 
    V_OD_erg=SQLAllocHandle(SQL_HANDLE_ENV,SQL_NULL_HANDLE,&V_OD_Env);
    if ((V_OD_erg != SQL_SUCCESS) && (V_OD_erg != SQL_SUCCESS_WITH_INFO))
    {
        printf("Error AllocHandle");
        exit(0);
    }

    V_OD_erg=SQLSetEnvAttr(V_OD_Env, SQL_ATTR_ODBC_VERSION, (void*)SQL_OV_ODBC3, 0); 
    if ((V_OD_erg != SQL_SUCCESS) && (V_OD_erg != SQL_SUCCESS_WITH_INFO))
    {
        printf("Error SetEnv");
        SQLFreeHandle(SQL_HANDLE_ENV, V_OD_Env);
        exit(0);
    }

    // 2. allocate connection handle, set timeout
    V_OD_erg = SQLAllocHandle(SQL_HANDLE_DBC, V_OD_Env, &V_OD_hdbc); 
    if ((V_OD_erg != SQL_SUCCESS) && (V_OD_erg != SQL_SUCCESS_WITH_INFO))
    {
        printf("Error AllocHDB %d",V_OD_erg);
        SQLFreeHandle(SQL_HANDLE_ENV, V_OD_Env);
        exit(0);
    }

    SQLSetConnectAttr(V_OD_hdbc, SQL_LOGIN_TIMEOUT, (SQLPOINTER *)5, 0);

    // 3. Connect to the datasource "web" 
    V_OD_erg = SQLConnect(V_OD_hdbc, (SQLCHAR*) "Test", SQL_NTS, (SQLCHAR*) "root", SQL_NTS, (SQLCHAR*) "", SQL_NTS);
    if ((V_OD_erg != SQL_SUCCESS) && (V_OD_erg != SQL_SUCCESS_WITH_INFO))
    {
        printf("Error SQLConnect %d",V_OD_erg);
        SQLGetDiagRec(SQL_HANDLE_DBC, V_OD_hdbc,1, 
        V_OD_stat, &V_OD_err,V_OD_msg,100,&V_OD_mlen);
        printf("%s (%d)",V_OD_msg,V_OD_err);
        SQLFreeHandle(SQL_HANDLE_ENV, V_OD_Env);
        exit(0);
    }
    printf("Connected !");

    V_OD_erg=SQLAllocHandle(SQL_HANDLE_STMT, V_OD_hdbc, &V_OD_hstmt);
    if ((V_OD_erg != SQL_SUCCESS) && (V_OD_erg != SQL_SUCCESS_WITH_INFO))
    {
        printf("Fehler im AllocStatement %d",V_OD_erg);
        SQLGetDiagRec(SQL_HANDLE_DBC, V_OD_hdbc,1, V_OD_stat,&V_OD_err,V_OD_msg,100,&V_OD_mlen);
        printf("%s (%d)",V_OD_msg,V_OD_err);
        SQLFreeHandle(SQL_HANDLE_ENV, V_OD_Env);
        exit(0);
    }
    SQLBindCol(V_OD_hstmt,1,SQL_C_CHAR, &V_OD_buffer,150,&V_OD_err);
    SQLBindCol(V_OD_hstmt,2,SQL_C_ULONG,&V_OD_id,150,&V_OD_err);


    V_OD_erg=SQLExecDirect(V_OD_hstmt,"SELECT dtname,iduser FROM web order by iduser",SQL_NTS); 
    if ((V_OD_erg != SQL_SUCCESS) && (V_OD_erg != SQL_SUCCESS_WITH_INFO))
    {
        printf("Error in Select %d",V_OD_erg);
        SQLGetDiagRec(SQL_HANDLE_DBC, V_OD_hdbc,1, V_OD_stat,&V_OD_err,V_OD_msg,100,&V_OD_mlen);
        printf("%s (%d)",V_OD_msg,V_OD_err);
        SQLFreeHandle(SQL_HANDLE_STMT,V_OD_hstmt);
        SQLFreeHandle(SQL_HANDLE_DBC,V_OD_hdbc);
        SQLFreeHandle(SQL_HANDLE_ENV, V_OD_Env);
        exit(0);
    }
    V_OD_erg=SQLNumResultCols(V_OD_hstmt,&V_OD_colanz);
    if ((V_OD_erg != SQL_SUCCESS) && (V_OD_erg != SQL_SUCCESS_WITH_INFO))
    {
        SQLFreeHandle(SQL_HANDLE_STMT,V_OD_hstmt);
        SQLDisconnect(V_OD_hdbc);
        SQLFreeHandle(SQL_HANDLE_DBC,V_OD_hdbc);
        SQLFreeHandle(SQL_HANDLE_ENV, V_OD_Env);
        exit(0);
    }
    printf("Number of Columns %d",V_OD_colanz);

    V_OD_erg=SQLRowCount(V_OD_hstmt,&V_OD_rowanz);
    if ((V_OD_erg != SQL_SUCCESS) && (V_OD_erg != SQL_SUCCESS_WITH_INFO))
    {
        printf("Number of RowCount %d",V_OD_erg);
        SQLFreeHandle(SQL_HANDLE_STMT,V_OD_hstmt);
        SQLDisconnect(V_OD_hdbc);
        SQLFreeHandle(SQL_HANDLE_DBC,V_OD_hdbc);
        SQLFreeHandle(SQL_HANDLE_ENV, V_OD_Env);
        exit(0);
    }
    printf("Number of Rows %d",V_OD_rowanz);

    V_OD_erg=SQLFetch(V_OD_hstmt); 
    while(V_OD_erg != SQL_NO_DATA)
    {
        printf("Result: %d %s",V_OD_id,V_OD_buffer);
        V_OD_erg=SQLFetch(V_OD_hstmt); 
    };

    SQLFreeHandle(SQL_HANDLE_STMT,V_OD_hstmt);
    SQLDisconnect(V_OD_hdbc);
    SQLFreeHandle(SQL_HANDLE_DBC,V_OD_hdbc);
    SQLFreeHandle(SQL_HANDLE_ENV, V_OD_Env);
    return(0);
}



2.QT下进行ODBC编程
QT 3.0提供了Data Table、Data Browser和Data View三个与数据库相关的控件。你可以在QT的Project设置你要连接的数据库,Driver一栏中选择QODBC3即可,其它选项你一看就明白了。上述的三个数据库控件的使用方法可以参见QT中相应文档,也很好使用的。

阅读(1207) | 评论(0) | 转发(0) |
0

上一篇:Installing ODBC on Linux

下一篇:ODBC 基本应用

给主人留下些什么吧!~~