Posting multipart http request with QNAM and getting thread crash
-
I'm trying to post a multipart http request with image to the server. Found this example of doing this: http://blog.ilric.org/2010/11/20/qt-http-post-multi-partupload/
I am implementing this on Nokia E7 device, and currently I'm getting thread crash:
@Thread has crashed: A data abort exception has occurred accessing 0x1.@Here is the code I'm using:
@void Uploader::Upload(QString path) {
QNetworkAccessManager *http;
QVector<QNetworkReply *> response;
QFileInfo finfo(path);
QNetworkRequest r(QUrl("http://myserver.com/postimage.php"));QString bound="---------------------------723690991551375838472828858"; QByteArray data(QString("--"+bound+"\r\n").toAscii()); data += "Content-Disposition: form-data; name=\"text\"\r\n\r\n"; data += "Text\r\n"; data += QString("--" + bound + "\r\n").toAscii(); data += "Content-Disposition: form-data; name=\"clientid\"\r\n\r\n"; data += "\r\n"; data += QString("--" + bound + "\r\n").toAscii(); data += "Content-Disposition: form-data; name=\"file\"; filename=\""+finfo.fileName()+"\"\r\n"; data += QString("--" + bound + "\r\n").toAscii(); data += "Content-Type: image/jpeg\r\n\r\n"; QFile file(path); if (!file.open(QIODevice::ReadOnly)) return; data += file.readAll(); data += "\r\n"; data += QString("--" + bound + "\r\n").toAscii(); r.setRawHeader(QString("Accept-Encoding").toAscii(), QString("gzip,deflate").toAscii()); r.setRawHeader(QString("Content-Type").toAscii(),QString("multipart/form-data; boundary=" + bound).toAscii()); r.setRawHeader(QString("Content-Length").toAscii(), QString::number(data.length()).toAscii()); //rep->deleteLater(); response.push_back(http->post(r, data));
}@
The whole thing crashes on that last line when doint http->post(). I wonder what might be wrong? Could it be mobile specific?
-
Ok, the reason was that http object wasn't initialized :D
@http=new QNetworkAccessManager(this);@
-
Maybe you should also do something like this (depending on your use of Uploader):
@
connect(http, SIGNAL(finished(QNetworkReply*)), this, SLOT(deleteLater()));
@
or
@
connect(http, SIGNAL(finished(QNetworkReply*)), http, SLOT(deleteLater()));
@Otherwise all those QNetworkAccessManager instances will stay in memory until the Uploader object is being deleted.
Did you consider making QNetworkAccessManager a member of the Uploader class and initialize it in the Uploader constructor to reuse it in each call to Upload?
-
Thanks, good hint. I'll do that deleteLater().
I'm currently having this QNAM as a class member, just copied it into the method for this question.
-
If you have it as a class member you should not use the QNAM's deleteLater slot as it will be automatically deleted with its parent.
But you should take care that you don't delete the Uploader object before all running transfers have finished. Otherwise you'll cancel them.
-
Thanks, good point!
-
By the way, any idea how to get a JSON object out of QNetworkReply? My server is suppose to return a JSON response on success, and I'm trying to figure out if it is in the QNetworkReply, and where exactly?
-
QNetworkReply inherits from QIODevice. So can can simple use readAll to get the UTF-8 encoded string as a QByteArray.