使用QT实现FTP客户端与服务端(1)

1.实现FTP客户端

作为FTP客户端,需要主动发起连接至服务端所在ip的默认21号端口,连接步骤与数据交互如下:
1.客户端链接服务器端口
2.客户端分步输入用户名密码
3.(可选)客户端输入数据传输模式,默认为被动模式,可主动切换为主动模式(在一些机器上被禁用,需手动开启)
4.输入操作指令
5.根据数据传输模式建立数据连接。(5*进行数据传输)
6.退出
1)h文件

#include <QFile>
#include <QObject>
#include <QTcpSocket>
#include <QTcpServer>
#include <QTextCodec>

#include "string.h"

class FtpClientCollecor : public QObject
{
    Q_OBJECT
public:
    explicit FtpClientCollecor(QObject *parent = nullptr);
    
public:
    void doConnect();
    void sendDataMsg(const std::string &msg, const int &length);
    
private slots:
    void ClientPORTCtrlRecvData();
    void ClientRecvData();
    void ClientPASVCtrlRecvData();
    void ConnectionFromClient();
    void serverErrorConnection();
    
private:
    QTcpSocket *m_tcpSocket;
    QTcpServer *m_tcpServer;
    QTcpSocket *m_tcpDataSocket;
    QString m_userName;
    QString m_passWord;
    QString m_serverIP;
    int m_serverPort;
    int i; // 交互次数
};

2)cpp文件

#include "ftpmanager.h"
#include <QDebug>
#include <QHostAddress>

FtpClientCollecor::FtpClientCollecor(QObject *parent):QObject(parent)
{
    m_tcpServer = new QTcpServer(this);
    m_tcpSocket = new QTcpSocket(this);
    m_tcpDataSocket = new QTcpSocket(this);

    connect(m_tcpServer, SIGNAL(newConnection()), this, SLOT(ConnectionFromClient()));
    // connect(m_tcpSocket, SIGNAL(readyRead()), this, SLOT(ClientPORTCtrlRecvData()));
    connect(m_tcpSocket, SIGNAL(readyRead()), this, SLOT(ClientPASVCtrlRecvData()));
    i = 0;
    doConnect();
}

void FtpClientCollecor::doConnect()
{
    m_serverIP = "xxx.xxx.xxx.xxx";
    m_serverPort = 21;
    if (m_serverIP.isEmpty())
        qCritical() << "IP is Empty!";
    m_tcpSocket->connectToHost(QHostAddress(m_serverIP), m_serverPort);
    if (!m_tcpSocket->waitForConnected(30000))
    {
        qDebug() << "服务器连接失败";
    }
    else
    {
        qDebug() << "服务器连接成功";
        std::string sendData = "USER user\r\n";
        sendDataMsg(sendData.c_str(), sendData.size());
    }
}

void FtpClientCollecor::sendDataMsg(const std::string &msg, const int &length)
{
    QByteArray sendMsgArray;
    sendMsgArray.append(msg.c_str(), length);
    m_tcpSocket->write(sendMsgArray);
}

