Qt5.5.1 使用ODB
环境
系统:Windows 10 64bit
数据库:SQLite3
Qt:Qt5.5.1(msvc2010)
Visual Studio:vs2010
ODB相关库版本:2.4.0
下载和编译
SQLite
参考上文编译。但是,ODB中用到了sqlite中的sqlite3_unlock_notify()函数,需要多做以下两步:
- 在”项目属性”-“配置属性”-“预处理器”-“预处理器定义”中添加一个宏:
SQLITE_ENABLE_UNLOCK_NOTIFY
- 在sqlite3.def文件最后添加一句:
sqlite3_unlock_notify
ODB
请参考:http://blog.csdn.net/calmreason/article/details/49492151
下载
从官网下载页面下载5个压缩文件:
- ODB编译器
- ODB主运行时库
- ODB数据库运行时库
- ODB-Qt扩展运行时库
- 代码样例
编译libodb和libodb-sqlite
请参考上文依次进行编译。
编译libodb-qt
与编译libodb-sqlite过程一样。需要将libodb的头文件、sqlite3的头文件,以及.lib文件拷贝到libodb-qt项目下进行编译。
在Qt Creator中使用ODB
创建工程
简单起见,我将直接编译和运行ODB提供的Qt Demo,Demo程序路径在odb-examples-2.4.0\qt
路径下。
- 在Qt Creator中新建一个工程,将Demo程序中的employee.h和driver.cpp文件拷贝到Qt的工程目录下,并添加到项目中。
- 在工程目录下新建include文件夹,将libodb、libodb-sqlite、libodb-qt三个项目的头文件全部拷贝进
include/odb/
目录,讲sqlite3.h拷贝到include/
目录。 - 在工程目录下新建lib文件夹,将sqlite3、libodb、libodb-sqlite和libodb-qt四个项目中编译出来的.lib文件全部拷贝进来。
- 修改项目的.pro文件,添加上面创建的引用目录和链接库目录。
使用ODB编译器编译数据库文件
使用ODB都需要将我们的定义的数据库类使用ODB的编译器编译成最终的odb数据库类,这里有两种编译方式:一种是我们编写好自己的类文件后,手动执行编译命令进行编译,将编译出的文件添加到Qt项目中;另一种是在Qt项目的.pro文件中自定义构建步骤,实现自动编译和添加引用。
手动编译
在控制台中跳转到Qt项目目录,执行命令: odb.exe --database sqlite --profile qt --generate-schema --generate-query --generate-session -ID:\Qt\Qt5.5.1_msvc2010\5.5\msvc2010\include employee.h
其中
参数:--profile qt
是编译Qt项目时所必须的,详见官网中关于PROFILES及Qt Profile的介绍
参数:-ID:\Qt\Qt5.5.1_msvc2010\5.5\msvc2010\include
是要向odb使用的mingw编译器的引用目录中,添加本机的Qt头文件所在目录。
编译成功后,将编译出的文件添加到Qt项目中。
修改.pro文件以自动编译
这里可以参考官方WIKI中的在Linux系统中的Qt Creator使用ODB这篇文章进行配置,只要将文章中给出的那段代码,放置到.pro文件的最后,稍微修改即可。
我这边修改后的.pro文件完整代码如下:
QT -= gui
CONFIG += c++11 console
CONFIG -= app_bundle
# The following define makes your compiler emit warnings if you use
# any feature of Qt which as been marked deprecated (the exact warnings
# depend on your compiler). Please consult the documentation of the
# deprecated API in order to know how to port your code away from it.
DEFINES += QT_DEPRECATED_WARNINGS
# You can also make your code fail to compile if you use deprecated APIs.
# In order to do so, uncomment the following line.
# You can also select to disable deprecated APIs only up to a certain version of Qt.
#DEFINES += QT_DISABLE_DEPRECATED_BEFORE=0x060000 # disables all the APIs deprecated before Qt 6.0.0
SOURCES += main.cpp
HEADERS += \
database.hxx
INCLUDEPATH += $$PWD/include/
ODB_FILES += employee.h
# ODB compiler flags.
#
ODB_FLAGS = --database sqlite --profile qt --generate-schema --generate-query --generate-session
# Select the database we are going to use.
#
DEFINES += DATABASE_SQLITE
# Suppress unknown pragmas GCC warnings.
#
#QMAKE_CXXFLAGS_WARN_ON = $$QMAKE_CXXFLAGS_WARN_ON -Wno-unknown-pragmas // had a error
QMAKE_CXXFLAGS_WARN_ON = $$QMAKE_CXXFLAGS_WARN_ON
# Link to the ODB runtime libraries.
#
LIBS += -L$$PWD/lib
CONFIG(debug, debug|release) {
#Linking library
LIBS += -lodb-sqlite-d -lodb-d -lodb-qt-d
#Destination path
DESTDIR = $$PWD/debug/
} else {
LIBS += -lodb-sqlite -lodb -lodb-qt
DESTDIR = $$PWD/release/
}
# ODB compilation rules. Normally you don't need to change anything here.
#
# Add the Qt headers directory to the ODB include directory list.
#
ODB_FLAGS += -I$$[QT_INSTALL_HEADERS]
# Newer versions of QtCreator do builds in a separate directory. As a
# result, we need to append the source directory to ODB files.
#
for(dir, ODB_FILES) {
ODB_PWD_FILES += $$PWD/$${dir}
}
odb.name = odb ${QMAKE_FILE_IN}
odb.input = ODB_PWD_FILES
odb.output = ${QMAKE_FILE_BASE}-odb.cxx
odb.commands = odb.exe $$ODB_FLAGS ${QMAKE_FILE_IN}
odb.depends = $$ODB_PWD_FILES
odb.variable_out = SOURCES
odb.clean = ${QMAKE_FILE_BASE}-odb.cxx ${QMAKE_FILE_BASE}-odb.hxx ${QMAKE_FILE_BASE}-odb.ixx ${QMAKE_FILE_BASE}.sql
QMAKE_EXTRA_COMPILERS += odb
odbh.name = odb ${QMAKE_FILE_IN}
odbh.input = ODB_PWD_FILES
odbh.output = ${QMAKE_FILE_BASE}-odb.hxx
odbh.commands = @true
odbh.CONFIG = no_link
odbh.depends = ${QMAKE_FILE_BASE}-odb.cxx
QMAKE_EXTRA_COMPILERS += odbh
其中 -Wno-unknown-pragmas
参数我这边编译时会报错,所以我将其去掉了。
另外,我这里在执行构建时,每次都会报未知指令: @true,不过程序依然能够成功构建。
还有这种方式在使用时,经常遇到odb编译出的文件找不到的情况,只要再依次执行清理、qmake、重新构建三步即可。
测试运行
odb的数据库文件编译成功后,基本就没什么问题了。为了成功能够正常运行,还需要将sqlite3、libodb、libodb-sqlite和libodb-qt四个项目中编译出来的.dll文件拷贝到项目输出目录下。直接启动测试程序,数据库默认是在内存中创建的,想在硬盘中创建出数据库文件,可以在控制台中启动程序,并加上参数--database test.db
即可。
问题记录
编译odb-sqlite库时报错:error LNK2001: 无法解析的外部符号 _sqlite3_unlock_notify
解决办法:重新编译启用sqlite3_unlock_notify()函数的SQLite3库,详见本文编译SQLite部分
ODB编译数据库文件时报错:error: unable to map C++ type ‘::QString’ used in data member ‘name_’ to a SQLite database type
解决办法:编译时使用--profile qt
或-p qt
命令使ODB启用Qt扩展,详见本文手动编译部分
ODB编译数据库文件时报错:error: QtCore/QString: No such file or directory
解决办法:编译时使用-I
命令指定本机Qt头文件位置,详见本文手动编译部分
Qt构建时报错:cl: 命令行 error D8021 :无效的数值参数“/Wno-unknown-pragmas”
解决办法:删除.pro文件中添加的-Wno-unknown-pragmas
参数
编译的文件和项目源码
我编译出的动态库、静态库以及Demo项目源代码可以在这里下载:
http://download.csdn.net/download/nitefullwind/10200839