找回密码
 立即注册
收起左侧

QT5写的tcpserver能接到client的文件,不能接收sscom和netassist的

2
回复
3400
查看
[复制链接]

尚未签到

来源: 2020-6-22 15:07:02 显示全部楼层 |阅读模式
1Qter豆
目的:在win7上用Qt写一个文件接收服务器,用于接收局域网内Android传来的文本文件。
出现的问题:用QTcreator写的tcpserver能够接收到用QT写的tcpclient的发送的文件。但是接收不到网络调试助手或者sscom发送的文件,Android也不行。可以互发消息。文件不行。
请教:有大佬知道问题出在哪里吗?
代码:
server和client的工程代码在附件

server.h

#ifndef SERVER_H
#define SERVER_H

#include <QtWidgets/QWidget>
#include "ui_Server.h"

#include <QtNetwork>
#include <QAbstractSocket>
#include <QTcpSocket>

#include <QFile>
#include <QFileDialog>

#include <QDateTime>
#include <QDataStream>

class Server : public QWidget
{
    Q_OBJECT

public:
    Server(QWidget *parent = 0);
    ~Server();

    QTcpServer *server;
    QTcpSocket *socket;
    QTcpServer *fileserver;
    QTcpSocket *filesocket;

private slots:
    void sendMessage();
    void acceptConnection();
    // 接收客户端发送的数据
    void receiveData();

    void acceptFileConnection();
    void updateFileProgress();
    void displayError(QAbstractSocket::SocketError socketError);

    // 选择发送的文件
    void selectFile();
    void sendFile();
    // 更新文件传送进度
    void updateFileProgress(qint64);

private:
    Ui::ServerClass ui;

    // 传送文件相关变量
    qint64 totalBytes;
    qint64 bytesReceived;
    qint64 bytestoWrite;
    qint64 bytesWritten;
    qint64 filenameSize;
    QString filename;
    // 每次发送数据大小
    qint64 perDataSize;
    QFile *localFile;
    // 本地缓冲区
    QByteArray inBlock;
    QByteArray outBlock;

    // 系统时间
    QDateTime current_date_time;
    QString str_date_time;
};

#endif // SERVER_H

server.cpp

#include "Server.h"
#include <QDataStream>
#include <QMessageBox>
#include <QString>
#include <QByteArray>

Server::Server(QWidget *parent)
    : QWidget(parent)
{
    ui.setupUi(this);

    this->socket = new QTcpSocket(this);
    this->server = new QTcpServer(this);
    this->server->listen(QHostAddress::Any, 6666);
    connect(this->server, SIGNAL(newConnection()), this, SLOT(acceptConnection()));
    connect(ui.pushButton_send, SIGNAL(clicked()), this, SLOT(sendMessage()));

    // 文件传送套接字
    this->filesocket = new QTcpSocket(this);
    this->fileserver = new QTcpServer(this);
    this->fileserver->listen(QHostAddress::Any, 5555);
    connect(this->fileserver, SIGNAL(newConnection()), this, SLOT(acceptFileConnection()));

    // 文件传送相关变量初始化
    bytesReceived = 0;
    totalBytes = 0;
    filenameSize = 0;
    connect(ui.pushButton_selectFile, SIGNAL(clicked()), this, SLOT(selectFile()));
    connect(ui.pushButton_sendFile, SIGNAL(clicked()), this, SLOT(sendFile()));
}

Server::~Server()
{

}

void Server::acceptConnection()
{
    this->socket = this->server->nextPendingConnection();

    connect(socket, SIGNAL(readyRead()), this, SLOT(receiveData()));
}

void Server::acceptFileConnection()
{
    bytesWritten = 0;
    // 每次发送数据大小为64kb
    perDataSize = 64 * 1024;
    this->filesocket = this->fileserver->nextPendingConnection();
    // 接受文件
    connect(filesocket, SIGNAL(readyRead()), this, SLOT(updateFileProgress()));

    connect(filesocket, SIGNAL(error(QAbstractSocket::SocketError)), this, SLOT(displayError(QAbstractSocket::SocketError)));
    connect(filesocket, SIGNAL(bytesWritten(qint64)), this, SLOT(updateFileProgress(qint64)));
    /*
    connect(filesocket, SIGNAL(error(QAbstractSocket::SocketError)), this, SLOT(updateFileProgress(qint64)));
    connect(filesocket, SIGNAL(bytesWritten(qint64)), this, SLOT(displayError(QAbstractSocket::SocketError socketError)));
    */
}

void Server::sendMessage()
{
    this->socket->write(ui.lineEdit->text().toLatin1());
    // 显示
    current_date_time = QDateTime::currentDateTime();
    str_date_time = current_date_time.toString("yyyy-MM-dd hh:mm:ss");
    QString str = "You " + str_date_time + "\n" + ui.lineEdit->text();
    ui.browser->append(str);
}

