Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • Users
  • Groups
  • Search
  • Get Qt Extensions
  • Unsolved
Collapse
Brand Logo
  1. Home
  2. Qt Development
  3. General and Desktop
  4. Using QNetworkAccessManager to download a file
Forum Updated to NodeBB v4.3 + New Features

Using QNetworkAccessManager to download a file

Scheduled Pinned Locked Moved Solved General and Desktop
12 Posts 3 Posters 1.9k Views 2 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • tomyT Offline
    tomyT Offline
    tomy
    wrote on last edited by
    #1

    Hi all,

    In the following example:

    downloader.h:

    #ifndef DOWNLOADER_H
    #define DOWNLOADER_H
    
    #include <QObject>
    #include <QNetworkAccessManager>
    #include <QNetworkRequest>
    #include <QNetworkReply>
    #include <QUrl>
    #include <QDateTime>
    #include <QFile>
    #include <QDebug>
    
    class Downloader : public QObject
    {
        Q_OBJECT
    public:
        explicit Downloader(QObject *parent = nullptr);
        void doDownload();
    
    public slots:
        void replyFinished(QNetworkReply*);
    
    private:
        QNetworkAccessManager* manager;
    };
    
    #endif // DOWNLOADER_H
    

    downloader.cpp:

    #include "downloader.h"
    
    Downloader::Downloader(QObject *parent) : QObject(parent){ }
    
    //**********************************************
    
    void Downloader::doDownload()
    {
        manager = new QNetworkAccessManager(this);
        connect(manager, &QNetworkAccessManager::finished, this, &Downloader::replyFinished);
        manager->get(QNetworkRequest(QUrl("http://qt-project.org")));
    }
    
    //******************************************************
    
    void Downloader::replyFinished(QNetworkReply* reply)
    {
        if(reply->error())
        {
            qDebug() << "ERROR!";
            qDebug() << reply->errorString();
        }
    
        else
        {
            qDebug() << "1) " << reply->header(QNetworkRequest::ContentTypeHeader).toString();
            qDebug() << "2) " << reply->header(QNetworkRequest::LastModifiedHeader).toDateTime().toString();
            qDebug() << "3) " << reply->header(QNetworkRequest::ContentLengthHeader).toULongLong();
            qDebug() << "4) " << reply->attribute(QNetworkRequest::HttpStatusCodeAttribute).toInt();
            qDebug() << "5) " << reply->attribute(QNetworkRequest::HttpReasonPhraseAttribute).toString();
    
            QFile* file = new QFile("C:/Users/ME/Desktop/downloaded.txt");
    
            if(file->open(QFile::Append))
            {
                qDebug() <<"The text file is open";
                file->write(reply->readAll());
                file->flush();
                file->close();
            }
            delete file;
        }
    
        reply->deleteLater();
    }
    

    main.cpp:

    #include <QCoreApplication>
    #include "downloader.h"
    
    int main(int argc, char *argv[])
    {
        QCoreApplication a(argc, argv);
    
        Downloader d;
        d.doDownload();
    
        return a.exec();
    }
    

    Why nothing is written in the downloaded.txt file please? Is it because the server, here the qt website, doesn't send any data and ...ContentLengthHeader).toULongLong() is zero?

    jsulmJ 1 Reply Last reply
    0
    • tomyT Offline
      tomyT Offline
      tomy
      wrote on last edited by tomy
      #12

      I think done! :)

      First I downloaded Win64 OpenSSL v1.1.1f EXE | MSI (experimental) 63MB Installer from https://slproweb.com/products/Win32OpenSSL.html. Then installed the program and went and copied the path: C:\Program Files\OpenSSL-Win64\bin. After these on Projects > Run > Run Environment > clicked on path and then the button "Append path" and pasted the above path.
      Now the program works for both "http" and "https" websites and the text file is also populated from the data received by QNetwork reply.

      It's 4:55 am here. It's time to sleep now. :)

      1 Reply Last reply
      0
      • tomyT tomy

        Hi all,

        In the following example:

        downloader.h:

        #ifndef DOWNLOADER_H
        #define DOWNLOADER_H
        
        #include <QObject>
        #include <QNetworkAccessManager>
        #include <QNetworkRequest>
        #include <QNetworkReply>
        #include <QUrl>
        #include <QDateTime>
        #include <QFile>
        #include <QDebug>
        
        class Downloader : public QObject
        {
            Q_OBJECT
        public:
            explicit Downloader(QObject *parent = nullptr);
            void doDownload();
        
        public slots:
            void replyFinished(QNetworkReply*);
        
        private:
            QNetworkAccessManager* manager;
        };
        
        #endif // DOWNLOADER_H
        

        downloader.cpp:

        #include "downloader.h"
        
        Downloader::Downloader(QObject *parent) : QObject(parent){ }
        
        //**********************************************
        
        void Downloader::doDownload()
        {
            manager = new QNetworkAccessManager(this);
            connect(manager, &QNetworkAccessManager::finished, this, &Downloader::replyFinished);
            manager->get(QNetworkRequest(QUrl("http://qt-project.org")));
        }
        
        //******************************************************
        
        void Downloader::replyFinished(QNetworkReply* reply)
        {
            if(reply->error())
            {
                qDebug() << "ERROR!";
                qDebug() << reply->errorString();
            }
        
            else
            {
                qDebug() << "1) " << reply->header(QNetworkRequest::ContentTypeHeader).toString();
                qDebug() << "2) " << reply->header(QNetworkRequest::LastModifiedHeader).toDateTime().toString();
                qDebug() << "3) " << reply->header(QNetworkRequest::ContentLengthHeader).toULongLong();
                qDebug() << "4) " << reply->attribute(QNetworkRequest::HttpStatusCodeAttribute).toInt();
                qDebug() << "5) " << reply->attribute(QNetworkRequest::HttpReasonPhraseAttribute).toString();
        
                QFile* file = new QFile("C:/Users/ME/Desktop/downloaded.txt");
        
                if(file->open(QFile::Append))
                {
                    qDebug() <<"The text file is open";
                    file->write(reply->readAll());
                    file->flush();
                    file->close();
                }
                delete file;
            }
        
            reply->deleteLater();
        }
        

        main.cpp:

        #include <QCoreApplication>
        #include "downloader.h"
        
        int main(int argc, char *argv[])
        {
            QCoreApplication a(argc, argv);
        
            Downloader d;
            d.doDownload();
        
            return a.exec();
        }
        

        Why nothing is written in the downloaded.txt file please? Is it because the server, here the qt website, doesn't send any data and ...ContentLengthHeader).toULongLong() is zero?

        jsulmJ Offline
        jsulmJ Offline
        jsulm
        Lifetime Qt Champion
        wrote on last edited by
        #2

        @tomy said in Using QNetworkAccessManager to download a file:

        QFile* file = new QFile

        There is no need to allocate file on the heap.

        Was the file opened successfully?
        Did you try

        qDebug() << reply->readAll()
        

        ?
        Also, if I open the URL in a browser I see that it is redirected to an HTTPS URL. Could be that you don't have working OpenSSL in your Qt set-up.

        https://forum.qt.io/topic/113070/qt-code-of-conduct

        tomyT 1 Reply Last reply
        2
        • jsulmJ jsulm

          @tomy said in Using QNetworkAccessManager to download a file:

          QFile* file = new QFile

          There is no need to allocate file on the heap.

          Was the file opened successfully?
          Did you try

          qDebug() << reply->readAll()
          

          ?
          Also, if I open the URL in a browser I see that it is redirected to an HTTPS URL. Could be that you don't have working OpenSSL in your Qt set-up.

          tomyT Offline
          tomyT Offline
          tomy
          wrote on last edited by
          #3

          @jsulm

          In,

          QFile* file = new QFile("C:/Users/ME/Desktop/downloaded.txt");
          
                 if(file->open(QFile::Append))
                 {
                     qDebug() <<"The text file is open";
                     file->write(reply->readAll());
                     file->flush();
                     file->close();
                 }
                 delete file;
          

          I have deleted file right at the point where it's not anymore needed. Is that heap allocation deprecated? Any general rule to obey, please?

          The qDebug() <<"The text file is open"; works and outputs the message, so the file opens, I assume.

          you don't have working OpenSSL in your Qt set-up.

          On my Qt set-up? Will you explain it please?

          jsulmJ Pablo J. RoginaP 2 Replies Last reply
          0
          • tomyT tomy

            @jsulm

            In,

            QFile* file = new QFile("C:/Users/ME/Desktop/downloaded.txt");
            
                   if(file->open(QFile::Append))
                   {
                       qDebug() <<"The text file is open";
                       file->write(reply->readAll());
                       file->flush();
                       file->close();
                   }
                   delete file;
            

            I have deleted file right at the point where it's not anymore needed. Is that heap allocation deprecated? Any general rule to obey, please?

            The qDebug() <<"The text file is open"; works and outputs the message, so the file opens, I assume.

            you don't have working OpenSSL in your Qt set-up.

            On my Qt set-up? Will you explain it please?

            jsulmJ Offline
            jsulmJ Offline
            jsulm
            Lifetime Qt Champion
            wrote on last edited by
            #4

            @tomy said in Using QNetworkAccessManager to download a file:

            Is that heap allocation deprecated?

            There is simply no need for heap allocation here. Also, stack allocation is a lot faster than heap.
            Look, isn't this simpler?

            QFile file("C:/Users/ME/Desktop/downloaded.txt");
            if(file.open(QFile::Append))
            {
                   qDebug() <<"The text file is open";
                   file.write(reply->readAll());
                   file.flush();
                   file.close();
            }
            

            And as additional bonus: you can't forget to delete it (as you could forget to put "delete file" there).

            Take a look at https://doc.qt.io/qt-5/ssl.html

            https://forum.qt.io/topic/113070/qt-code-of-conduct

            1 Reply Last reply
            1
            • tomyT tomy

              @jsulm

              In,

              QFile* file = new QFile("C:/Users/ME/Desktop/downloaded.txt");
              
                     if(file->open(QFile::Append))
                     {
                         qDebug() <<"The text file is open";
                         file->write(reply->readAll());
                         file->flush();
                         file->close();
                     }
                     delete file;
              

              I have deleted file right at the point where it's not anymore needed. Is that heap allocation deprecated? Any general rule to obey, please?

              The qDebug() <<"The text file is open"; works and outputs the message, so the file opens, I assume.

              you don't have working OpenSSL in your Qt set-up.

              On my Qt set-up? Will you explain it please?

              Pablo J. RoginaP Offline
              Pablo J. RoginaP Offline
              Pablo J. Rogina
              wrote on last edited by
              #5

              @tomy just in case, this example may be of inspiration

              Upvote the answer(s) that helped you solve the issue
              Use "Topic Tools" button to mark your post as Solved
              Add screenshots via postimage.org
              Don't ask support requests via chat/PM. Please use the forum so others can benefit from the solution in the future

              1 Reply Last reply
              0
              • tomyT Offline
                tomyT Offline
                tomy
                wrote on last edited by tomy
                #6

                @jsulm

                Take a look at https://doc.qt.io/qt-5/ssl.html

                Thanks. I did but it's very confusing. I've not done this before. Let me explain please:
                I downloaded openssl-1.1.1f and found the file opensslv.h in the include folder of it. Now should I add this file to "...\mingw73_64\bin" and include that header in the downloader.h?

                @Pablo-J-Rogina
                Thank you. Why does the code have C style!?
                Is this example not better?

                Pablo J. RoginaP 1 Reply Last reply
                0
                • tomyT tomy

                  @jsulm

                  Take a look at https://doc.qt.io/qt-5/ssl.html

                  Thanks. I did but it's very confusing. I've not done this before. Let me explain please:
                  I downloaded openssl-1.1.1f and found the file opensslv.h in the include folder of it. Now should I add this file to "...\mingw73_64\bin" and include that header in the downloader.h?

                  @Pablo-J-Rogina
                  Thank you. Why does the code have C style!?
                  Is this example not better?

                  Pablo J. RoginaP Offline
                  Pablo J. RoginaP Offline
                  Pablo J. Rogina
                  wrote on last edited by
                  #7

                  @tomy said in Using QNetworkAccessManager to download a file:

                  Is this example not better?

                  It's another example from same author. If you feel comfortable with that, it's Ok. It has a fancy GUI I guess

                  Upvote the answer(s) that helped you solve the issue
                  Use "Topic Tools" button to mark your post as Solved
                  Add screenshots via postimage.org
                  Don't ask support requests via chat/PM. Please use the forum so others can benefit from the solution in the future

                  1 Reply Last reply
                  0
                  • tomyT Offline
                    tomyT Offline
                    tomy
                    wrote on last edited by tomy
                    #8

                    I myself created the GUI part by code in a project under the name GuiHttpDownload as follows:

                    GuiHttpDownload.h

                    #ifndef GUIHTTPDOWNLOAD_H
                    #define GUIHTTPDOWNLOAD_H
                    
                    #include <QWidget>
                    #include <QNetworkAccessManager>
                    #include <QNetworkRequest>
                    #include <QNetworkReply>
                    #include <QUrl>
                    #include <QDateTime>
                    #include <QFile>
                    #include <QDebug>
                    
                    class QPushButton;
                    class QTextEdit;
                    class GuiHttpDownload : public QWidget
                    {
                        Q_OBJECT
                    
                    public:
                        GuiHttpDownload(QWidget *parent = nullptr);
                        ~GuiHttpDownload();
                    
                    public slots:
                        void replyFinished(QNetworkReply*);
                    
                    private:
                        QPushButton* download;
                        QPushButton* quit;
                        QTextEdit* textEdit;
                        QNetworkAccessManager* manager;
                    };
                    #endif // GUIHTTPDOWNLOAD_H
                    

                    GuiHttpDownload.cpp

                    #include "guihttpdownload.h"
                    #include <QPushButton>
                    #include <QTextEdit>
                    #include <QHBoxLayout>
                    #include <QVBoxLayout>
                    
                    GuiHttpDownload::GuiHttpDownload(QWidget *parent)
                        : QWidget(parent)
                    {
                        download = new QPushButton("&Download");
                        quit = new QPushButton("&Quit");
                        textEdit = new QTextEdit;
                        manager = new QNetworkAccessManager(this);
                    
                         connect(manager, &QNetworkAccessManager::finished,
                                 this, &GuiHttpDownload::replyFinished);
                         connect(download, &QPushButton::clicked, [this]() {
                             this->manager->get(QNetworkRequest(QUrl("http://qt-project.org")));
                         });
                         connect(quit, &QPushButton::clicked, this, &GuiHttpDownload::close);
                    
                        QHBoxLayout* hLayout = new QHBoxLayout;
                        hLayout->addWidget(download);
                        hLayout->addWidget(quit);
                    
                        QVBoxLayout* vLayout = new QVBoxLayout;
                        vLayout->addWidget(textEdit);
                        vLayout->addLayout(hLayout);
                    
                        setLayout(vLayout);
                    
                        setWindowTitle("Download Test");
                    }
                    
                    //*********************************************
                    
                    GuiHttpDownload::~GuiHttpDownload()
                    {
                        delete download;
                        delete quit;
                        delete manager;
                    }
                    
                    //***************************************************************
                    
                    void GuiHttpDownload::replyFinished(QNetworkReply* reply)
                    {
                        if(reply->error())
                        {
                            textEdit->insertPlainText("ERROR!");
                            textEdit->insertPlainText(reply->errorString());
                        }
                    
                        else
                        {
                            textEdit->insertPlainText("1) " + reply->header(QNetworkRequest::ContentTypeHeader).toString());
                            textEdit->insertPlainText("\n2) " + reply->header(QNetworkRequest::LastModifiedHeader).toDateTime().toString());
                            textEdit->insertPlainText("\n3) " + reply->header(QNetworkRequest::ContentLengthHeader).toULongLong());
                            textEdit->insertPlainText("\n4) " + reply->attribute(QNetworkRequest::HttpStatusCodeAttribute).toInt());
                            textEdit->insertPlainText("\n5) " + reply->attribute(QNetworkRequest::HttpReasonPhraseAttribute).toString());
                    
                            QFile file("C:/Users/ME/Desktop/downloaded.txt");
                    
                            if(file.open(QFile::Append))
                            {
                                textEdit->insertPlainText("\n\nThe text file is open\n");
                                file.write(reply->readAll());
                                file.flush();
                                file.close();
                            }
                        }
                    
                        reply->deleteLater();
                    }
                    

                    main.cpp

                    #include "guihttpdownload.h"
                    
                    #include <QApplication>
                    
                    int main(int argc, char *argv[])
                    {
                        QApplication a(argc, argv);
                        GuiHttpDownload w;
                        w.show();
                        return a.exec();
                    }
                    

                    It works rather fine. But still I've not found the correct way to have working OpenSSL in my Qt set-up!
                    @jsulm if possible, please help me on that.
                    Is the way I stated on my above post right for the job? I didn't find a solution to use it and solve the problem either.

                    Pablo J. RoginaP 1 Reply Last reply
                    0
                    • tomyT tomy

                      I myself created the GUI part by code in a project under the name GuiHttpDownload as follows:

                      GuiHttpDownload.h

                      #ifndef GUIHTTPDOWNLOAD_H
                      #define GUIHTTPDOWNLOAD_H
                      
                      #include <QWidget>
                      #include <QNetworkAccessManager>
                      #include <QNetworkRequest>
                      #include <QNetworkReply>
                      #include <QUrl>
                      #include <QDateTime>
                      #include <QFile>
                      #include <QDebug>
                      
                      class QPushButton;
                      class QTextEdit;
                      class GuiHttpDownload : public QWidget
                      {
                          Q_OBJECT
                      
                      public:
                          GuiHttpDownload(QWidget *parent = nullptr);
                          ~GuiHttpDownload();
                      
                      public slots:
                          void replyFinished(QNetworkReply*);
                      
                      private:
                          QPushButton* download;
                          QPushButton* quit;
                          QTextEdit* textEdit;
                          QNetworkAccessManager* manager;
                      };
                      #endif // GUIHTTPDOWNLOAD_H
                      

                      GuiHttpDownload.cpp

                      #include "guihttpdownload.h"
                      #include <QPushButton>
                      #include <QTextEdit>
                      #include <QHBoxLayout>
                      #include <QVBoxLayout>
                      
                      GuiHttpDownload::GuiHttpDownload(QWidget *parent)
                          : QWidget(parent)
                      {
                          download = new QPushButton("&Download");
                          quit = new QPushButton("&Quit");
                          textEdit = new QTextEdit;
                          manager = new QNetworkAccessManager(this);
                      
                           connect(manager, &QNetworkAccessManager::finished,
                                   this, &GuiHttpDownload::replyFinished);
                           connect(download, &QPushButton::clicked, [this]() {
                               this->manager->get(QNetworkRequest(QUrl("http://qt-project.org")));
                           });
                           connect(quit, &QPushButton::clicked, this, &GuiHttpDownload::close);
                      
                          QHBoxLayout* hLayout = new QHBoxLayout;
                          hLayout->addWidget(download);
                          hLayout->addWidget(quit);
                      
                          QVBoxLayout* vLayout = new QVBoxLayout;
                          vLayout->addWidget(textEdit);
                          vLayout->addLayout(hLayout);
                      
                          setLayout(vLayout);
                      
                          setWindowTitle("Download Test");
                      }
                      
                      //*********************************************
                      
                      GuiHttpDownload::~GuiHttpDownload()
                      {
                          delete download;
                          delete quit;
                          delete manager;
                      }
                      
                      //***************************************************************
                      
                      void GuiHttpDownload::replyFinished(QNetworkReply* reply)
                      {
                          if(reply->error())
                          {
                              textEdit->insertPlainText("ERROR!");
                              textEdit->insertPlainText(reply->errorString());
                          }
                      
                          else
                          {
                              textEdit->insertPlainText("1) " + reply->header(QNetworkRequest::ContentTypeHeader).toString());
                              textEdit->insertPlainText("\n2) " + reply->header(QNetworkRequest::LastModifiedHeader).toDateTime().toString());
                              textEdit->insertPlainText("\n3) " + reply->header(QNetworkRequest::ContentLengthHeader).toULongLong());
                              textEdit->insertPlainText("\n4) " + reply->attribute(QNetworkRequest::HttpStatusCodeAttribute).toInt());
                              textEdit->insertPlainText("\n5) " + reply->attribute(QNetworkRequest::HttpReasonPhraseAttribute).toString());
                      
                              QFile file("C:/Users/ME/Desktop/downloaded.txt");
                      
                              if(file.open(QFile::Append))
                              {
                                  textEdit->insertPlainText("\n\nThe text file is open\n");
                                  file.write(reply->readAll());
                                  file.flush();
                                  file.close();
                              }
                          }
                      
                          reply->deleteLater();
                      }
                      

                      main.cpp

                      #include "guihttpdownload.h"
                      
                      #include <QApplication>
                      
                      int main(int argc, char *argv[])
                      {
                          QApplication a(argc, argv);
                          GuiHttpDownload w;
                          w.show();
                          return a.exec();
                      }
                      

                      It works rather fine. But still I've not found the correct way to have working OpenSSL in my Qt set-up!
                      @jsulm if possible, please help me on that.
                      Is the way I stated on my above post right for the job? I didn't find a solution to use it and solve the problem either.

                      Pablo J. RoginaP Offline
                      Pablo J. RoginaP Offline
                      Pablo J. Rogina
                      wrote on last edited by
                      #9

                      @tomy said in Using QNetworkAccessManager to download a file:

                      But still I've not found the correct way to have working OpenSSL in my Qt set-up!

                      Could you please state:

                      1. the OS
                      2. how did you installed Qt framework?
                      3. what compiler are you using?

                      Upvote the answer(s) that helped you solve the issue
                      Use "Topic Tools" button to mark your post as Solved
                      Add screenshots via postimage.org
                      Don't ask support requests via chat/PM. Please use the forum so others can benefit from the solution in the future

                      tomyT 1 Reply Last reply
                      0
                      • Pablo J. RoginaP Pablo J. Rogina

                        @tomy said in Using QNetworkAccessManager to download a file:

                        But still I've not found the correct way to have working OpenSSL in my Qt set-up!

                        Could you please state:

                        1. the OS
                        2. how did you installed Qt framework?
                        3. what compiler are you using?
                        tomyT Offline
                        tomyT Offline
                        tomy
                        wrote on last edited by
                        #10

                        @Pablo-J-Rogina

                        Could you please state:

                        1. the OS

                        Windows 10 x64

                        1. how did you installed Qt framework?

                        The online installer

                        1. what compiler are you using?

                        MinGW x64

                        Pablo J. RoginaP 1 Reply Last reply
                        0
                        • tomyT tomy

                          @Pablo-J-Rogina

                          Could you please state:

                          1. the OS

                          Windows 10 x64

                          1. how did you installed Qt framework?

                          The online installer

                          1. what compiler are you using?

                          MinGW x64

                          Pablo J. RoginaP Offline
                          Pablo J. RoginaP Offline
                          Pablo J. Rogina
                          wrote on last edited by
                          #11

                          @tomy so then it's very likely the OpenSSL DLLs cannot be found by your app.
                          Please connect the QNetworkAccessManager::sslErrors() signal to a slot and check the error(s) there.

                          Upvote the answer(s) that helped you solve the issue
                          Use "Topic Tools" button to mark your post as Solved
                          Add screenshots via postimage.org
                          Don't ask support requests via chat/PM. Please use the forum so others can benefit from the solution in the future

                          1 Reply Last reply
                          1
                          • tomyT Offline
                            tomyT Offline
                            tomy
                            wrote on last edited by tomy
                            #12

                            I think done! :)

                            First I downloaded Win64 OpenSSL v1.1.1f EXE | MSI (experimental) 63MB Installer from https://slproweb.com/products/Win32OpenSSL.html. Then installed the program and went and copied the path: C:\Program Files\OpenSSL-Win64\bin. After these on Projects > Run > Run Environment > clicked on path and then the button "Append path" and pasted the above path.
                            Now the program works for both "http" and "https" websites and the text file is also populated from the data received by QNetwork reply.

                            It's 4:55 am here. It's time to sleep now. :)

                            1 Reply Last reply
                            0

                            • Login

                            • Login or register to search.
                            • First post
                              Last post
                            0
                            • Categories
                            • Recent
                            • Tags
                            • Popular
                            • Users
                            • Groups
                            • Search
                            • Get Qt Extensions
                            • Unsolved