From 64e01132905a9ef7f61b89c629e96bdee0204416 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E5=BE=90=E6=B5=B7?= Date: Thu, 16 Apr 2026 20:26:41 +0800 Subject: [PATCH] =?UTF-8?q?=E8=B0=83=E6=95=B4=E6=B5=8B=E9=87=8F=E6=9C=8D?= =?UTF-8?q?=E5=8A=A1=E6=9E=B6=E6=9E=84?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/MeasureDeviceController.cpp | 6 + src/MeasureDeviceController.h | 1 + src/MeasureServer.cpp | 89 ++++++++++++- src/MeasureServer.h | 27 +++- src/MeasureTask.h | 37 ----- ...easureTask.cpp => RequstDataProcesser.cpp} | 126 ++++-------------- src/RequstDataProcesser.h | 26 ++++ src/src.pro | 10 +- 8 files changed, 174 insertions(+), 148 deletions(-) delete mode 100644 src/MeasureTask.h rename src/{MeasureTask.cpp => RequstDataProcesser.cpp} (65%) create mode 100644 src/RequstDataProcesser.h diff --git a/src/MeasureDeviceController.cpp b/src/MeasureDeviceController.cpp index 943eb03..7b04a58 100644 --- a/src/MeasureDeviceController.cpp +++ b/src/MeasureDeviceController.cpp @@ -244,6 +244,12 @@ bool MeasureDeviceController::ClearData(const QString &device_guid) return ok; } +bool MeasureDeviceController::GetData(const QString &device_guid, int board_id, int channel_id) +{ + bool ok = false; + return ok; +} + QString MeasureDeviceController::GetMeasureGvfDataFilename() { QString measure_gvf_data_filename; diff --git a/src/MeasureDeviceController.h b/src/MeasureDeviceController.h index 6c73672..1686293 100644 --- a/src/MeasureDeviceController.h +++ b/src/MeasureDeviceController.h @@ -29,6 +29,7 @@ public: bool StopMeasure(const QString& device_guid, int board_id, int channel_id); bool StopMeasure(const QString& device_guid); bool ClearData(const QString& device_guid); + bool GetData(const QString& device_guid, int board_id, int channel_id); QString GetMeasureGvfDataFilename(); static QStringList GetMeasureDeviceList(); diff --git a/src/MeasureServer.cpp b/src/MeasureServer.cpp index 555d3b0..7bc0cd8 100644 --- a/src/MeasureServer.cpp +++ b/src/MeasureServer.cpp @@ -1,6 +1,14 @@ #include "MeasureServer.h" -#include "MeasureTask.h" #include "QsLogManage.h" +#include "MeasureDeviceController.h" +#include "MeasureServiceProtocol.h" +#include "RequstDataProcesser.h" +#include +#include +#include +#include +#include +#include MeasureServer::MeasureServer(QObject *parent) : QTcpServer(parent) @@ -17,11 +25,82 @@ void MeasureServer::Stop() this->close(); } -void MeasureServer::incomingConnection(qintptr socketDescriptor) +void MeasureServer::incomingConnection(qintptr socket_descriptor) { - QLOG_INFO() << QStringLiteral(u"接收到新的请求连接") << socketDescriptor; - MeasureTask * measure_thread = new MeasureTask(socketDescriptor, this); - connect(measure_thread, &MeasureTask::finished, measure_thread, &MeasureTask::deleteLater); + QLOG_INFO() << QStringLiteral(u"接收到新的请求连接") << socket_descriptor; + MeasureSession * measure_thread = new MeasureSession(socket_descriptor, this); + connect(measure_thread, &MeasureSession::finished, measure_thread, &MeasureSession::deleteLater); measure_thread->start(); } +MeasureSession::MeasureSession(int socket_descriptor, QObject* parent) + : QThread(parent) + , _socket_descriptor(socket_descriptor) + , _tcp_socket(nullptr) + , _requst_buffer(new QByteArray) + , _requst_data_len(0) +{ +} + +void MeasureSession::run() +{ + // 在子线程中创建套接字(关键:必须在当前线程创建) + _tcp_socket = new RequstDataProcesser; + // 设置客户端套接字描述符(绑定连接) + if (!_tcp_socket->setSocketDescriptor(_socket_descriptor)) { + QLOG_ERROR() << QStringLiteral(u"套接字初始化失败:") << _tcp_socket->errorString(); + return; + } + QLOG_INFO() << QStringLiteral(u"新客户端接入:") << _tcp_socket->peerAddress().toString() + << QStringLiteral(u"端口:") << _tcp_socket->peerPort() + << QStringLiteral(u"线程ID:") << QThread::currentThreadId(); + // 绑定信号槽(长连接核心:持续监听数据/断开) + connect(_tcp_socket, &QTcpSocket::readyRead, this, &MeasureSession::onClientRequstData, Qt::DirectConnection); + connect(_tcp_socket, &QTcpSocket::disconnected, this, &MeasureSession::onClientDisconnected, Qt::DirectConnection); + connect(_tcp_socket, QOverload::of(&QTcpSocket::error), this, &MeasureSession::onSocketError, Qt::DirectConnection); + // 开启线程事件循环(保持长连接,不退出线程) + exec(); + // 线程退出后清理资源 + _tcp_socket->close(); + _tcp_socket->deleteLater(); +} + +void MeasureSession::onClientRequstData() +{ + _requst_buffer->append(_tcp_socket->readAll()); + while (true) { + // 读头 + if (_requst_data_len == 0) { + if (_requst_buffer->size() < Protocol::HEAD_SIZE) + break; + QByteArray head = _requst_buffer->left(Protocol::HEAD_SIZE); + _requst_data_len = Protocol::UnpackDataLen(head); + _requst_buffer->remove(0, Protocol::HEAD_SIZE); + } + // 读满完整数据 + if (_requst_buffer->size() >= _requst_data_len) { + QByteArray requst_data = _requst_buffer->left(_requst_data_len); + _requst_buffer->remove(0, _requst_data_len); + QLOG_INFO() << QStringLiteral(u"接收请求数据长度%1").arg(requst_data.size()); + QThread* process_thread = QThread::create(&RequstDataProcesser::ProcessRequstData, _tcp_socket, requst_data); + connect(process_thread, &QThread::finished, process_thread, &QThread::deleteLater); + process_thread->start(); + _requst_data_len = 0; + } else { + break; + } + } +} + +void MeasureSession::onClientDisconnected() +{ + QLOG_INFO() << QStringLiteral(u"客户端%1断开连接").arg(_tcp_socket->peerAddress().toString()); + quit(); +} + +void MeasureSession::onSocketError(QAbstractSocket::SocketError error) +{ + Q_UNUSED(error); + QLOG_INFO() << QStringLiteral(u"套接字错误:").arg(_tcp_socket->errorString()); + quit(); +} diff --git a/src/MeasureServer.h b/src/MeasureServer.h index f99dcbf..5e72638 100644 --- a/src/MeasureServer.h +++ b/src/MeasureServer.h @@ -3,8 +3,10 @@ #include #include +#include +#include -class MeasureTask; +class RequstDataProcesser; class MeasureServer : public QTcpServer { @@ -16,7 +18,28 @@ public: void Stop(); protected: - void incomingConnection(qintptr socketDescriptor) override; + void incomingConnection(qintptr socket_descriptor) override; +}; + +class MeasureSession : public QThread +{ + Q_OBJECT + +public: + MeasureSession(int socket_descriptor, QObject *parent = nullptr); + + void run() override; + +private slots: + void onClientRequstData(); + void onClientDisconnected(); + void onSocketError(QAbstractSocket::SocketError error); + +private: + int _socket_descriptor; + RequstDataProcesser * _tcp_socket; + QByteArray * _requst_buffer; + qint32 _requst_data_len; }; diff --git a/src/MeasureTask.h b/src/MeasureTask.h deleted file mode 100644 index 71792a1..0000000 --- a/src/MeasureTask.h +++ /dev/null @@ -1,37 +0,0 @@ -#ifndef MEASURETASK_H -#define MEASURETASK_H - -#include -#include - -class MeasureTask : public QThread -{ - Q_OBJECT - -public: - MeasureTask(int socketDescriptor, QObject *parent = nullptr); - - void run() override; - -private slots: - void onClientRequstData(); - void onClientDisconnected(); - void onSocketError(QAbstractSocket::SocketError error); - -private: - void processRequstData(const QByteArray& requst_data); - void processStartMeasureCmd(const QString& device_guid, const QString& cmd_data); - void processStopMeasureCmd(const QString& device_guid); - void processSetDeviceMeasureConfigParamsCmd(const QString& device_guid, const QString& cmd_data); - void processClearDataCmd( const QString& device_guid); - void processGetMeasureDeviceListCmd(); - void replayClient(const QByteArray& replay_data); - -private: - int _socket_descriptor; - QTcpSocket * _tcp_socket; - QByteArray * _requst_buffer; - qint32 _requst_data_len; -}; - -#endif diff --git a/src/MeasureTask.cpp b/src/RequstDataProcesser.cpp similarity index 65% rename from src/MeasureTask.cpp rename to src/RequstDataProcesser.cpp index 84e2480..a37fe0e 100644 --- a/src/MeasureTask.cpp +++ b/src/RequstDataProcesser.cpp @@ -1,90 +1,30 @@ -#include "MeasureTask.h" +#include "RequstDataProcesser.h" +#include "QsLogManage.h" #include "MeasureDeviceController.h" #include "MeasureServiceProtocol.h" -#include "QsLogManage.h" -#include -#include +#include #include #include +#include #include -#include -#include -#include -#include -MeasureTask::MeasureTask(int socketDescriptor, QObject* parent) - : QThread(parent) - , _socket_descriptor(socketDescriptor) - , _tcp_socket(nullptr) - , _requst_buffer(new QByteArray) - , _requst_data_len(0) -{ -} +RequstDataProcesser::RequstDataProcesser(QObject *parent) + : QTcpSocket{parent} +{} -void MeasureTask::run() +void RequstDataProcesser::OnReplayClient(const QByteArray& replay_data) { - // 在子线程中创建套接字(关键:必须在当前线程创建) - _tcp_socket = new QTcpSocket; - // 设置客户端套接字描述符(绑定连接) - if (!_tcp_socket->setSocketDescriptor(_socket_descriptor)) { - QLOG_ERROR() << QStringLiteral(u"套接字初始化失败:") << _tcp_socket->errorString(); + if (!this->isOpen()) { + QLOG_WARN() << QStringLiteral(u"未连接,发送失败"); return; } - QLOG_INFO() << QStringLiteral(u"新客户端接入:") << _tcp_socket->peerAddress().toString() - << QStringLiteral(u"端口:") << _tcp_socket->peerPort() - << QStringLiteral(u"线程ID:") << QThread::currentThreadId(); - // 绑定信号槽(长连接核心:持续监听数据/断开) - connect(_tcp_socket, &QTcpSocket::readyRead, this, &MeasureTask::onClientRequstData); - connect(_tcp_socket, &QTcpSocket::disconnected, this, &MeasureTask::onClientDisconnected); - connect(_tcp_socket, QOverload::of(&QTcpSocket::error), this, &MeasureTask::onSocketError); - // 开启线程事件循环(保持长连接,不退出线程) - exec(); - // 线程退出后清理资源 - _tcp_socket->close(); - _tcp_socket->deleteLater(); + QByteArray replay_buf = Protocol::PackData(replay_data); + this->write(replay_buf); + this->flush(); + QLOG_DEBUG() << QStringLiteral(u"发送数据大小: %1 字节").arg(replay_buf.size()); } -void MeasureTask::onClientRequstData() -{ - _requst_buffer->append(_tcp_socket->readAll()); - while (true) { - // 读头 - if (_requst_data_len == 0) { - if (_requst_buffer->size() < Protocol::HEAD_SIZE) - break; - QByteArray head = _requst_buffer->left(Protocol::HEAD_SIZE); - _requst_data_len = Protocol::UnpackDataLen(head); - _requst_buffer->remove(0, Protocol::HEAD_SIZE); - } - // 读满完整数据 - if (_requst_buffer->size() >= _requst_data_len) { - QByteArray requst_data = _requst_buffer->left(_requst_data_len); - _requst_buffer->remove(0, _requst_data_len); - QLOG_INFO() << QStringLiteral(u"接收请求数据长度%1").arg(requst_data.size()); - QThread* process_thread = QThread::create(&MeasureTask::processRequstData, this, requst_data); - connect(process_thread, &QThread::finished, process_thread, &QThread::deleteLater); - process_thread->start(); - _requst_data_len = 0; - } else { - break; - } - } -} - -void MeasureTask::onClientDisconnected() -{ - QLOG_INFO() << QStringLiteral(u"客户端%1断开连接").arg(_tcp_socket->peerAddress().toString()); - quit(); -} - -void MeasureTask::onSocketError(QAbstractSocket::SocketError error) -{ - Q_UNUSED(error); - QLOG_INFO() << QStringLiteral(u"套接字错误:").arg(_tcp_socket->errorString()); - quit(); -} - -void MeasureTask::processRequstData(const QByteArray &requst_data) +void RequstDataProcesser::ProcessRequstData(const QByteArray& requst_data) { QDataStream requst_data_stream(requst_data); QString cmd_type, device_guid, cmd_data; @@ -110,11 +50,11 @@ void MeasureTask::processRequstData(const QByteArray &requst_data) QByteArray replay_data; QDataStream replay_data_stream(&replay_data, QIODevice::Append); replay_data_stream << QString("UNKNOW") << false << QStringLiteral(u"未知请求"); - this->replayClient(replay_data); + QMetaObject::invokeMethod(this, "OnReplayClient", Qt::QueuedConnection, Q_ARG(QByteArray, replay_data)); } } -void MeasureTask::processStartMeasureCmd(const QString& device_guid, const QString& cmd_data) +void RequstDataProcesser::processStartMeasureCmd(const QString& device_guid, const QString& cmd_data) { QByteArray json_data = cmd_data.toUtf8(); QJsonDocument json_doc = QJsonDocument::fromJson(json_data); @@ -165,7 +105,7 @@ void MeasureTask::processStartMeasureCmd(const QString& device_guid, const QStri QDataStream replay_data_stream(&replay_data, QIODevice::Append); if (!errors.isEmpty()) { replay_data_stream << QString("START") << false << errors.join("\n"); - this->replayClient(replay_data); + QMetaObject::invokeMethod(this, "OnReplayClient", Qt::QueuedConnection, Q_ARG(QByteArray, replay_data)); } else { const QString& measure_data_gvf_filename = MeasureDeviceController::Instance()->GetMeasureGvfDataFilename(); QString replay_info; @@ -178,20 +118,20 @@ void MeasureTask::processStartMeasureCmd(const QString& device_guid, const QStri QByteArray replay_data; QDataStream replay_data_stream(&replay_data, QIODevice::Append); replay_data_stream << QString("START") << ok << replay_info; - this->replayClient(replay_data); + QMetaObject::invokeMethod(this, "OnReplayClient", Qt::QueuedConnection, Q_ARG(QByteArray, replay_data)); } } -void MeasureTask::processStopMeasureCmd(const QString& device_guid) +void RequstDataProcesser::processStopMeasureCmd(const QString& device_guid) { MeasureDeviceController::Instance()->StopMeasure(device_guid); QByteArray replay_data; QDataStream replay_data_stream(&replay_data, QIODevice::Append); replay_data_stream << QString("STOP") << true << QStringLiteral(u"停止测量完成"); - this->replayClient(replay_data); + QMetaObject::invokeMethod(this, "OnReplayClient", Qt::QueuedConnection, Q_ARG(QByteArray, replay_data)); } -void MeasureTask::processSetDeviceMeasureConfigParamsCmd(const QString& device_guid, const QString& cmd_data) +void RequstDataProcesser::processSetDeviceMeasureConfigParamsCmd(const QString& device_guid, const QString& cmd_data) { QByteArray json_data = cmd_data.toUtf8(); QJsonDocument json_doc = QJsonDocument::fromJson(json_data); @@ -232,19 +172,19 @@ void MeasureTask::processSetDeviceMeasureConfigParamsCmd(const QString& device_g } else { replay_data_stream << QString("SET") << ok << QStringLiteral(u"设置测量参数完成"); } - this->replayClient(replay_data); + QMetaObject::invokeMethod(this, "OnReplayClient", Qt::QueuedConnection, Q_ARG(QByteArray, replay_data)); } -void MeasureTask::processClearDataCmd(const QString& device_guid) +void RequstDataProcesser::processClearDataCmd(const QString& device_guid) { MeasureDeviceController::Instance()->ClearData(device_guid); QByteArray replay_data; QDataStream replay_data_stream(&replay_data, QIODevice::Append); replay_data_stream << QString("CLEAR") << true << QStringLiteral(u"清除数据完成"); - this->replayClient(replay_data); + QMetaObject::invokeMethod(this, "OnReplayClient", Qt::QueuedConnection, Q_ARG(QByteArray, replay_data)); } -void MeasureTask::processGetMeasureDeviceListCmd() +void RequstDataProcesser::processGetMeasureDeviceListCmd() { QStringList device_list = MeasureDeviceController::Instance()->GetMeasureDeviceList(); bool ok = !device_list.isEmpty(); @@ -260,17 +200,5 @@ void MeasureTask::processGetMeasureDeviceListCmd() } else { replay_data_stream << ok << QStringLiteral(u"测量设备未找到"); } - this->replayClient(replay_data); -} - -void MeasureTask::replayClient(const QByteArray &replay_data) -{ - if (!_tcp_socket->isOpen()) { - QLOG_WARN() << QStringLiteral(u"未连接,发送失败"); - return; - } - QByteArray replay_buf = Protocol::PackData(replay_data); - _tcp_socket->write(replay_buf); - _tcp_socket->flush(); - QLOG_DEBUG() << QStringLiteral(u"发送数据大小: %1 字节").arg(replay_buf.size()); + QMetaObject::invokeMethod(this, "OnReplayClient", Qt::QueuedConnection, Q_ARG(QByteArray, replay_data)); } diff --git a/src/RequstDataProcesser.h b/src/RequstDataProcesser.h new file mode 100644 index 0000000..bc11eb4 --- /dev/null +++ b/src/RequstDataProcesser.h @@ -0,0 +1,26 @@ +#ifndef REQUSTDATAPROCESSER_H +#define REQUSTDATAPROCESSER_H + +#include +#include + +class RequstDataProcesser : public QTcpSocket +{ + Q_OBJECT +public: + explicit RequstDataProcesser(QObject *parent = nullptr); + + void ProcessRequstData(const QByteArray& requst_data); + +public slots: + void OnReplayClient(const QByteArray& replay_data); + +private: + void processStartMeasureCmd(const QString& device_guid, const QString& cmd_data); + void processStopMeasureCmd(const QString& device_guid); + void processSetDeviceMeasureConfigParamsCmd(const QString& device_guid, const QString& cmd_data); + void processClearDataCmd( const QString& device_guid); + void processGetMeasureDeviceListCmd(); +}; + +#endif // REQUSTDATAPROCESSER_H diff --git a/src/src.pro b/src/src.pro index 9b7250d..7c7b8be 100644 --- a/src/src.pro +++ b/src/src.pro @@ -21,15 +21,15 @@ UI_DIR = $${BUILD_UI}/$${TARGET}/ui SOURCES += \ $${PWD}/MeasureServer.cpp \ - $${PWD}/MeasureTask.cpp \ $${PWD}/main.cpp \ - MeasureDeviceController.cpp + $${PWD}/MeasureDeviceController.cpp \ + $${PWD}/RequstDataProcesser.cpp HEADERS += \ $${PWD}/MeasureServer.h \ - $${PWD}/MeasureTask.h \ - MeasureDeviceController.h \ - MeasureServiceProtocol.h + $${PWD}/MeasureDeviceController.h \ + $${PWD}/MeasureServiceProtocol.h \ + $${PWD}/RequstDataProcesser.h DEFINES += ENABLE_DEBUG