2016-12-19 1 views
0

Je suis impatient de créer un client pour un service Web. Mon but est de envoyer une demande à mon serveur chaque seconde. J'ai utilisé cette bibliothèque pour me aider: QHttpPassez QCoreApplication dans le paramètre

Je crée une minuterie que je créer un lien avec un signal à mon QCoreApplication app et envoie ma demande lorsque la portée de la minuterie 1 seconde.

Voici comment je le fais:

main.cpp

#include "request.h" 

int main(int argc, char** argv) { 

    QCoreApplication app(argc, argv); 
    Request* request = new Request(); 
    request->sendRequestPeriodically(1000, app); 


    return app.exec(); 
} 

request.h

//lots of include before 
class Request 
{ 
    Q_OBJECT 

public: 
    Request(); 
    void sendRequestPeriodically (int time, QCoreApplication app); 

public slots: 
    void sendRequest (QCoreApplication app); 

}; 

request.cpp

#include "request.h" 

void Request::sendRequest (QCoreApplication app){ 
    using namespace qhttp::client; 
    QHttpClient client(&app); 
    QUrl  server("http://127.0.0.1:8080/?Clearance"); 

    client.request(qhttp::EHTTP_GET, server, [](QHttpResponse* res) { 
     // response handler, called when the incoming HTTP headers are ready 


     // gather HTTP response data (HTTP body) 
     res->collectData(); 

     // when all data in HTTP response have been read: 
     res->onEnd([res]() { 
      // print the XML body of the response 
      qDebug("\nreceived %d bytes of http body:\n%s\n", 
        res->collectedData().size(), 
        res->collectedData().constData() 
       ); 

      // done! now quit the application 
      //qApp->quit(); 
     }); 

    }); 

    // set a timeout for the http connection 
    client.setConnectingTimeOut(10000, []{ 
     qDebug("connecting to HTTP server timed out!"); 
     qApp->quit(); 
    }); 
} 

void Request::sendRequestPeriodically(int time, QCoreApplication app){ 
    QTimer *timer = new QTimer(this); 
    QObject::connect(timer, SIGNAL(timeout()), this, SLOT(sendRequest(app))); 
    timer->start(time); //time specified in ms 
} 

Request::Request() 
{ 

} 

J'ai eu ces erreurs:

C:\Qt\5.7\mingw53_32\include\QtCore\qcoreapplication.h:211: erreur : 'QCoreApplication::QCoreApplication(const QCoreApplication&)' is private 
    Q_DISABLE_COPY(QCoreApplication) 

C:\Users\ebelloei\Documents\qhttp\example\client-aircraft\main.cpp:7: erreur : use of deleted function 'QCoreApplication::QCoreApplication(const QCoreApplication&)' 

Je suis nouveau à Qt, mais je suppose que cela vient du fait que je ne peux pas mon passe QCoreApplication dans les paramètres, est ce droit?

Répondre

4

Tout d'abord, si vous devez accéder à l'instance d'application globale, vous ne devez pas la transmettre. Utilisez la macro qApp ou QCoreApplication::instance().

Mais c'est en plus le point: l'instance QHttpClient client est une variable locale dont la durée de vie est gérée par le compilateur. Il ne sert à rien de lui donner un parent. Le client se détruit juste comme sendRequest quitte: votre sendRequest est effectivement un no-op à cause de cela.

Vous avez également des erreurs dans vos déclarations connect: vous ne pouvez pas transmettre des valeurs d'argument en utilisant l'ancien style connect syntaxe:

// Wrong: the connection fails and does nothing. 
connect(timer, SIGNAL(timeout()), this, SLOT(sendRequest(foo))); 
// Qt 5 
connect(timer, &QTimer::timeout, this, [=]{ sendRequest(foo); }); 
// Qt 4 
this->foo = foo; 
connect(timer, SIGNAL(timeout()), this, SLOT(sendRequest())); 
    // sendRequest would then use this->foo 