void Server::receiveData()
{
    // 获取当前时间
    current_date_time = QDateTime::currentDateTime();
    str_date_time = current_date_time.toString("yyyy-MM-dd hh:mm:ss") + "\n";

    // 接收数据
    QString str = this->socket->readAll();

    // 显示
    str = "Client " + str_date_time + str;
    this->ui.browser->append(str);
}

void Server::updateFileProgress()
{
    QDataStream inFile(this->filesocket);
    inFile.setVersion(QDataStream::Qt_5_9);

    // 如果接收到的数据小于16个字节,保存到来的文件头结构
    if (bytesReceived <= sizeof(qint64)* 2)
    {
        if ((filesocket->bytesAvailable() >= (sizeof(qint64)) * 2) && (filenameSize == 0))
        {
            inFile >> totalBytes >> filenameSize;
            bytesReceived += sizeof(qint64)* 2;
        }
        if ((filesocket->bytesAvailable() >= filenameSize) && (filenameSize != 0))
        {
            inFile >> filename;
            bytesReceived += filenameSize;
            filename = "D:/socket/"+filename;
            localFile = new QFile(filename);
            if (!localFile->open(QFile::WriteOnly))
            {
                qDebug() << "Server::open file error!";
                return;
            }
        }
        else
            return;
    }
    // 如果接收的数据小于总数据,则写入文件
    if (bytesReceived < totalBytes)
    {
        bytesReceived += filesocket->bytesAvailable();
        inBlock = filesocket->readAll();
        localFile->write(inBlock);
        inBlock.resize(0);
    }
    // 更新进度条显示
    this->ui.progressBar_fileProgress->setMaximum(totalBytes);
    this->ui.progressBar_fileProgress->setValue(bytesReceived);
    // 数据接收完成时
    if (bytesReceived == totalBytes)
    {
        this->ui.browser->append("Receive file successfully!");
        bytesReceived = 0;
        totalBytes = 0;
        filenameSize = 0;
        localFile->close();
        filesocket->close();
    }
}

void Server::displayError(QAbstractSocket::SocketError/* socketError*/)
{
    qDebug() << socket->errorString();
    socket->close();
}

void Server::selectFile()
{
    filesocket->open(QIODevice::WriteOnly);
    // 文件传送进度更新
    connect(filesocket, SIGNAL(bytesWritten(qint64)), this, SLOT(updateFileProgress(qint64)));

    this->filename = QFileDialog::getOpenFileName(this, "Open a file", "/", "files (*)");
    ui.lineEdit_fileName->setText(filename);
}

void Server::sendFile()
{
    this->localFile = new QFile(filename);
    if (!localFile->open(QFile::ReadOnly))
    {
        return;
    }
    // 获取文件大小
    this->totalBytes = localFile->size();
    QDataStream sendout(&outBlock, QIODevice::WriteOnly);
    sendout.setVersion(QDataStream::Qt_4_8);
    QString currentFileName = filename.right(filename.size() - filename.lastIndexOf('/') - 1);

    // 保留总代大小信息空间、文件名大小信息空间、文件名
    sendout << qint64(0) << qint64(0) << currentFileName;
    totalBytes += outBlock.size();
    sendout.device()->seek(0);
    sendout << totalBytes << qint64((outBlock.size() - sizeof(qint64)* 2));

    bytestoWrite = totalBytes - filesocket->write(outBlock);
    outBlock.resize(0);
}

void Server::updateFileProgress(qint64 numBytes)
{
    ////已经发送的数据大小
    bytesWritten += (int)numBytes;

    ////如果已经发送了数据
    if (bytestoWrite > 0)
    {
        outBlock = localFile->read(qMin(bytestoWrite, perDataSize));
        ///发送完一次数据后还剩余数据的大小
        bytestoWrite -= ((int)filesocket->write(outBlock));
        ///清空发送缓冲区
        outBlock.resize(0);
    }
    else
        localFile->close();

    // 如果发送完毕
    if (bytesWritten == totalBytes)
    {
        localFile->close();
        //filesocket->close();
    }
}

main.cpp

#include "Server.h"
#include <QApplication>

int main(int argc, char *argv[])
{
    QApplication a(argc, argv);
    Server w;
    w.show();

    return a.exec();
}

回复

使用道具 举报

尚未签到

2020-6-22 15:18:24 显示全部楼层
server和client的工程在:
  1. 链接:pan.baidu.com/s/1Kxkgv9b1hN5NCsMIJwa-hQ
  2. 提取码:90su
复制代码


回复

使用道具 举报

累计签到:742 天
连续签到:1 天
2020-6-23 17:15:15 显示全部楼层
你用了这东西,发送方也应该用这个发才行,你说的能通讯我有点疑惑,但是你的问题应该就在这里QDataStream inFile(this->filesocket);    inFile.setVersion(QDataStream:t_5_9);
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

公告
可以关注我们的微信公众号yafeilinux_friends获取最新动态,或者加入QQ会员群进行交流:190741849、186601429(已满) 我知道了