#include "processthread.h" #include "appevent.h" #include "processmodel.h" #include "qjsonarray.h" #include "qjsonobject.h" #include #include "api/processapi.h" #include "qjsonvalue.h" CWF::SqlDatabaseStorage storage("QSQLITE", "localhost", "postgres", "postgres", "1234", 5432); // 将 FILETIME 转换为 Unix 时间戳 static qint64 fileTimeToUnixTimestamp(FILETIME ft) { // FILETIME 是自 1601 年以来的 100 毫微秒数 ULARGE_INTEGER ull; ull.LowPart = ft.dwLowDateTime; ull.HighPart = ft.dwHighDateTime; // FILETIME 和 时间戳的 基础时间不一样 // 转换为秒,并减去 1601 到 1970 年之间的秒数 if (ull.QuadPart / 10000000LL > 11644473600LL) { qint64 timestamp = ull.QuadPart / 10000000LL - 11644473600LL; return timestamp; } return ull.QuadPart / 10000000LL; } void sendExitTime(qint64 updataTime) { ProcessModel processModel{storage}; // 在数据库 获取 不是这个更新日期的数据 CWF::SqlQueryManager qry(storage); qry.select("*", processModel.getTableName()) .where(QString("updataTime != '%1' OR updataTime IS NULL").arg(updataTime)); qry.prepare(); QJsonObject jsonObject = qry.exec(); QJsonArray jsonArray = qry.toJson(); QJsonArray sendJsonArray; if (jsonArray.size() > 0) { for (const auto &json : jsonArray) { const QJsonObject object = json.toObject(); QJsonObject sendObject; sendObject.insert("pid", object["pid"]); sendObject.insert("pid_name", object["processName"]); sendObject.insert("begin_time", object["creationTime"]); sendObject.insert("end_time", object["exitTime"]); sendObject.insert("last_check_time", object["updataTime"]); sendObject.insert("status", 1); sendObject.insert("notes", ""); sendJsonArray.append(sendObject); } } // 上传 后 删除 if (sendJsonArray.size() > 0) { TC::ProcessApi processApi(sendJsonArray); bool isSendok = processApi.post(); if (isSendok) { // 移除发送到服务器的本地数据 CWF::SqlQueryManager qry(storage); qry.remove(processModel.getTableName(), QString("updataTime != '%1' OR updataTime IS NULL").arg(updataTime)); qry.prepare(); QJsonObject jsonObject = qry.exec(); QJsonArray jsonArray = qry.toJson(); } } bool isok = false; QVariant timeVariant = AppEvent::instance()->configReadValue("ProcessOutTime", &isok); int time = 0; if (isok) { time = timeVariant.toLongLong(); } else { // 服务器时间 } if (time > 0) { CWF::SqlQueryManager qry(storage); qry.select("*", processModel.getTableName()) .where(QString("(updataTime - lastAlertTime) > %1").arg(time)); qry.prepare(); QJsonObject jsonObject = qry.exec(); QJsonArray jsonArray = qry.toJson(); } // 提示 // SELECT * FROM ProcessTime WHERE (updataTime - lastAlertTime) > 1565; } bool ProcessThread::upDataProcessSql() { std::vector> timeProcessVector = processMonitor.checkProcesses(); // 退出时间默认当前时间 然后更新 auto exitTimestamp = QDateTime::currentSecsSinceEpoch(); auto updataTimestamp = QDateTime::currentSecsSinceEpoch(); QStringList sqlValues; for (auto timeProcess : timeProcessVector) { qint64 timestamp = fileTimeToUnixTimestamp(timeProcess->creationTime); ProcessModel processModel{storage}; CWF::SqlQueryManager qry(storage); qry.select("*", processModel.getTableName()) .where(QString("pid == '%1' AND processName == '%2'") .arg(timeProcess->pid) .arg(timeProcess->processName.c_str())); qry.prepare(); QJsonObject jsonObject = qry.exec(); if (jsonObject["success"].toBool()) { // 查询或者替换 ? QJsonArray array = qry.toJson(); if (array.size() > 0) { // 替换 for (const QJsonValue &info : array) { const QJsonObject object = info.toObject(); //数据还原到 结构体 processModel.buildFromJson(object); // 更新 结束时间 processModel.setExitTime(exitTimestamp); processModel.setUpdataTime(updataTimestamp); processModel.save(); } } else { // 插入数据 processModel.setProcessName(timeProcess->processName.c_str()); processModel.setPid(timeProcess->pid); processModel.setCreationTime(timestamp); processModel.setExitTime(exitTimestamp); processModel.setUpdataTime(updataTimestamp); processModel.setLastAlertTime(updataTimestamp); processModel.save(); } } qDebug().noquote().nospace() << jsonObject << qry.toJson(); // jsonObject.insert("begin_time", object["creationTime"]); // jsonObject.insert("end_time", object["exitTime"]); // jsonObject.insert("last_check_time", object["updataTime"]); // jsonObject.insert("status", 1); // jsonObject.insert("notes", ""); // FILETIME ft = timeProcess->creationTime; // FILETIME currentTime; // GetSystemTimeAsFileTime(¤tTime); // ULARGE_INTEGER creation, current; // creation.LowPart = ft.dwLowDateTime; // creation.HighPart = ft.dwHighDateTime; // current.LowPart = currentTime.dwLowDateTime; // current.HighPart = currentTime.dwHighDateTime; // ULONGLONG elapsedSeconds = (current.QuadPart - creation.QuadPart) / 10000000; // // 计算天、小时、分钟和秒 // ULONGLONG days = elapsedSeconds / 86400; // 1天 = 86400秒 // ULONGLONG hours = (elapsedSeconds % 86400) / 3600; // 1小时 = 3600秒 // ULONGLONG minutes = (elapsedSeconds % 3600) / 60; // 1分钟 = 60秒 // ULONGLONG seconds = elapsedSeconds % 60; // 剩余秒数 // // 打印进程的运行时间 // qDebug() << QString::fromStdString(timeProcess->processName) // // << days << hours << minutes << seconds << timestamp; /* INSERT OR REPLACE INTO ProcessTime (pid, processName, creationTime, exitTime) VALUES (123, 'process1', strftime('%s', 'now'), strftime('%s', 'now')), (124, 'process2', strftime('%s', 'now'), strftime('%s', 'now')), (125, 'process3', strftime('%s', 'now'), strftime('%s', 'now')); */ // sqlValues.append(QString("(%1,'%2',%3,%4,%5)") // .arg(timeProcess->pid) // pid // .arg(timeProcess->processName.c_str()) // 进程名 // .arg(timestamp) // 开始时间戳 // .arg(exitTimestamp) // 结束时间戳 // .arg(updataTimestamp)); // 数据更新时间 } // const QString query = QString( // R"(INSERT OR REPLACE INTO ProcessTime // (pid, processName, creationTime, exitTime, updataTime) // VALUES // %1)") // .arg(sqlValues.join(",")); // // 使用上述插入或者替换 // // 首先查找 // QString where; // CWF::SqlQueryManager qry(storage); // QJsonObject jsonObject = qry.exec(query); // 发送更新后的数据 sendExitTime(updataTimestamp); // if (jsonObject.contains("success")) { // if (jsonObject["success"].toBool()) { // return true; // } // } return false; } ProcessThread::ProcessThread( QObject *parent) : QThread{parent} {} void ProcessThread::run() { ProcessModel processModel{storage}; processModel.updateDB(); { const QString query = QString("CREATE UNIQUE INDEX %2_%3_unique ON %1 (%2, %3);") .arg(processModel.getTableName()) .arg("pid") .arg("processName"); CWF::SqlQuery qry(storage); qry.exec(query); } QElapsedTimer timer; // 创建高精度计时器 timer.start(); // 启动计时器 upDataProcessSql(); while (true) { // 校验网络 if (timer.elapsed() >= 30 * 1000) { // 检查是否经过1分钟 timer.restart(); // 重新启动计时器 upDataProcessSql(); } msleep(1000); // 休息1秒 } }