如果数据库可到达,如何快速检查?(QT,QML,C ) - Linux
How check fast, if database reachable? (Qt, QML, C++)- Linux
我将QT与QML和C 一起使用。在我的应用程序上,我使用数据库。如果数据库可以到达,则一切都可以。
我的问题是,我想检查数据库(例如ping)。
我尝试了
db.setDatabaseName(dsn);
if(db.isValid())
{
if(db.open())
{
//std::cout <<"Offene Datenbank";
connected=true;
}
else
{
connected=false;
}
}
else
{
connected=false;
}
并将连接值作为结果。但是,如果没有连接,那需要很长的时间(也许30秒)。如果我有数据库连接,我如何快速检查?
可能有一种打破命令的方法。未连接5秒后打开?
我认为一个简单的解决方案就是仅检查数据库dever的ping。您可以使用平台的特定方式进行刺激。
这将在Linux上使用:
int exitCode = QProcess::execute("ping", QStringList() << "-c 2" << serverIp);
if (exitCode==0)
{
// is reachable
} else
{
// is not reachable
}
我已经研究了一个问题。这是我发现的。
问题是在默认DB连接超时 - 太长了。每个DB允许您使用自己的API将其更改为可接受的值。在QT中,有一个常见的DB接口-QSqlDatabase
。而且它没有这种方法。您可以通过调用其QSqlDatabase::setConnectOptions
方法来设置连接设置,但是它仅接受预定义的选项列表(您可以在QT的帮助中阅读)。
对于PostgreSQL
,有一个选项connect_timeout
,因此您可以写:
db.setConnectOptions("connect_timeout=5"); // Set to 5 seconds
对于其他数据库,没有这样的参数。每个DB的连接选项都在其"驱动程序"类中解析,该类别派生QSqlDriver
并存储在"驱动程序"库中。
所以,您可以做什么:
- 您可以重写数据库的驱动程序,以便接受超时选项。
- 您可以使用本机API为每个DB编写单独的代码。
update
事实证明,ODBC
具有SQL_ATTR_CONNECTION_TIMEOUT
选项。
更新2
qsql_odbc.cpp:713
} else if (opt.toUpper() == QLatin1String("SQL_ATTR_CONNECTION_TIMEOUT")) {
v = val.toUInt();
r = SQLSetConnectAttr(hDbc, SQL_ATTR_CONNECTION_TIMEOUT, (SQLPOINTER) v, 0);
https://msdn.microsoft.com/en-us/library/ms713605(v = vs.85).aspx
sql_attr_connection_timeout(ODBC 3.0)
sqluinteger值 对应于等待任何请求的秒数 连接到返回应用程序之前完成。司机 应返回sqlstate hyt00(超时到期) 在与查询无关的情况下可能会超时 执行或登录。
如果ValuePtr等于0(默认值),则没有超时。
应该正常工作...
我建议我有一些单独的线程/类,如果没有发生任何时间,请在某些时间后检查连接和发射信号(使用检查 - 知道连接 - 如果已连接到它,我们已经发现了)。此代码未在我的头顶上从头开始测试和写入。
可能包含一些错误。/// db connection validator in separate thread
void validator::doValidate() {
this->knowConnection = false;
db.setDatabaseName(dsn);
if(db.isValid())
{
QTimer::singleShot(1000, [this]() {
if (!this->knowConnection) {
emit connected(false);dm->connected=false;
}
});
if(db.open())
{
//std::cout <<"Offene Datenbank";
this->knowConnection = true;
dm->connected=true;
emit connected(true);
}
else
{
dm->connected=false;
this->knowConnection = true;
emit connected(false);
}
}
else
{
dm->connected=false;
this->knowConnection = true;
emit connected(false);
}
}
/// db manager in different thread
void dm::someDbFunction() {
if (connected) {
/// db logic
}
}
/// in gui or whatever
MainWindow::MainWindow() : whatever, val(new validator(..), .. {
connect(val, SIGNAL(connected(bool)), this, SLOT(statusSlot(bool));
....
}
void MainWindow::statusSlot(bool connected) {
ui->statusBar->setText((connected?"Connected":"Disconnected"));
}
- QT通过C++添加映射QML项目
- Qt Quick-如何仅从c++代码与qml属性交互
- Qt QML桌面应用程序自动化测试
- Qt QML相机在部署后显示白屏
- 如何注册Qt C++对象以在QML中使用它
- 控制带有信号/插槽的Qt QML滑动视图
- Qt - 为什么Visual Studio 2019在qml资源中添加10Mb文件后无法再编译我的项目?
- Qt QML for Android bugs
- Qt Quick - 如何在 qml 接口中使用继承自 QQuickPaintedItem 的 c++ 类?
- Qt 5.9中的QML崩溃-帮助读取堆栈跟踪
- 如何替换QML(QT)文件上的图像中的图像中没有资源中的图像
- QML/QT 无法将 C++ 中的 QList<QVariantMap> 转换为 JavaScript 中的对象数组
- 如何在QML(Qt)中离线运行OpenStreetMap
- 将图像拆分为单元格 QML/QT
- 如何从新线程 QML QT c++ 更改文本字段
- 从QML(Qt Quick应用程序)调用C++方法
- 如何使用命令行 qmake 创建 Qt GUI 或 QML/Qt 快速项目
- Integrate C++ and QML. Qt 5.4
- Qml/Qt/C++:小部件中的QQuickView,无法获得正确的位置
- 如何在Repeater内部的UI QML (QT)中显示列表中的值