2016-05-22 3 views
0

Ich mache eine HTTP-Operation (Get, Post etc ...) mit QNetworkAccessManager. Ich mache ein paar "Get" -Operationen parallel. Dazu verwende ich QtConcurrent :: run (dies, & RestWebservice :: GetHTTPData), um mehrere HTTP-Operationen zu machen. Mein Problem ist Wenn ich die App schließe, bevor der HTTP-Vorgang nicht abgeschlossen ist, stürzt App ab.Application Output schreibe diese Zeile QMutex: zerstört gesperrt Mutex dann schreibe Das Programm wurde unerwartet beendet. ich Gase Problem in dieser LinieQt, QMutex: Zerstören gesperrter Mutex dann App Absturz

void RestWebservice::get() 
{ 
// mutex.lock(); 
    m_networkManager.get(m_networkrequest); 
// mutex.unlock(); 


} 

Aber ich bin nicht sicher, tritt auf, weil QtCreater Debugger nicht gut wie VS.By ist die Art und Weise, ist GetHTTPData in anderer Klasse.

MY CODE für Start Netzwerk Betrieb: (MobileOperation.cpp) .Für exapmle getUserAccount metod einen http Betrieb starten.

void MobileOperations::getWorkOrderListT(int ekipId) { 


    MyGlobal::Metods metod=MyGlobal::EkipIsEmriListesi; 
    QString parameters="{EkipId}"; 
    QMap<QString,QVariant> paramlist; 

    paramlist["EkipId"]=ekipId; 

    GetHTTPData(metod,parameters,paramlist); 

    if(m_workorder.IsSuccess==true) 
    { 

     // emit successupdatewo(); 

      if(m_workorder.workorders.count()>0) 
      { 
       InsertWo(json.workorder->workorders); 
      emit processstop("İş Emri Listesi Güncellendi"); 




      // QThread::sleep(2); 
      } 
      else 
      { 
       emit processstop(json.workorder->ReturnMessage); 
      } 

      emit successworkstart(); 

    } 
    else 
    { 
     emit processstop("Bağlantı Başarısız Oldu"); 
    } 


} 
    void MobileOperations::getUserAccount(QString kullaniciAdi, QString sifre,bool isremember) 
{ 
    json.user=m_user; 

    QtConcurrent::run(this,&MobileOperations::getUserAccountT,kullaniciAdi,sifre,isremember); 
    // getUserAccountT(kullaniciAdi,sifre,isremember); 
    processstart("Baglaniyor"); 




} 






void MobileOperations::GetHTTPData(MyGlobal::Metods MetodName, QString Parameters, QMap<QString, QVariant> paramlist) 
{ 

    try 
    { 
    parameter=new HttpRequest(); 
    parameter->url=m_url; 
    parameter->metodname=MetodName; 
    parameter->resource=m_path; 
    parameter->appid=m_appid; 
    parameter->apppass=m_apppass; 
    parameter->parametersname=Parameters; 
    parameter->params=paramlist; 
    rest= new RestWebservice(parameter->GenerateHTTPQuery(),MetodName); 
    // json=new JSonParser(); 
    // loop=new QEventLoop(); 

    loop=new QEventLoop(); 
    QObject::connect(rest,SIGNAL(sendhttpdata(QByteArray,MyGlobal::Metods)),&json,SLOT(onGetData(QByteArray,MyGlobal::Metods))); 
    QObject::connect(&json,SIGNAL(serilazitionCompleted()),loop,SLOT(quit())); 
    rest->get(); 
    loop->exec(); 
    } 

    catch(std::string &exp) 
    { 
     qDebug()<<"Sonlandırıldı"; 
    } 

} 

MEIN CODE Klasse Für HTTP operatins:

#include "restwebservice.h" 
#include <QJsonDocument> 
#include<QJsonArray> 
#include <QJsonObject> 
#include<QJsonValue> 
#include<QList> 
#include <QThread> 




RestWebservice::RestWebservice(QNetworkRequest request, 
           MyGlobal::Metods metod, 
           QObject* parent):QObject(parent),m_networkrequest(request),m_metodname(metod) 
{ 


    connect(&m_networkManager, SIGNAL(finished(QNetworkReply*)),this, SLOT(onResult(QNetworkReply*))); 
// connect(&m_networkManager,SIGNAL()) 

} 

