Qt網路(三)FTP(一)

來源:互聯網
上載者:User

上一節我們講述了HTTP的編程,這一節講述與其及其相似的FTP的編程。FTP即File Transfer Protocol,也就是檔案傳輸通訊協定。FTP的主要作用,就是讓使用者串連上一個遠端電腦,查看遠端電腦有哪些檔案,然後把檔案從遠端電腦上拷貝到本機電腦,或者把本機電腦的檔案送到遠端電腦上。

     在Qt中,我們可以使用上一節講述的QNetworkAccessManager和QNetworkReply類來進行FTP 程式的編寫,因為它們用起來很簡單。但是,對於較複雜的FTP操作,Qt還提供了QFtp類,利用這個類,我們很容易寫出一個FTP用戶端程式。下面我們先在協助中查看這個類。

 

在QFtp中,所有的操作都對應一個特定的函數,我們可以稱它們為命令。如connectToHost()串連到伺服器命令,login()登入命令,get()下載命令,mkdir()建立目錄命令等。因為QFtp類以非同步方式工作,所以所有的這些函數都不是阻塞函數。也就是說,如果一個操作不能立即執行,那麼這個函數就會直接返回,直到程式控制權返回Qt事件迴圈後才真正執行,它們不會影響介面的顯示。

所有的命令都返回一個int 型的編號,使用這個編號讓我們可以跟蹤這個命令,查看其執行狀態。當每條命令開始執行時,都會發出commandStarted()訊號,當該命令執行結束時,會發出commandFinished()訊號。我們可以利用這兩個訊號和命令的編號來擷取命令的執行狀態。當然,我們不想執行每條命令都要記下它的編號,所以我們也可以使用currentCommand()來擷取現在執行的命令,其傳回值與命令的對應關係如。

 

下面我們先看一個簡單的FTP用戶端的例子,然後對它進行擴充。

在這個例子中我們從FTP伺服器上下載一個檔案並顯示出來。

1.我們建立Qt4 Gui QApplication

工程名為“myFtp”,然後選中QtNetwork模組,最後Base class選擇QWidget 。

2.修改widget.ui檔案。

在其中添加一個Text Browser 和一個 Label,效果如下。

 

3.在main.cpp中進行修改。

為了在程式中可以使用中文,我們在main.cpp中添加標頭檔#include <QTextCodec>

並在main()函數中添加代碼:QTextCodec::setCodecForTr(QTextCodec::codecForLocale());

4.在widget.h中進行修改。

先添加標頭檔:#include <QFtp>

再在private中定義對象:QFtp *ftp;

添加私人槽函數:

private slots:

    void ftpCommandStarted(int);

void ftpCommandFinished(int,bool);

5.在widget.cpp中變更。

(1)在建構函式中添加代碼:

ftp = new QFtp(this);

    ftp->connectToHost(“ftp.qt.nokia.com”); //串連到伺服器

    ftp->login();   //登入

    ftp->cd(“qt”);   //跳轉到“qt”目錄下

    ftp->get(“INSTALL”);  //下載“INSTALL”檔案

    ftp->close();   //關閉串連

    connect(ftp,SIGNAL(commandStarted(int)),

            this,SLOT(ftpCommandStarted(int)));

    //當每條命令開始執行時發出相應的訊號

    connect(ftp,SIGNAL(commandFinished(int,bool)),

            this,SLOT(ftpCommandFinished(int,bool)));

//當每條命令執行結束時發出相應的訊號

我們在建構函式裡執行了幾個FTP的操作,登入網站,並下載了一個檔案。然後我們又關聯了兩個訊號和槽,用來跟蹤命令的執行情況。

(2)實現槽函數:

void Widget::ftpCommandStarted(int)

{

    if(ftp->currentCommand() == QFtp::ConnectToHost){

        ui->label->setText(tr(“正在串連到伺服器…”));

    }

    if (ftp->currentCommand() == QFtp::Login){

        ui->label->setText(tr(“正在登入…”));

    }

    if (ftp->currentCommand() == QFtp::Get){

        ui->label->setText(tr(“正在下載…”));

    }

    else if (ftp->currentCommand() == QFtp::Close){

        ui->label->setText(tr(“正在關閉串連…”));

    }

}

每當命令執行時,都會執行ftpCommandStarted()函數,它有一個參數int id,這個id就是調用命令時返回的id,如int loginID = ftp->login(); 這時,我們就可以用if(id == loginID)來判斷執行的是否是login()函數。但是,我們不想為每個命令都設定一個變數來儲存其傳回值,所以,我們這裡使用了ftp->currentCommand() ,它也能擷取當前執行的命令的類型。在這個函數裡我們讓開始不同的命令時顯示不同的狀態資訊。

void Widget::ftpCommandFinished(int,bool error)

{

    if(ftp->currentCommand() == QFtp::ConnectToHost){

        if(error) ui->label->setText(tr(“串連伺服器出現錯誤:%1″).arg(ftp->errorString()));

        else ui->label->setText(tr(“串連到伺服器成功”));

    }

    if (ftp->currentCommand() == QFtp::Login){

        if(error) ui->label->setText(tr(“登入出現錯誤:%1″).arg(ftp->errorString()));

        else ui->label->setText(tr(“登入成功”));

    }

    if (ftp->currentCommand() == QFtp::Get){

        if(error) ui->label->setText(tr(“下載出現錯誤:%1″).arg(ftp->errorString()));

        else {

            ui->label->setText(tr(“已經完成下載”));

            ui->textBrowser->setText(ftp->readAll());

        }

    }

    else if (ftp->currentCommand() == QFtp::Close){

        ui->label->setText(tr(“已經關閉串連”));

    }

}

這個函數與ftpCommandStarted()函數相似,但是,它是在一個命令執行結束時執行的。它有兩個參數,第一個int id,就是調用命令時返回的編號,我們在上面已經講過了。第二個是bool error,它標誌現在執行的命令是否出現了錯誤。如果出現了錯誤,那麼error 為true ,否則為false。我們可以利用它來輸出錯誤資訊。在這個函數中,我們在完成一條命令時顯示不同的狀態資訊,並顯示可能的出錯資訊。在if (ftp->currentCommand() == QFtp::Get) 中,也就是已經完成下載時,我們讓textBrowser顯示下載的資訊。

6.運行程式,效果如下。

登入狀態。

 

下載完成後。

 

7.出錯示範。

下面我們示範一下出錯時的情況。

將建構函式中的代碼ftp->login();改為ftp->login(“tom”,”123456″);

這時我們再運行程式:

 

可以看到,它輸出了錯誤資訊,指明了錯誤的指令和出錯的內容。其實我們設定的這個錯誤,也是想告訴大家,在FTP中如果沒有設定使用者名稱和密碼,那麼預設的使用者名稱應該是anonymous,這時密碼可以任意填寫,而使用其他使用者名稱是會出錯的。

     在下一節中,我們將會對這個程式進行擴充,讓它可以瀏覽伺服器上的所有檔案,並進行下載。

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.