void FtpClientCollecor::ClientPORTCtrlRecvData()
{
    i++;
    if (!m_tcpSocket->bytesAvailable())
        return;
    QByteArray recvDatas = m_tcpSocket->readAll();
    qDebug() << "收到数据:";
    qDebug() << recvDatas;
    
    if (i == 2)
    {
        std::string sendData = "PASS 123456\r\n";
        sendDataMsg(sendData.c_str(), sendData.size());
    }
    if (i == 3)
    {
        std::string sendData = "PORT xxx,xxx,xxx,xxx,250,103\r\n";
        sendDataMsg(sendData.c_str(), sendData.size());
    }
    if (i == 4)
    {
        m_tcpServer->listen(QHostAddress::Any, 64103);
        std::string sendData = "RETR test.txt\r\n";
        sendDataMsg(sendData.c_str(), sendData.size());
        qDebug() << "发送通信请求";
    }
}
void FtpClientCollecor::ClientPASVCtrlRecvData()
{
    i++;
    if (!m_tcpSocket->bytesAvailable())
        return;
    QByteArray recvDatas = m_tcpSocket->readAll();
    qDebug() << "收到数据:";
    qDebug() << recvDatas;
    if (i == 2)
    {
        std::string sendData = "PASS 123456\r\n";
        sendDataMsg(sendData.c_str(), sendData.size());
    }
    if (i == 3)
    {
        std::string sendData = "PASV \r\n";
        sendDataMsg(sendData.c_str(), sendData.size());
    }
    if (i == 4)
    {
        QString sql = recvDatas;
        QStringList list1 = sql.split("(");
        QString listRight = list1[1];
        QStringList list2 = listRight.split(")");
        QString listLeft = list2[0];
        QStringList listIPPort = listLeft.split(",");
        int port = QString(listIPPort[4]).toInt() * 256 + QString(listIPPort[5]).toInt();
        m_tcpDataSocket->connectToHost(m_serverIP, port);
        connect(m_tcpDataSocket, SIGNAL(readyRead()), this, SLOT(ClientRecvData()));
        std::string sendData = "RETR file.txt\r\n";
        sendDataMsg(sendData.c_str(), sendData.size());
    }
}

void FtpClientCollecor::ClientRecvData()
{
    if (m_tcpServer->isListening())
    {
        m_tcpServer->close();
    }
    if (!m_tcpDataSocket->bytesAvailable())
        return;

    QByteArray recvDatas = m_tcpDataSocket->readAll();

    // 转换中文字符
    QTextCodec *tc = QTextCodec::codecForName("GBK");
    QString recvDataString = tc->toUnicode(recvDatas);
    qDebug() << recvDataString;
    QFile file("F:/file.txt");
    QTextStream out(&file);
    if(file.open(QFile::WriteOnly|QFile::Truncate))
    {
        out << recvDataString;
    }
    std::string sendData = "QUIT\r\n";
    sendDataMsg(sendData.c_str(), sendData.size());
    QByteArray sendMsgArray;
    sendMsgArray.append(sendData.c_str(), sendData.size());
    m_tcpDataSocket->write(sendMsgArray);
    qDebug() << "再见";
}

void FtpClientCollecor::ConnectionFromClient()
{
    m_tcpDataSocket = m_tcpServer->nextPendingConnection();
    connect(m_tcpDataSocket, SIGNAL(readyRead()), this, SLOT(ClientRecvData()));
}

void FtpClientCollecor::serverErrorConnection()
{
    qDebug() << m_tcpServer->errorString();
}

3)main.cpp

 FtpClientCollecor p;
  • 4
    点赞
  • 31
    收藏
    觉得还不错? 一键收藏
  • 6
    评论
基于Qt实现FTP客户端服务端程序是一种用于文件传输的网络应用程序。Qt是一个跨平台的开发框架,可以帮助开发者简化程序编写过程并实现不同操作系统下的程序兼容性。 FTP客户端通过用户操作,可以连接到FTP服务端,并进行文件的上传和下载操作。FTP客户端程序提供了用户界面,包括登录信息的输入、文件列表的展示以及上传下载按钮等。用户可以通过FTP客户端上传本地文件到FTP服务器,或者从FTP服务器下载文件到本地。上传、下载的过程中,FTP客户端会与FTP服务端进行交互,通过FTP协议进行数据传输。 FTP服务端程序则负责接收FTP客户端的连接,处理客户端的请求,并根据请求进行文件的上传和下载。FTP服务端通过监听指定的端口号,等待客户端的连接请求。一旦有客户端的连接请求,服务端接受连接,并通过鉴权确认客户端的身份。服务端程序接收客户端的上传请求后,将文件保存在服务器指定的位置;接收客户端的下载请求后,从服务器指定位置读取文件并发送给客户端。 基于QtFTP客户端服务端程序可以实现跨平台的文件传输功能,提供了图形化的用户界面和方便的操作方式。科研工作者、程序员、企业等可以使用FTP客户端服务端程序,方便地在不同设备之间进行文件传输,提高工作效率。此外,通过FTP的鉴权机制,可以保证文件传输的安全性,更好地满足用户的需求。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 6
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值