void RestWebservice::get() 
{ 
    // mutex.lock(); 
    m_networkManager.get(m_networkrequest); 
// mutex.unlock(); 


} 

void RestWebservice::post(QString request) 
{ 

    QByteArray requestA= request.toUtf8(); 
    m_networkManager.post(m_networkrequest,requestA); 
} 

void RestWebservice::onResult(QNetworkReply* reply) 
{ 
    try 
    { 
     if (reply->error() != QNetworkReply::NoError) 
     { 



       qDebug()<<reply->error()<<":"<<reply->errorString(); 
       MyGlobal::NetworkStatus=reply->errorString(); 
       emit sendhttpdata(m_data,m_metodname); 
       return; 

      // throw(reply->errorString().toStdString()); 



     } 



     QByteArray data = reply->readAll(); 

     reply->deleteLater(); 
     m_data=data; 

     MyGlobal::NetworkStatus="Tablolar Yüklendi"; 
     emit sendhttpdata(m_data,m_metodname); 


} 

    catch(std::string exp) 
    { 
     qDebug()<<"Exception:"<<QString::fromStdString(exp); 


    } 

    catch(std::exception &exp) 
    { 
     qDebug()<<"Exception:"<<QString::fromStdString(exp.what()); 
    } 


} 

void RestWebservice::onError() 
{ 


    qDebug()<<"Hata VAR"; 
} 


HttpRequest::HttpRequest(QObject *parent) : 
    QObject(parent) 
{ 

} 

QNetworkRequest HttpRequest::GenerateHTTPQuery() 
{ 

    // QString path=""; 
    QString path=QString("/%1/%2/%3/%4/%5").arg(resource).arg(MyGlobal::getMetodName(metodname)).arg(appid).arg(apppass).arg(parametersname); 
    foreach (QString param, params.keys()) { 

     path.replace("{"+param+"}",params[param].toString()); 

    } 

    QUrl m_url(url); 
    m_url.setPath(path); 
    m_request.setUrl(m_url); 
    m_request.setRawHeader("Content-Type","application/json;charset=utf-8"); 
    // m_request.setRawHeader("SOAPAction","http://tempuri.org/IMobileClient/UserAuth"); 
    qDebug()<<m_url.url(); 


    return m_request; 

} 


QNetworkRequest HttpRequest::GenerateHTTPQueryPost() 
{ 

    // QString path=""; 
    QString path=QString("/%1/%2").arg(resource).arg(MyGlobal::getMetodName(metodname)); 
    QUrl m_url(url); 
    m_url.setPath(path); 
    m_request.setUrl(m_url); 
    m_request.setRawHeader("Content-Type","application/json;charset=utf-8"); 
    // m_request.setRawHeader("SOAPAction","http://tempuri.org/IMobileClient/UserAuth"); 
    qDebug()<<m_url.url(); 


    return m_request; 

} 
+0

Sie müssen 'QtConcurrent :: run nicht verwenden()' zu * mehr get Operationen parallel * laufen, 'QNetworkAccessManager' ist asynchron, so können Sie viele Anfragen im selben Thread starten und verbinden ihre' readyread() 'Signal zu Slots, die sie behandeln. Bitte zeigen Sie uns, wie genau Ihr Thread funktioniert, da ich denke, dass Sie Ihr Design ändern müssen. . . – Mike

+0

@Mike, wenn ich QtConcurrent :: run nicht verwende, ist App Windows einfrieren. –

Antwort

0

Sind Sie ein Mitglied der Klasse Mutex. In diesem Fall wird der Mutex zerstört, bevor er entsperrt wird (da ich anmaße, dass die umschließende Klasse den Gültigkeitsbereich verlässt), was die Nachricht verursacht, die Sie sehen. Der Destruktor des Mutex wird aufgerufen, wenn die Klasse zerstört wird, während die Sperre gehalten wird. Das ist ein Problem. Normalerweise müssen Sie eine Möglichkeit finden, während Ihrer Netzwerkanforderung nicht unbegrenzt zu blockieren.

+0

Ich benutze Mutex nicht. Das funktioniert nicht . Ich mache nur versuchen, dann commet Linie, die Mutex enthält. –

+0

Wenn Sie die Mutex taten verwenden, zeigte das Problem auf die Mutex verwendet. –