Idéalement, vous devriez revoir votre code pour utiliser QNetworkAccessManager.Sinon, vous devez garder l'instance QHttpClient vivant dans les main:

int main(int argc, char** argv) { 
    QCoreApplication app(argc, argv); 
    qhttp::client::QHttpClient client; 
    auto request = new Request(&client); 
    request->sendRequestPeriodically(1000); 
    return app.exec(); 
} 

Et puis:

class Request : public QObject 
{ 
    Q_OBJECT 
    QTimer m_timer{this}; 
    qhttp::client::QHttpClient *m_client; 
public: 
    explicit Request(qhttp::client::QHttpClient *client); 
    void sendRequestPeriodically(int time); 
    void sendRequest(); 
}; 

Request::Request(qhttp::client::QHttpClient *client) : 
    QObject{client}, 
    m_client{client} 
{ 
    QObject::connect(&m_timer, &QTimer::timeout, this, &Request::sendRequest); 
} 

void Request::sendRequestPeriodically(int time) { 
    timer->start(time); 
} 

void Request::sendRequest() { 
    QUrl server("http://127.0.0.1:8080/?Clearance"); 

    m_client->request(qhttp::EHTTP_GET, server, [](QHttpResponse* res) { 
     ... 
    }); 
} 
+0

Réponse très forte, et la compréhension de mon problème. Je me souviens avoir demandé quelque chose il y a 4 ans ici et avoir une réponse de votre part, merci pour votre travail. –

1

Vous ne pouvez pas passer un objet copie QCoreApplication via son constructeur de copie, vous devez passer un pointeur à QCoreApplication.

Toute l'application "QCoreApplication" doit être remplacée par "QCoreApplication * app" et les appels à ces fonctions doivent inclure un pointeur vers l'application et non une copie de celle-ci.

request.h

//lots of include before 
class Request 
{ 
    Q_OBJECT 

public: 
    Request(); 
    void sendRequestPeriodically (int time, QCoreApplication *app); 

public slots: 
    void sendRequest (QCoreApplication *app); 

}; 

request.cpp

#include "request.h" 

void Request::sendRequest (QCoreApplication *app){ 
    using namespace qhttp::client; 
    QHttpClient client(app); 
    QUrl  server("http://127.0.0.1:8080/?Clearance"); 

    client.request(qhttp::EHTTP_GET, server, [](QHttpResponse* res) { 
     // response handler, called when the incoming HTTP headers are ready 


     // gather HTTP response data (HTTP body) 
     res->collectData(); 

     // when all data in HTTP response have been read: 
     res->onEnd([res]() { 
      // print the XML body of the response 
      qDebug("\nreceived %d bytes of http body:\n%s\n", 
        res->collectedData().size(), 
        res->collectedData().constData() 
       ); 

      // done! now quit the application 
      //qApp->quit(); 
     }); 

    }); 

    // set a timeout for the http connection 
    client.setConnectingTimeOut(10000, []{ 
     qDebug("connecting to HTTP server timed out!"); 
     qApp->quit(); 
    }); 
} 

void Request::sendRequestPeriodically(int time, QCoreApplication app){ 
    QTimer *timer = new QTimer(this); 
    QObject::connect(timer, SIGNAL(timeout()), this, SLOT(sendRequest(app))); 
    timer->start(time); //time specified in ms 
} 

Request::Request() 
{ 

} 

main.cpp

#include "request.h" 

int main(int argc, char** argv) { 

    QCoreApplication app(argc, argv); 
    Request* request = new Request(); 
    request->sendRequestPeriodically(1000, &app); 

    return app.exec(); 
} 

Modifier Comme KubaOber dit, il y a plus de problèmes dans votre code, lire sa réponse

+0

Ce manque les autres problèmes avec le code et ne fonctionnera pas comme indiqué. –

+0

@KubaOber pourriez-vous s'il vous plaît le rendre plus clair? –

+0

@KubaOber j'ai répondu à son erreur, vous avez là plus d'erreurs sur le code –