Qt实现FTP文件传输协议

发布时间:2024年01月07日

????????FTP(File Transfer Protocol,文件传输协议)是用于在网络上进行文件传输的一套标准协议,它属于网络传输协议的应用层。它最主要的功能是在服务器与客户端之间进行文件的传输。这个协议使用的是明文传输。FTP服务器的功能除了单纯的进行文件的传输与管理外,依据服务器软件的配置架构,它还可以提供以下几个主要功能:

(1)不同的用户:FTP服务器在默认的情况下,依据用户登录的情况而分为三种不同的身份,分别是:实体用户,real user;访客,guest;匿名用户,anonymous。

(2)命令记录与日志文件记录:FTP可以利用系统的syslogd来进行数据的记录,而记录的数据包括了用户曾经使用过的命令与用户传输数据(传输时间、文件大小等)的记录,所以可以在/var/log/里面找到各项日志信息。

(3)限制用户活动的目录(change root,简称chroot):为了避免用户在你的linux系统中随意切换目录,所以将用户的工作范围局限在用户主目录下面。FTP可以限制用户仅能在自己的用户主目录当中活动。当用户登录FTP后,由于用户无法离开自己的用户主目录,显示的根目录就是自己用户主目录的内容。这种环境称为change root,即chroot,即改变根目录的意思。

1.Qt当中导入FTP相关类

Qt当中FTP相关类,在Qt5之后便删除了,在使用时我们需要将这几个文件加入到项目当中

链接:https://pan.baidu.com/s/117nfMYsIdPWauYB7Ur_2Nw?pwd=u8ub?
提取码:u8ub?

2.FTP初始化及主要信号与槽
? ? ftp=new QFtp(this);
? ? ftp->setTransferMode(QFtp::Passive);
? ? connect(ftp,SIGNAL(stateChanged(int)),this,SLOT(slot_stateChanged(int)));
? ? connect(ftp,SIGNAL(commandFinished(int,bool)),this,SLOT(slot_command_finish(int,bool)));
? ? connect(ftp,SIGNAL(listInfo(QUrlInfo)),this,SLOT(slot_listInfo(QUrlInfo)));
3.FTP上传文件
//上传文件
void MainWindow::upload_file(QString src, QString dst)
{
? ? if(!(ftp->state()==QFtp::LoggedIn && ftp!=nullptr)){
? ? ? ? return;
? ? }
? ? if(up_file!=nullptr)
? ? ? ? delete up_file;
? ? up_file = new QFile(src);
? ? if (up_file != nullptr && up_file->open(QIODevice::ReadOnly)) {
? ? ? ? ftp->put(up_file, dst);
? ? }
}
4.FTP下载文件
//下载文件
void MainWindow::download_file(QString src, QString dst)
{
? ? if(!(ftp->state()==QFtp::LoggedIn && ftp!=nullptr)){
? ? ? ? return;
? ? }
? ? if(down_file!=nullptr)
? ? ? ? delete down_file;
? ? down_file = new QFile(dst);
? ? if (down_file != nullptr && down_file->open(QIODevice::WriteOnly)) {
? ? ? ? ftp->get(src, down_file);
? ? }
}
5.FTP获取当前目录下所有文件
ftp->list(dir_path);
6.FTP状态改变槽函数
void MainWindow::slot_stateChanged(int state)
{
? ? if(state==QFtp::Unconnected){
? ? ? ? ui->pushButton->setEnabled(false);
? ? ? ? ui->pushButton_2->setEnabled(false);
? ? ? ? ui->listWidget->setEnabled(false);
? ? ? ? ftp->connectToHost(ftp_ip,ftp_port);
? ? ? ? QMessageBox::warning(this,"操作提示","FTP连接断开");
? ? }
? ? else if(state == QFtp::Connected){
? ? ? ? ftp->login(ftp_user,ftp_password);
? ? }
? ? else if(state == QFtp::LoggedIn){
? ? ? ? ui->pushButton->setEnabled(true);
? ? ? ? ui->pushButton_2->setEnabled(true);
? ? ? ? ui->listWidget->setEnabled(true);
? ? ? ? ftp->list(dir_path);

? ? ? ? list_dir.clear();
? ? ? ? list_file.clear();
? ? }
}

注意:FTP在长时间没有进行任何操作时,可能会进行断开重连操作

7.FTP命令执行完成槽函数
void MainWindow::slot_command_finish(int id, bool fail)
{
? ? Q_UNUSED(id)

? ? if(fail){
? ? ? ? QMessageBox::warning(this,"操作提示",QString("%1 命令执行失败,%2").arg(ftp->currentCommand()).arg(ftp->errorString()));
? ? }
? ? else{
? ? ? ? if(ftp->currentCommand() == QFtp::List){
? ? ? ? ? ? update_list();
? ? ? ? }
? ? ? ? else if(ftp->currentCommand() == QFtp::Put){
? ? ? ? ? ? QMessageBox::information(this,"操作提示","上传成功");
? ? ? ? ? ? ftp->list(dir_path);
? ? ? ? ? ? list_dir.clear();
? ? ? ? ? ? list_file.clear();
? ? ? ? ? ? ui->label->setText(dir_path);
? ? ? ? }
? ? ? ? else if(ftp->currentCommand() == QFtp::Get){
? ? ? ? ? ? QMessageBox::information(this,"操作提示","下载成功");
? ? ? ? }
? ? }
}

注意:在执行完成命令之后,获取当前命令可能会变为None,所以我们在执行FTP操作之前最好设置一个标志位或一个枚举变量

8.FTP获取文件信息槽函数,在执行list命令时执行
void MainWindow::slot_listInfo(QUrlInfo info)
{
? ? if(info.isDir())
? ? ? ? list_dir.append(info.name());
? ? else if(info.isFile())
? ? ? ? list_file.append(info.name());
}

文章来源:https://blog.csdn.net/weixin_55238862/article/details/135419803
本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。